使用ImmutableList时DynamicData未按预期工作的问题排查
测试DynamicData传入ImmutableList计数为0的问题分析
测试代码
public static IEnumerable<object[]> TestData { get { yield return new object[] { "hello", ImmutableList<string>.Empty.AddRange( new List<string>() { "one", "two" } ) }; } } [TestMethod] [DynamicData(nameof(TestData))] public void Sandbox(string myString, ImmutableList<string> myList) { var sameListInstantiatedHere = ImmutableList<string>.Empty.AddRange( new List<string>() { "one", "two" } ); sameListInstantiatedHere.Count.Should().Be(2); myString.Should().Be("hello"); myList.Count.Should().Be(2); }
测试错误信息
Expected myList.Count to be 2, but found 0 (difference of -2).
问题
方法内实例化的sameListInstantiatedHere计数为2且测试通过,但通过DynamicData传入的myList计数为0,这是为什么?哪里操作错了?
原因与解决方案
这个问题的核心原因是MSTest的DynamicData机制在序列化/反序列化ImmutableList这类不可变集合时存在兼容性问题,导致传递到测试方法中的实例丢失了元素,变成空集合。
你可以通过以下几种方式解决:
- 改用ImmutableList的直接创建方法,避免通过
AddRange结合List<T>的方式生成实例:
public static IEnumerable<object[]> TestData { get { yield return new object[] { "hello", ImmutableList.Create("one", "two") }; } }
- 在测试方法内转换集合类型:TestData中传递普通
List<string>,测试方法内再转换为ImmutableList:
public static IEnumerable<object[]> TestData { get { yield return new object[] { "hello", new List<string> { "one", "two" } }; } } [TestMethod] [DynamicData(nameof(TestData))] public void Sandbox(string myString, List<string> myList) { var immutableList = myList.ToImmutableList(); immutableList.Count.Should().Be(2); myString.Should().Be("hello"); }
- 使用工厂方法延迟创建实例:避免直接传递
ImmutableList实例,而是传递创建实例的委托,在测试方法中执行生成:
public static IEnumerable<object[]> TestData { get { yield return new object[] { "hello", new Func<ImmutableList<string>>(() => ImmutableList<string>.Empty.AddRange(new List<string> { "one", "two" })) }; } } [TestMethod] [DynamicData(nameof(TestData))] public void Sandbox(string myString, Func<ImmutableList<string>> listFactory) { var myList = listFactory(); myList.Count.Should().Be(2); myString.Should().Be("hello"); }
内容的提问来源于stack exchange,提问作者me.at.coding
相关产品推荐
相关产品推荐

