具有连接的通用存储库模式
generic repository pattern with joins
我已经开始使用 entity framework (6.x) 探索存储库模式,方法是阅读本文中我认为对主题的最佳基本处理:http://www.codeguru.com/csharp/.net/net_asp/mvc/using-the-repository-pattern-with-asp.net-mvc-and-entity-framework.htm
不幸的是,它没有解决联接问题。使用通用存储库,如何加入任意数量的其他存储库 entities/repositories?
截至目前,我有这个通用接口:
interface IGenericRepository<T> where T: class
{
IEnumerable<T> SelectAll();
T SelectByID(object id);
void Insert(T obj);
void Update(T obj);
void Delete(object id);
void Save();
}
public class GenericRepository<T> : IGenericRepository<T> where T : class
{
private SocialMediaEntities db = null;
private DbSet<T> table = null;
public GenericRepository()
{
this.db = new SocialMediaEntities();
table = db.Set<T>();
}
public GenericRepository(SocialMediaEntities db)
{
this.db = db;
table = db.Set<T>();
}
public IEnumerable<T> SelectAll()
{
return table.ToList();
}
public T SelectByID(object id)
{
return table.Find(id);
}
public void Insert(T obj)
{
table.Add(obj);
}
public void Update(T obj)
{
table.Attach(obj);
db.Entry(obj).State = EntityState.Modified;
}
public void Delete(object id)
{
T existing = table.Find(id);
table.Remove(existing);
}
public void Save()
{
db.SaveChanges();
}
}
}
也许客户,客户订单的例子是很好的选择来说明。谢谢。
在问完我的问题后,我发现了另一个 SO 问题,其答案导致了
以下解决方案对我有用。问题是我混合了成语吗?这是
保持通用存储库模式的方法?
(问题是 Entityframework Join using join method and lambdas)
using (CommerceEntities ce = new CommerceEntities())
{
// the repository is Company
var results = repository.SelectAll()
.Join(ce.Orders, // target
p => p.OrderID, // FK
s => s.ID, // PK
(p, s) => new { Order = s, Company = p }) // project result
.Select(x => x.Company).ToList(); // select result
}
研究给出的第一个答案后,它似乎更符合通用存储库模式的精神。
您可以为 GetAll 方法创建多个重载。像这样:
//get all, including orderby clause, and includes
//usage: var s = repository.GetAll(i => i.Name, false, i => i.NavigationProperty);
public IEnumerable<T> GetAll<TOrderKey>(Expression<Func<T, TOrderKey>> orderbyExp,
Boolean descending,
params Expression<Func<T, Object>>[] includeExps)
{
var query = table.AsQueryable();
query = !descending ? query.OrderBy(orderByExp) : query.OrderByDescending(orderByExp);
if (includeExps != null)
query = includeExps.Aggregate(query, (current, exp) => current.Include(exp));
return query.ToList();
}
//get all, including select clause, orderby clause, and includes
//usage: var s = repository.GetAll(i => new { Name = i.Name }, i => i.Name, false, i => i.NavigationProperty
public IEnumerable<TReturn> GetAll<TReturn, TOrderKey>(Expression<Func<T, TReturn>> selectExp,
Expression<Func<T, TOrderKey>> orderExp,
Boolean descending,
params Expression<Func<T, Object>>[] includeExps)
{
var query = table.AsQueryable();
query = !descending ? query.OrderBy(orderByExp) : query.OrderByDescending(orderByExp);
if (includeExps != null)
query = includeExps.Aggregate(query, (current, exp) => current.Include(exp));
return query.Select(selectExp).ToList();
}
//get all, including select clause, where clause, order by clause, and includes
//usage: var s = repository.GetAll(i => new { i.Name }, i => i.Name.Contains('John'), i => i.Name, false, i => i.NavigationProperty
public IEnumerable<TReturn> GetAll<TReturn, TOrderKey>(Expression<Func<T, TReturn>> selectExp,
Expression<Func<T, Boolean>> whereExp,
Expression<Func<T, TOrderKey>> orderbyExp,
Boolean descending,
params Expression<Func<T, object>>[] includeExps)
{
var query = table.Where(whereExp);
query = !descending ? query.OrderBy(orderbyExp) : query.OrderByDescending(orderbyExp);
if (includeExps != null)
query = includeExps.Aggregate(query, (current, exp) => current.Include(exp));
return query.Select(selectExp).ToList();
}
以上方法只是一个例子。您应该根据需要重新创建它们。
我已经开始使用 entity framework (6.x) 探索存储库模式,方法是阅读本文中我认为对主题的最佳基本处理:http://www.codeguru.com/csharp/.net/net_asp/mvc/using-the-repository-pattern-with-asp.net-mvc-and-entity-framework.htm
不幸的是,它没有解决联接问题。使用通用存储库,如何加入任意数量的其他存储库 entities/repositories?
截至目前,我有这个通用接口:
interface IGenericRepository<T> where T: class
{
IEnumerable<T> SelectAll();
T SelectByID(object id);
void Insert(T obj);
void Update(T obj);
void Delete(object id);
void Save();
}
public class GenericRepository<T> : IGenericRepository<T> where T : class
{
private SocialMediaEntities db = null;
private DbSet<T> table = null;
public GenericRepository()
{
this.db = new SocialMediaEntities();
table = db.Set<T>();
}
public GenericRepository(SocialMediaEntities db)
{
this.db = db;
table = db.Set<T>();
}
public IEnumerable<T> SelectAll()
{
return table.ToList();
}
public T SelectByID(object id)
{
return table.Find(id);
}
public void Insert(T obj)
{
table.Add(obj);
}
public void Update(T obj)
{
table.Attach(obj);
db.Entry(obj).State = EntityState.Modified;
}
public void Delete(object id)
{
T existing = table.Find(id);
table.Remove(existing);
}
public void Save()
{
db.SaveChanges();
}
}
}
也许客户,客户订单的例子是很好的选择来说明。谢谢。
在问完我的问题后,我发现了另一个 SO 问题,其答案导致了 以下解决方案对我有用。问题是我混合了成语吗?这是 保持通用存储库模式的方法?
(问题是 Entityframework Join using join method and lambdas)
using (CommerceEntities ce = new CommerceEntities())
{
// the repository is Company
var results = repository.SelectAll()
.Join(ce.Orders, // target
p => p.OrderID, // FK
s => s.ID, // PK
(p, s) => new { Order = s, Company = p }) // project result
.Select(x => x.Company).ToList(); // select result
}
研究给出的第一个答案后,它似乎更符合通用存储库模式的精神。
您可以为 GetAll 方法创建多个重载。像这样:
//get all, including orderby clause, and includes
//usage: var s = repository.GetAll(i => i.Name, false, i => i.NavigationProperty);
public IEnumerable<T> GetAll<TOrderKey>(Expression<Func<T, TOrderKey>> orderbyExp,
Boolean descending,
params Expression<Func<T, Object>>[] includeExps)
{
var query = table.AsQueryable();
query = !descending ? query.OrderBy(orderByExp) : query.OrderByDescending(orderByExp);
if (includeExps != null)
query = includeExps.Aggregate(query, (current, exp) => current.Include(exp));
return query.ToList();
}
//get all, including select clause, orderby clause, and includes
//usage: var s = repository.GetAll(i => new { Name = i.Name }, i => i.Name, false, i => i.NavigationProperty
public IEnumerable<TReturn> GetAll<TReturn, TOrderKey>(Expression<Func<T, TReturn>> selectExp,
Expression<Func<T, TOrderKey>> orderExp,
Boolean descending,
params Expression<Func<T, Object>>[] includeExps)
{
var query = table.AsQueryable();
query = !descending ? query.OrderBy(orderByExp) : query.OrderByDescending(orderByExp);
if (includeExps != null)
query = includeExps.Aggregate(query, (current, exp) => current.Include(exp));
return query.Select(selectExp).ToList();
}
//get all, including select clause, where clause, order by clause, and includes
//usage: var s = repository.GetAll(i => new { i.Name }, i => i.Name.Contains('John'), i => i.Name, false, i => i.NavigationProperty
public IEnumerable<TReturn> GetAll<TReturn, TOrderKey>(Expression<Func<T, TReturn>> selectExp,
Expression<Func<T, Boolean>> whereExp,
Expression<Func<T, TOrderKey>> orderbyExp,
Boolean descending,
params Expression<Func<T, object>>[] includeExps)
{
var query = table.Where(whereExp);
query = !descending ? query.OrderBy(orderbyExp) : query.OrderByDescending(orderbyExp);
if (includeExps != null)
query = includeExps.Aggregate(query, (current, exp) => current.Include(exp));
return query.Select(selectExp).ToList();
}
以上方法只是一个例子。您应该根据需要重新创建它们。