【问题标题】:How to implement test data in JSON file in data-driven unit test in .NET using C#如何使用 C# 在 .NET 中的数据驱动单元测试中实现 JSON 文件中的测试数据
【发布时间】:2020-03-01 08:37:54
【问题描述】:

我正在为我的类库使用 xUnit 包进行单元测试。我想尝试使用 JSON 方法而不是普通的对象方法来进行数据驱动的单元测试。但是,我看不到任何地方能够实现这一目标。

我坚持的是数据驱动测试 MemberData 要求测试数据以IEnumerable<object[]> 类型存在,当我从 JSON 文件调用数据时,它在我的数据模型类中键入。我是否将它们添加到IEnumerable<object[]>?还是有别的办法?

这是我目前的代码:

这是包含 5 个测试数据的 json 文件:

{
  "user": [
    {
      "name": "John",
      "age": 12,
      "gender": "Male",
      "Hobby": "Reading"
    },
    {
      "name": "Susan",
      "age": 34,
      "gender": "Female",
      "Hobby": "Gardening"
    },
    {
      "name": "Larry",
      "age": 24,
      "gender": "Male",
      "Hobby": "Gaming"
    },
    {
      "name": "Jack",
      "age": 3,
      "gender": "Male",
      "Hobby": "Sleeping"
    },
    {
      "name": "Minnie",
      "age": 15,
      "gender": "Female",
      "Hobby": "Partying"
    }
  ]
}

这是测试类文件:

private User GetTestData()
{
     var filePath = Path.Combine(AppDomain.CurrentDomain.BaseDirectory, "TestData.json"); 
     var reader = new StreamReader(filePath);
     var jsonStr = reader.ReadToEnd();
     var jsonObj = JObject.Parse(jsonStr);

     var testDataObj = jsonObj["user"].ToString();
     var testData = JsonConvert.DeserializeObject<User>(testDataObj);

     return testData;
}

public static IEnumerable<object[]> ValidUserTestData()
{
     //What should I do here?   
}

[Theory]
[MemberData(nameof(ValidUserTestData))]
public void Test1()
{

}

这是实施此类测试的正确方法吗?或者还有其他更好的选择来在数据驱动测试中使用 JSON 文件吗?

谢谢。

【问题讨论】:

    标签: c# .net json unit-testing xunit


    【解决方案1】:

    MemberData 属性接受 IEnumerable&lt;object[]&gt; 的对象,这些对象将一一传递给您的测试方法。因此,您应该将您的 JSON 反序列化为对象数组(您的 json 示例包含一个 User 对象数组),然后从 ValidUserTestData 方法返回它。还要确保Test1() 接受正确的参数

    [Theory]
    [MemberData(nameof(ValidUserTestData))]
    public void Test1(User user)
    {
        //test logic against every User instance
    }
    

    ValidUserTestData 可以按照以下方式声明:首先读取 json,然后将其转换为 User 对象的枚举并将其作为 IEnumerable&lt;object[]&gt; 返回

    public static IEnumerable<object[]> ValidUserTestData()
    {
        var filePath = Path.Combine(AppDomain.CurrentDomain.BaseDirectory, "TestData.json");
        var json = File.ReadAllText(filePath);
        var jobject = JObject.Parse(json);
        var users = jobject["user"]?.ToObject<IEnumerable<User>>();
    
        foreach (var user in users ?? Enumerable.Empty<User>())
        {
            yield return new[] { user };
        }
    }
    

    IEnumerable&lt;object[]&gt; 中的每一项都代表一组参数,被测试方法接受。您的测试方法中只需要一个输入参数,因此每个object[] 都包含一个user 实例。

    有一篇很好的文章Creating parameterized tests in xUnit

    【讨论】:

      猜你喜欢
      • 2017-01-06
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2012-11-05
      • 1970-01-01
      • 2016-11-26
      相关资源
      最近更新 更多