Repository یک design pattern می باشد که بعنوان یک واسط جهت کار با داده ها ودرون لایه Data Access Layer .که باعث میشوند منطق مورد نیاز برای ذخیره یا یازیابی داده ها پنهان شوند.بتابراین برنامه ما از orm استفاده شده هیچگونه اطلاعاتی ندارد چرا که این موارد در لایه Repository انجام میگیرد.
یکی از مزایای مهم استفاده از Repository Pattern می تواند شامل کاهش در حجم کدنویسی باشد . چرا که ممکن است فرامین اسکیوال مشابهی در بخشهای مختلف برنامه اجرا گردد لذا با استفاده از الگوی Repository Pattern این مشکل حل خواهد شد.
در این آموزش پیاده سازی Repository Pattern بصورت Generic Class خواهیم پرداخت. لذا برای شروع یک اینترفیس بنام IRepository بصورت زیر ایجاد میکنیم.
public interface IRepository<T> where T:class
{
T Get(int id);
IEnumerable<T> GetAll(
Expression<Func<T,bool>> filter=null,
Func<IQueryable<T>,IOrderedQueryable<T>> orderby=null,
string includeProperties=null
);
T GetFirstOrDefault(
Expression<Func<T, bool>> filter = null,
string includeProperties = null
);
void Add(T entity);
void Remove(int id);
void Remove(T entity);
}
سپس کلاس دیگری بنام Repository جهت پیاده سازی اینترفیس فوق بصورت زیر ایجاد میکنیم
public class Repository<T> : IRepository<T> where T : class
{
protected readonly DbContext Context;
private DbSet<T> dbSet;
public Repository(DbContext context)
{
Context = context;
this.dbSet = Context.Set<T>();
}
public void Add(T entity)
{
dbSet.Add(entity);
}
public T Get(int id)
{
return dbSet.Find(id);
}
public IEnumerable<T> GetAll(Expression<Func<T, bool>> filter = null, Func<IQueryable<T>, IOrderedQueryable<T>> orderby = null, string includeProperties = null)
{
IQueryable<T> query = dbSet;
if (filter != null)
{
query = query.Where(filter);
}
//will br camma seperated
if (includeProperties != null)
{
foreach (var includeProperty in includeProperties.Split(new char[] { ',' }, StringSplitOptions.RemoveEmptyEntries))
{
query = query.Include(includeProperty);
}
}
if (orderby != null)
{
return orderby(query).ToList();
}
return query.ToList();
}
public T GetFirstOrDefault(Expression<Func<T, bool>> filter = null, string includeProperties = null)
{
IQueryable<T> query = dbSet;
if (filter != null)
{
query = query.Where(filter);
}
//will br camma seperated
if (includeProperties != null)
{
foreach (var includeProperty in includeProperties.Split(new char[] { ',' }, StringSplitOptions.RemoveEmptyEntries))
{
query = query.Include(includeProperty);
}
}
return query.FirstOrDefault();
}
public void Remove(int id)
{
T entityToRemove = dbSet.Find(id);
Remove(entityToRemove);
}
public void Remove(T entity)
{
dbSet.Remove(entity);
}
}
در کلاس فوق ازتابع Set شیئ Context جهت نمونه سازی شیئ dbSet استفاده کردیم.
در آموزشهای بعدی به مبحث UnitOfWork و پیاده سازی عملی جهت استفاده در برنامه ها خواهیم پرداخت