Festivejelly
Festivejelly

Reputation: 690

Getting the declared name of a variable passed into a method C#

I've seen this discussed a few times before, and im not really sure if this is the best thing for me to be doing so any suggestions for improvement would be welcomed.

I'm trying to build some detailed logging for my Selenium tests.

I have a method call which is:

Admin_Login.Username.SetText("MyUsername");

Admin_Login is just a standard class. However "Username" is a variable passed into the "SetText" method which is shown below:

public static void SetText(this By identifier, string value)
{
    StackTrace stackTrace = new StackTrace();
    string methodName = stackTrace.GetFrame(1).GetMethod().Name;
    string className = stackTrace.GetFrame(1).GetMethod().DeclaringType.FullName;


    //I do some logging here for the manual testers so they can debug after a run
    TestDriver.ResultsLog.LogComment("Class: " + className);
    TestDriver.ResultsLog.LogComment("Calling Method: " + methodName);
    TestDriver.ResultsLog.LogComment("Calling Element: " + identifier.toString());

    IWebElement element = WebDriver.driver.FindElementSafe(identifier);
    ((IJavaScriptExecutor)WebDriver.driver).ExecuteScript("arguments[0].value = arguments[1]", element, value);
}

For reference, here is the Admin class:

public class Admin_Login
{
    public static By Username = By.Id("ctl00_MainContent_ctlLoginView_ctlLogin_UserName");
}

So I can log the class name and method name fine, but what I need to find out is the declared name of the "identifier" variable thats passed into the method.

So the value should be "Username" in this instance.

I've tried a couple of suggestions that yield the name of Identifier as "identifier" but that's really not what I want. I need to know which object the SetText method was called off, if that makes sense.

As I said maybe i'm not going about this the right way so any suggestions would be helpful.

Upvotes: 1

Views: 734

Answers (1)

Aydin
Aydin

Reputation: 15294

I can not believe I'm actually suggesting this because of how dirty this solution is... but, it is a solution... sooooo...

class Program
{
    static void Main()
    {
        var foo = new Foo();
        var bar = foo;

        foo.Hit();
        bar.Hit();
    }
}

public static class Extensions
{
    public static void Hit(this Foo foo, [CallerMemberName] string name = null, [CallerFilePath] string path = null, [CallerLineNumber] int lineNumber = -1)
    {
        string callerVariableName;

        using (FileStream stream = new FileStream(path, FileMode.Open, FileAccess.Read))
        {
            StreamReader reader = new StreamReader(stream);
            string csharpFile = reader.ReadToEnd();
            string[] lines = csharpFile.Split('\n');
            string callingLine = lines[lineNumber - 1];

            Match matchVariableName = Regex.Match(callingLine, @"([a-zA-Z]+[^\.]*)\.Hit\(\)");

            callerVariableName = matchVariableName.Groups[1].Value;
        }

        Console.WriteLine("\n///////////////////////////////");
        Console.WriteLine("Caller method name:   {0}", name);
        Console.WriteLine("Caller variable name: {0}", callerVariableName);
        Console.WriteLine("File Path:            {0}", path);
        Console.WriteLine("Line number:          {0}", lineNumber);

    }
}

public class Foo
{
}

Upvotes: 1

Related Questions