我发现在我的 UnitOfWork 中,我为每种类型的实体都有一个存储库,并且没有使用聚合根,所以我正在尝试解决这个问题。解决计算机库存的想法,我目前的 UnitOfWork 结构如下:
public class UnitOfWork : IUnitOfWork
{
private readonly ReportingDbContext _dbContext = null;
public UnitOfWork()
{
_dbContext = new ReportingDbContext();
}
public void Commit()
{
_dbContext.SaveChanges();
}
// Inventory
public IRepository<ComputerEntity> Computers {get { return new Repository<ComputerEntity>(_dbContext); }}
public IRepository<NetworkAdapterEntity> NetworkAdapters { get { return new Repository<NetworkAdapterEntity>(_dbContext); } }
// plus a bunch more
}
我只希望我的聚合根出现在那里,这应该很容易做到。我认为问题在于我正在使用单个存储库类并在我新建它时输入类型。我相信答案是拥有多个存储库,每个存储库对应一个聚合根。我为每种类型使用的这个通用存储库的优点在于它可以处理我的所有实体框架内容,例如按 ID 查找、保存到 DbSet 等。我的通用存储库是这样设置的:
public class Repository<T> : IRepository<T> where T : class
{
protected DbContext DbContext { get; set; }
protected DbSet<T> DbSet { get; set; }
public Repository(DbContext dbContext)
{
if (dbContext == null)
{
throw new ArgumentNullException("dbContext");
}
DbContext = dbContext;
DbSet = DbContext.Set<T>();
}
public IQueryable<T> GetAll()
{
return DbSet;
}
public IQueryable<T> Find(System.Linq.Expressions.Expression<Func<T, bool>> predicate)
{
return DbSet.Where(predicate);
}
// the rest of the implementation omitted for brevity
}
此存储库使用我所有尚未创建的聚合根存储库应使用的接口:
public interface IRepository<T> where T : class
{
IQueryable<T> GetAll();
IQueryable<T> Find(Expression<Func<T, bool>> predicate);
T GetById(int id);
void Remove(T entity);
void Add(T newEntity);
}
现在这是问题的真正实质。我在具体的 Repository 类中很好地实现了上述接口,并且我希望在我将制作的所有聚合根存储库中具有相同的功能。我不想直接使用这个通用存储库,因为我只想使用它作为基础来获取它对实体框架所做的基本 CRUD 内容。我不想重复已经实现的通用存储库的东西,只是继承它。更重要的是,我想第一次正确地设计这个。
像这样创建基于聚合根的存储库是否合适:
public interface IComputerRepository
{
string ComputerSpecificMethod(string param);
}
public class ComputerRepository : Repository<ComputerEntity>, IComputerRepository
{
public ComputerRepository(DbContext dbContext) : base(dbContext)
{
//
}
public string ComputerSpecificMethod(string param)
{
// do stuff
return "test";
}
}
然后在我的 UnitOfWork 中使用这个新奇特的存储库(以及其他类似的存储库):
public IRepository<ComputerEntity> Computers {get { return new ComputerRepository(_dbContext); }}
代替:
public IRepository<ComputerEntity> Computers {get { return new Repository<ComputerEntity>(_dbContext); }}
目标是坚持 UnitOfWork/Repository 模式,我不确定这是否是正确的做法。