首页 > 解决方案 > moq.As<>().Setup() 在获取 moq.Object 后似乎不起作用

问题描述

我从 Microsoft 关于使用 moq 测试 EF 的文章中得出了一个小测试:Testing with a mocking framework

namespace TestingDemo
{
    public class BloggingContext : DbContext
    {
        public virtual DbSet<Blog> Blogs { get; set; }
    }

    public class Blog
    {
        public string Name { get; set; }
    }

    [TestClass]
    public class QueryTests
    {
        [TestMethod]
        public void Test()
        {
            var data = new List<Blog> { new Blog { Name = "AAA" } }.AsQueryable();
            var mockSet = new Mock<DbSet<Blog>>();
            //var a = mockSet.Object;
            mockSet.As<IQueryable<Blog>>().Setup(m => m.Provider).Returns(data.Provider);
            mockSet.As<IQueryable<Blog>>().Setup(m => m.Expression).Returns(data.Expression);
            mockSet.As<IQueryable<Blog>>().Setup(m => m.ElementType).Returns(data.ElementType);
            mockSet.As<IQueryable<Blog>>().Setup(m => m.GetEnumerator()).Returns(data.GetEnumerator());
            var b = mockSet.Object.ToList();
        }
    }
}

在我取消注释该行之前它工作正常var a = mockSet.Object; 在此之后我最终在该行上出现异常var b = mockSet.Object.ToList();

System.NotImplementedException: '成员'IEnumerable.GetEnumerator'尚未在继承自'DbSet`1'的类型'DbSet`1Proxy'上实现。'DbSet`1' 的测试替身必须提供所使用的方法和属性的实现。

我错过了什么吗?

UPD:使用最小起订量 4.10.1、EF 6.2.0、VS 社区 2019 16.6.1、.NET 4.7.2

标签: c#entity-frameworklinqmoq

解决方案


问题是您在IQueryable<T>获得模拟对象 () 的实例后添加设置mockSet.Object;它不起作用,这也是为什么一旦您将作业注释到a. 为要使用的行为添加设置后,您应该只检索模拟对象。

有趣的是,一旦您添加了这些设置,您就可以随时更改它们(使用另一个设置覆盖)。您只需在检索模拟对象之前进行初始注册。我一直用我的系统模拟库来做这件事。


推荐阅读