加入收藏 | 设为首页 | 会员中心 | 我要投稿 李大同 (https://www.lidatong.com.cn/)- 科技、建站、经验、云计算、5G、大数据,站长网!
当前位置: 首页 > 百科 > 正文

c# – 如何Moq实体框架SqlQuery调用

发布时间:2020-12-15 03:45:24 所属栏目:百科 来源:网络整理
导读:我已经能够使用这个 link从Moq的实体框架中模拟DbSet. 但是,我现在想知道如何可以模拟对SqlQuery的调用.不知道这是可能的,还是如何依赖于嘲弄的数据库环境,知道正在调用什么“查询”. 下面是我试图嘲笑的. var myObjects = DbContext.Database .SqlQueryMyOb
我已经能够使用这个 link从Moq的实体框架中模拟DbSet.

但是,我现在想知道如何可以模拟对SqlQuery的调用.不知道这是可能的,还是如何依赖于嘲弄的数据库环境,知道正在调用什么“查询”.

下面是我试图嘲笑的.

var myObjects = DbContext.Database
    .SqlQuery<MyObject>("exec [dbo].[my_sproc] {0}","some_value")
    .ToList();

我目前没有尝试任何东西,因为不知道如何开始嘲笑这个例子.

DbSet的嘲笑在下面并重新迭代,我可以正确地模拟返回MyObject的DbSet,但现在我试图模拟一个返回MyObject列表的SqlQuery.

var dbContext = new Mock<MyDbContext>();
dbContext.Setup(m => m.MyObjects).Returns(mockObjects.Object);

dbContext.Setup(m => m.Database.SqlQuery... something along these lines

解决方法

Database.SqlQuery<T>未标记为虚拟,但 Set<T>.SqlQuery被标记为虚拟.

基于Database.SqlQuery<T>文档

The results of this query are never tracked by the context even if the
type of object returned is an entity type. Use the 07003 method to return entities that are tracked by the
context.

Set<T>.SqlQuery文档

By default,the entities returned are tracked by the context; this can
be changed by calling AsNoTracking on the DbRawSqlQuery returned.

那么Database.SqlQuery< T>(String,Object [])应该与Set< T> .SqlQuery(String,Object [])等同.AsNoTracking()(只有当T是EF实体,而不是DTO / VM) .

所以如果你可以将实现替换成:

var myObjects = DbContext
    .Set<MyObject>()
    .SqlQuery("exec [dbo].[my_sproc] {0}","some_value")
    .AsNoTracking()
    .ToList();

你可以嘲笑它如下

var list = new[] 
{ 
    new MyObject { Property = "some_value" },new MyObject { Property = "some_value" },new MyObject { Property = "another_value" }
};

var setMock = new Mock<DbSet<MyObject>>();
setMock.Setup(m => m.SqlQuery(It.IsAny<string>(),It.IsAny<object[]>()))
    .Returns<string,object[]>((sql,param) => 
    {
        // Filters by property.
        var filteredList = param.Length == 1 
            ? list.Where(x => x.Property == param[0] as string) 
            : list;
        var sqlQueryMock = new Mock<DbSqlQuery<MyObject>>();
        sqlQueryMock.Setup(m => m.AsNoTracking())
            .Returns(sqlQueryMock.Object);
        sqlQueryMock.Setup(m => m.GetEnumerator())
            .Returns(filteredList.GetEnumerator());
        return sqlQueryMock.Object;
    });

var contextMock = new Mock<MyDbContext>();
contextMock.Setup(m => m.Set<MyObject>()).Returns(setMock.Object);

(编辑:李大同)

【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容!

    推荐文章
      热点阅读