53

Have browsed, searched and hoped but cannot find a straight answer.

Is there anyway in C# 6.0 to get the current method name using nameof withouth specifying the method name?

I am adding my test results to a dictionary like this:

Results.Add(nameof(Process_AddingTwoConsents_ThreeExpectedRowsAreWrittenToStream), result);

I would prefer if I would not have to specify the method name explicitly so I can copy+paste the line, a non-working example:

Results.Add(nameof(this.GetExecutingMethod()), result);

If possible I do not want to use Reflection.

UPDATE

This is not (as suggested) a duplicate of this question. I am asking if is explicitly possible to make use of nameof without(!) reflection to get the current method name.

Community
  • 1
  • 1
Marcus
  • 8,230
  • 11
  • 61
  • 88
  • 1
    And why don´t you use this: http://stackoverflow.com/questions/44153/can-you-use-reflection-to-find-the-name-of-the-currently-executing-method? – MakePeaceGreatAgain Jun 29 '16 at 11:55
  • You can use `StackTrace` to get such info, but this is slow. To achieve something automatic you can use code-generation (e.g. a tool which run before compiler and replaces something with something else) or AOP (see [this](http://stackoverflow.com/q/25803/1997232)). – Sinatr Jun 29 '16 at 12:18
  • 1
    Wouldn't this do it? `System.Reflection.MethodInfo.GetCurrentMethod().Name` – Zorkind Feb 23 '18 at 20:50
  • 4
    He Literally said "without using reflection" – Gaspa79 Jul 10 '18 at 14:28

4 Answers4

115

You can't use nameof to achieve that, but how about this workaround:

The below uses no direct reflection (just like nameof) and no explicit method name.

Results.Add(GetCaller(), result);

public static string GetCaller([CallerMemberName] string caller = null)
{
    return caller;
}

GetCaller returns the name of any method that calls it.

Zein Makki
  • 29,485
  • 6
  • 52
  • 63
  • How does this help? You need the caller of the executing method, not the caller of `GetCaller`; unless you are proposing adding an optional parameter to *all* potentially callable methods in order to make this work which is, frankly, hideous. – InBetween Jun 29 '16 at 12:12
  • 11
    @InBetween The OP stated `"get the current method name"` . This does exactly what he stated ! You only need one `GetCaller` method that you can call from anywhere to get the current executing method name. – Zein Makki Jun 29 '16 at 12:13
  • I would recommend using `caller = null` since this is more obvious imo. Its also the example from MS istelf and R# – Mafii Jun 30 '16 at 07:19
  • Wish this had been around from the beginning... :-( – GreatAndPowerfulOz Jun 30 '17 at 21:20
  • 1
    this works greatly. The problem with nameof(method) is beyound simple copy-paste issues. When you use nameof(method) for logging, for example, visual studio counts 1 reference/caller in method for each nameof(method) you use. It becomes hard to identify if a method is not called by any other and can be safelly deleted – Vitor Luiz Rubio Aug 09 '22 at 16:17
15

Building on user3185569's great answer:

public static string GetMethodName(this object type, [CallerMemberName] string caller = null)
{
    return type.GetType().FullName + "." + caller;
}

Results in you being able to call this.GetMethodName() anywhere to return the fully qualified method name.

Mike Cole
  • 14,474
  • 28
  • 114
  • 194
  • How I call in ***static method*** ? not valid `this` – Kiquenet Oct 18 '18 at 14:25
  • @Kiquenet Make an overload of GetMethodName() that doesn't include the `type` parameter, and call it like any other static method. e.g. `Util.GetMethodName();` – jk7 Jul 15 '20 at 23:38
2

Same as others, but some variation:

    /// <summary>
    /// Returns the caller method name.
    /// </summary>
    /// <param name="type"></param>
    /// <param name="caller"></param>
    /// <param name="fullName">if true returns the fully qualified name of the type, including its namespace but not its assembly.</param>
    /// <returns></returns>
    public static string GetMethodName(this object type, [CallerMemberName] string caller = null, bool fullName = false)
    {
        if (type == null) throw new ArgumentNullException(nameof(type));
        var name = fullName ? type.GetType().FullName : type.GetType().Name;
        return $"{name}.{caller}()";
    }

Allows to call it like this:

Log.Debug($"Enter {this.GetMethodName()}...");
Chris
  • 1,122
  • 1
  • 12
  • 14
-1

If you want to add the name of the current method into the Results List then you may use this :

StackTrace sTrace= new StackTrace();
StackFrame sFrame= sTrace.GetFrame(0);
MethodBase currentMethodName = sFrame.GetMethod();
Results.Add(currentMethodName.Name, result);

Or you can use,

Results.Add(new StackTrace().GetFrame(0).GetMethod().Name, result);    
Sarath S Menon
  • 2,168
  • 1
  • 16
  • 21