gpt4 book ai didi

c# - 使用最小起订量通用存储库和 UnitOfWork 进行单元测试

转载 作者:行者123 更新时间:2023-11-30 16:43:56 25 4
gpt4 key购买 nike

我有一个像这样的特定和通用存储库:

通用存储库:

public class Repository<TEntity> : IRepository<TEntity> where TEntity : class
{
protected readonly DbContext Context;
private DbSet<TEntity> _entities;

public Repository(DbContext context)
{
Context = context;
_entities = Context.Set<TEntity>();
}

public IEnumerable<TEntity> Find(Expression<Func<TEntity, bool>> predicate)
{
return _entities.Where(predicate);
}
}

特定存储库:

public class HolidayCalendarRepository : Repository<HolidayCalendar>, IHolidayCalendarRepository
{
public HolidayCalendarRepository(ApplicationDbContext context)
: base(context)
{
}

public ApplicationDbContext ApplicationDbContext
{
get { return Context as ApplicationDbContext; }
}

public bool IsHoliday(DateTime date)
{
return Find(h => h.Date == date.Date).Any();
}
}

IRepository

public interface IRepository<TEntity> where TEntity : class
{
IEnumerable<TEntity> Find(Expression<Func<TEntity, bool>> predicate);
}

IHolidayCalendarRepository

public interface IHolidayCalendarRepository : IRepository<HolidayCalendar>
{
bool IsHoliday(DateTime date);
}

工作单元

public class UnitOfWork : IUnitOfWork
{
private readonly ApplicationDbContext _context;

public UnitOfWork(ApplicationDbContext context)
{
_context = context;
HolidayCalendars = new HolidayCalendarRepository(_context);
}

public IHolidayCalendarRepository HolidayCalendars { get; private set; }

public int Complete()
{
return _context.SaveChanges();
}

public void Dispose()
{
_context.Dispose();
}
}

如何在我的存储库上测试方法 IsHoliday(DateTime date)。我是单元测试的初学者。这是我尝试的方法,但它不起作用。

[TestFixture]
public class HolidayCalendarRepositoryTests
{
private HolidayCalendarRepository _holidayCalendarRepository;
private Mock<DbSet<HolidayCalendar>> _mockHolidayCalendar;

[SetUp]
public void TestInitialize()
{
var mockContext = new Mock<ApplicationDbContext>();
_mockHolidayCalendar = new Mock<DbSet<HolidayCalendar>>();


mockContext.Setup(hc => hc.HolidayCalendar).Returns(_mockHolidayCalendar.Object);
_holidayCalendarRepository = new HolidayCalendarRepository(mockContext.Object);

}

[Test]
public void IsHoliday_CurrentDateIsHoliday_ShouldBeTrue()
{
var holidays = new List<HolidayCalendar>() { new HolidayCalendar { ID = 1, Date = DateTime.Today } };

_mockHolidayCalendar.SetSource(holidays);

var result = _holidayCalendarRepository.IsHoliday(DateTime.Today);

Assert.IsTrue(result);
}
}

SetSource 方法

    public static void SetSource<T>(this Mock<DbSet<T>> mockSet, IList<T> source) where T : class
{
var data = source.AsQueryable();

mockSet.As<IQueryable<T>>().Setup(m => m.Provider).Returns(data.Provider);
mockSet.As<IQueryable<T>>().Setup(m => m.Expression).Returns(data.Expression);
mockSet.As<IQueryable<T>>().Setup(m => m.ElementType).Returns(data.ElementType);
mockSet.As<IQueryable<T>>().Setup(m => m.GetEnumerator()).Returns(data.GetEnumerator());
}

最佳答案

根据过去的经验,上下文的设置似乎没有正确完成。

Repository正在通过 .Set<TEntity>() 访问 DbSets方法...

通用存储库:

//...ctor
public Repository(DbContext context) {
Context = context;
_entities = Context.Set<TEntity>(); //<-- Note method used to access DbSet
}
//...

但是模拟是通过暴露的属性设置的 HolidayCalendar而不是 .Set<TEntity>()

HolidayCalendarRepositoryTests

mockContext
.Setup(hc => hc.HolidayCalendar) //<-- Note the setup
.Returns(_mockHolidayCalendar.Object);

这需要根据所用代码的预期行为进行设置。

更新设置以包括...

//...
mockContext
.Setup(_ => _.Set<HolidayCalendar>())
.Returns(_mockHolidayCalendar.Object);
//...

...这将允许存储库实现在执行测试时按预期运行。

这里的假设是 _mockHolidayCalendar.SetSource(holidays)是某种扩展方法,它将可枚举/可查询的假数据源分配给模拟集合。

关于c# - 使用最小起订量通用存储库和 UnitOfWork 进行单元测试,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/44099573/

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