moq测试LINQ哪里查询
我使用EF 4.1构建域模型.我有一个具有Validate(string userCode)方法的Task类,其中我想确保用户代码映射到数据库中的有效用户,因此:
public static bool Validate(string userCode) { IDbSet<User> users = db.Set<User>(); var results = from u in users where u.UserCode.Equals(userCode) select u; return results.FirstOrDefault() != null; } 我可以使用Moq来模拟IDbSet没问题.但是遇到麻烦的地方呼叫: User user = new User { UserCode = "abc" }; IList<User> list = new List<User> { user }; var users = new Mock<IDbSet<User>>(); users.Setup(x => x.Where(It.IsAny<Expression<Func<User,bool>>>())).Returns(list.AsQueryable); Initialization method JLTi.iRIS3.Tests.TaskTest.SetUp threw exception. System.NotSupportedException: System.NotSupportedException: Expression references a method that does not belong to the mocked object: x => x.Where<User>(It.IsAny<Expression`1>()). 除了创建一个间接级别(例如,使用ServiceLocator获取运行LINQ的对象,然后模拟该方法)我不能想到如何测试这个,但我想确保没有办法我介绍另一层.而且我可以看到这种LINQ查询需要很频繁,所以服务对象可以迅速地失控. 有可能有一点灵魂有帮助吗?谢谢!
据我所知,Moq只能设置虚拟对象本身的虚拟方法,但您正在尝试设置扩展(静态)方法 – 没有办法!这些方法绝对不在您的模拟范围之内.
此外,代码错误,难以测试.您需要进行大量初始化才能测试.改用: internal virtual IQueryable<User> GetUserSet() { return db.Set<User>(); } public bool Validate(string userCode) { IQueryable<User> users = GetUserSet(); var results = from u in users where u.UserCode.Equals(userCode) select u; return results.FirstOrDefault() != null; } 您只需要设置GetUserSet以返回您的列表.这样的测试有一些重大问题: >你没有测试真正的实现 – 如果EF嘲笑集是愚蠢的方法,因为一旦你这样做,你将linq-to-entity更改为linq-to-objects.这两个是完全不同的,linq到实体只是linq-to-objects的一小部分,你的单元测试可以通过linq-to-object传递,但你的代码在运行时会失败. 更好的方法是从Validate方法中删除您的LINQ查询 – 只需将它们称为对象的另一种虚拟方法即可.单元使用嘲弄的查询方法测试您的Validate方法,并使用集成测试来自行测试查询. (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |