Testfx: Not able to get datarow value in TestContext

Created on 27 Oct 2017  路  13Comments  路  Source: microsoft/testfx

Description

Describe the issue you've observed
I am trying to get the datarow values from TestContext.DataRow[0] but DataRow is always coming as NULL.

Steps to reproduce

What steps can reproduce the defect?
Please share the setup, sample project, target platform (desktop, core, up)
[TestClass]
public class TestFrameworkTest
{

    static TestContext TestContext;

    [ClassInitialize]
    public static void OneTimeSetUp(TestContext testContext) {
        TestContext = testContext;
    }


    [DataTestMethod]
    [DataRow(1, 2, 3)]
    [DataRow(2, 2, 4)]
    [DataRow(3, 2, 5)]
    [DataRow(5, 2, 7)]
    public void RowTest(int a, int b, int result)
    {
        if (TestContext.DataRow[0] != null){ }


        Assert.AreEqual(result, a + b);
    }
}

Expected behavior

Share the expected output
TestContext.DataRow is not null

Actual behavior

What is the behavior observed?
TestContext.DataRow is Always null

Environment

Please share additional details about the test environment.
Operating system, Build version of vstest.console, Package version of MSTest
framework and adapter

question

All 13 comments

@ylnkancheti : What you are observing is expected. I believe there is some confusion in TestContext.DataRow object and [DataRow] attribute.

TestContext.DataRow is used to consume test data when data is provided using [DataSource] attribute. However, when you provide inline data by using [DataRow] attribute, then you should use the TestMethod parameters to access test data(i.e. variables a, b, result in your case).

Adapter will not populate TestContext.DataRow object in case of [DataRow] attribute and the data should only be consumed from TestMethod parameters only.

@jayaranigarg Got it. Thanks

@ylnkancheti : What you are observing is expected....
...Adapter will not populate TestContext.DataRow object in case of [DataRow] attribute and the data should only be consumed from TestMethod parameters only.

@jayaranigarg isn't that extremely unintuitive though? Wouldn't it make sense to always populate the DataRow property whenever data is available, no matter from where?

I think this might be an outdated discussion since I can't even find the DataRow property on TestContext anymore (let me know if I'm missing something there), but it doesn't hurt to ask.

@jayaranigarg, this should not be expected behavior. In my case, the test setup is dependent on the parameter values and there is absolutely no way to access them if they are not available in TestContext.

PS: I'm using MSTest v1.4.0.

@zendu : In case of testmethods having datarow, testmethods has to take method parameters and you should use those method parameters to access datarow values and should not depend on testcontext.

Test method uses parameters but what about test setup method?

@zendu : Can you please explain your scenario(maybe a code snippet explaining your expectation)? Which values is your test setup method dependent on? DataRow values are specific to your test methods and not make much sense in case of test setup/clean up as such.
Also, please create a new issue explaining your scenario. This issue is already closed and we will not be actively monitoring it.

I have several entities saved as JSON files. Test case is executed for each entity. Test setup needs to initialize another object using the entity.

[TestSetup]
public void Setup(){
    var entityFileName = this.TestContext.DataRow["fileName"];
    var entity = JsonDeserialize($"TestData\{entityFileName}");
    ...
}

@zendu : Can you please share a repro project with us?

How does your test method look like? How are you passing DataRow values to the testMethod? It would help if you can share snippet for that as well.

@zendu Afaik mstest does not have a [TestSetup] attribute. May i know what test framework you are using?

@ylnkancheti

    static TestContext TestContext;

    [ClassInitialize]
    public static void OneTimeSetUp(TestContext testContext) {
        TestContext = testContext;
    }


    [DataTestMethod]
    [DataRow(1, 2, 3)]
    [DataRow(2, 2, 4)]
    [DataRow(3, 2, 5)]
    [DataRow(5, 2, 7)]
    public void RowTest(int a, int b, int result)
    {
        Assert.AreEqual(result, a + b);
    }
}

This would be your code snippet to achieve the same thing. Since an int can't be null. The adapter would throw much earlier if you passed a data row similar to

[DataRow(null, 2, 3)]

Let's say the first param was an object then

    static TestContext TestContext;

    [ClassInitialize]
    public static void OneTimeSetUp(TestContext testContext) {
        TestContext = testContext;
    }


    [DataTestMethod]
    [DataRow(null, 2, 3)]
    public void RowTest(obj a, int b, int result)
    {
        if (a != null){ }

        Assert.AreEqual(result, b);
    }
}

you can do the above. The TestContext.DataRow is reserved for something else entirely and not for basic Data driven tests such as the one you are authoring.

@zendu @ylnkancheti any updates here?

Closing due to no response. Please reopen a new issue if your problem still persists. Locking the conversation here as the issue has started branch out into more than one query.

Was this page helpful?
0 / 5 - 0 ratings