gpt4 book ai didi

c# - 模拟 AsNoTracking Entity Framework

转载 作者:IT王子 更新时间:2023-10-29 04:52:06 28 4
gpt4 key购买 nike

如何模拟 AsNoTracking 方法?
在下面的示例中,DbContext 已注入(inject)服务类。如果我从 GetOrderedProducts 方法中删除 AsNoTracking 扩展方法,它工作正常,但 AsNoTracking 测试失败,因为它返回 null。我也尝试模拟 AsNoTracking 以返回正确的值,但它没有用。

public interface IUnitOfWork
{
IDbSet<TEntity> Set<TEntity>() where TEntity : class;
int SaveAllChanges();
}

public class Entites : DbContext, IUnitOfWork
{
public virtual DbSet<Product> Products { get; set; } // This is virtual because Moq needs to override the behaviour

public new virtual IDbSet<TEntity> Set<TEntity>() where TEntity : class // This is virtual because Moq needs to override the behaviour
{
return base.Set<TEntity>();
}

public int SaveAllChanges()
{
return base.SaveChanges();
}
}

public class ProductService
{
private readonly IDbSet<Product> _products;
private readonly IUnitOfWork _uow;

public ProductService(IUnitOfWork uow)
{
_uow = uow;
_products = _uow.Set<Product>();
}
public IEnumerable<Product> GetOrderedProducts()
{
return _products.AsNoTracking().OrderBy(x => x.Name).ToList();
}
}

[TestFixture]
public class ProductServiceTest
{
private readonly ProductService _productService;

public ProductServiceTest()
{
IQueryable<Product> data = GetRoadNetworks().AsQueryable();
var mockSet = new Mock<DbSet<Product>>();
mockSet.As<IQueryable<Product>>().Setup(m => m.Provider).Returns(data.Provider);
mockSet.As<IQueryable<Product>>().Setup(m => m.Expression).Returns(data.Expression);
mockSet.As<IQueryable<Product>>().Setup(m => m.ElementType).Returns(data.ElementType);
mockSet.As<IQueryable<Product>>().Setup(m => m.GetEnumerator()).Returns(data.GetEnumerator());
var context = new Mock<Entites>();
context.Setup(c => c.Products).Returns(mockSet.Object);
context.Setup(m => m.Set<Product>()).Returns(mockSet.Object);
context.Setup(c => c.Products.AsNoTracking()).Returns(mockSet.Object);
_productService = new ProductService(context.Object);
}

private IEnumerable<Product> GetRoadNetworks()
{
return new List<Product>
{
new Product
{
Id = 1,
Name = "A"
},
new Product
{
Id = 2,
Name = "B"
},
new Product
{
Id = 1,
Name = "C"
}
};
}

[Test]
public void GetOrderedProductTest()
{
IEnumerable<Product> products = _productService.GetOrderedProducts();
List<string> names = products.Select(x => x.Name).ToList();
var expected = new List<string> {"A", "B", "C"};
CollectionAssert.AreEqual(names, expected);
}
}

问题是 AsNoTracking 在单元测试中返回 null enter image description here

最佳答案

查看 source codeAsNoTracking()扩展方法:

public static IQueryable AsNoTracking(this IQueryable source)
{
var asDbQuery = source as DbQuery;
return asDbQuery != null ? asDbQuery.AsNoTracking() : CommonAsNoTracking(source);
}

source (你的 DbSet<Product> 你想 mock )确实是一个 DbQuery (因为 DbSet 派生自 DbQuery ),它尝试调用“真实”(非模拟) AsNoTracking()正确返回 null 的方法。

尝试模拟 AsNoTracking()方法也是:

mockSet.Setup(x => x.AsNoTracking()).Returns(mockSet.Object);

关于c# - 模拟 AsNoTracking Entity Framework ,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/27038253/

28 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com