快速信息:我正在使用C#4.0和RhinoMocks(带有AAA)
我将通过一些代码解释我在考虑做什么:
public class SampleData
{
private List<Person> _persons = new List<Person>()
{
new Person { PersonID = 1, Name = "Jack"},
new Person { PersonID = 2, Name = "John"}
};
public List<Person> Persons
{
get { return _persons; }
}
}
因此,这是一个模拟数据库中数据的类。现在,我想在单元测试中使用这些数据。换句话说,我不是要从数据库中获取数据,而是要从数据存储库中获取数据。
我想可以通过对存储库进行存根并使其使用DataRepository来实现此目的:
UC1003_ConsultantsBeherenBL consultantsBeherenBL = new UC1003_ConsultantsBeherenBL();
consultantsBeherenBL = MockRepository.GeneratePartialMock<UC1003_ConsultantsBeherenBL>();
consultantsBeherenBL.Repository = MockRepository.GenerateMock<IRepository>();
这将导致我的代码改为自动在DataRepository中查找数据。因此,与其使用一个方法而不是直接插入一个列表(例如,d => d.Find(Arg.Is.Anything))。IgnoreArguments()。Return(您刚刚填写的列表),我会得到“真实”返回数据(已从DataRepository过滤的数据)。这意味着我可以测试我的代码是否真的可以找到某些东西,而不必在数据库中插入测试数据(集成测试)。
我将如何实施这样的事情?我尝试在网上查找文章或问题,但似乎找不到很多:/
任何帮助表示赞赏。
编辑:我尝试过SimpleInjector和StructureMap,但我坚持实现其中之一。
我当前在实体框架上使用存储库,所以我的baseBL看起来像这样(注意:我所有其他的BL继承自此)
public class BaseBL
{
private IRepository _repository;
public IRepository Repository
{
get
{
if (_repository == null)
_repository = new Repository(new DetacheringenEntities());
return _repository;
}
set { _repository = value; }
}
public IEnumerable<T> GetAll<T>()
{
... --> Generic methods
我的存储库类:
public class Repository : BaseRepository, IRepository
{
#region Base Implementation
private bool _disposed;
public Repository(DetacheringenEntities context)
{
this._context = context;
this._contextReused = true;
}
#endregion
#region IRepository Members
public int Add<T>(T entity)
... --> implementations of generic methods
据我所知,我现在需要能够在测试中说,我需要使用DataRepository而不是使用DetacheringenEntities。我不明白如何用数据类切换实体框架,因为该数据类不适合该类。
是否应该让DataRepository继承IRepository类并进行自己的实现?
public class SampleData : IRepository
但是我不能用列表做这样的事情:/
public IEnumerable<T> GetAll<T>()
{
return Repository.GetAll<T>();
}
再次非常感谢您的帮助
编辑:我意识到单元测试不需要数据存储库,所以我只是在集成测试中测试该逻辑。这使得数据存储库无用,因为无需存储库即可测试代码。
我要感谢大家的帮助,谢谢:)
最佳答案
使用Dependency injection framework处理依赖关系。在单元测试中,您可以将实际的实现与存根的实现交换。
例如,在StructureMap中,您将在代码中说。 “好吧,现在给我IDataRepository
的活动实例”,对于您的常规代码,这将指向实际数据库的实现。在单元测试中,您可以通过放置ObjectFactory.Inject(new FakeDataRepository())
覆盖它。然后,所有代码都使用伪造的回购协议,这使得测试单个工作单元非常容易。