创建通用存储库的异步版本
本文关键字:异步 版本 存储 创建 | 更新日期: 2023-09-27 18:17:09
我有一个实现以下接口的通用存储库:
public interface IRepository
{
IUnitOfWork UnitOfWork { get; }
IEnumerable<TEntity> GetWithRawSql<TEntity>(string query, params object[] parameters) where TEntity : class;
TEntity GetByKey<TEntity>(object keyValue) where TEntity : class;
IQueryable<TEntity> GetQuery<TEntity>() where TEntity : class;
IQueryable<TEntity> GetQuery<TEntity>(Expression<Func<TEntity, bool>> predicate) where TEntity : class;
IQueryable<TEntity> GetQuery<TEntity>(ISpecification<TEntity> criteria) where TEntity : class;
TEntity Single<TEntity>(Expression<Func<TEntity, bool>> criteria) where TEntity : class;
TEntity Single<TEntity>(ISpecification<TEntity> criteria) where TEntity : class;
TEntity First<TEntity>(Expression<Func<TEntity, bool>> predicate) where TEntity : class;
TEntity First<TEntity>(ISpecification<TEntity> criteria) where TEntity : class;
void Add<TEntity>(TEntity entity) where TEntity : class;
void Attach<TEntity>(TEntity entity) where TEntity : class;
void Delete<TEntity>(TEntity entity) where TEntity : class;
void Delete<TEntity>(Expression<Func<TEntity, bool>> criteria) where TEntity : class;
void Delete<TEntity>(ISpecification<TEntity> criteria) where TEntity : class;
void Update<TEntity>(TEntity entity) where TEntity : class;
IEnumerable<TEntity> Find<TEntity>(ISpecification<TEntity> criteria) where TEntity : class;
IEnumerable<TEntity> Find<TEntity>(Expression<Func<TEntity, bool>> criteria) where TEntity : class;
TEntity FindOne<TEntity>(ISpecification<TEntity> criteria) where TEntity : class;
TEntity FindOne<TEntity>(Expression<Func<TEntity, bool>> criteria) where TEntity : class;
IEnumerable<TEntity> GetAll<TEntity>() where TEntity : class;
IEnumerable<TEntity> Get<TEntity, TOrderBy>(Expression<Func<TEntity, TOrderBy>> orderBy, int pageIndex,
int pageSize, SortOrder sortOrder = SortOrder.Ascending) where TEntity : class;
IEnumerable<TEntity> Get<TEntity, TOrderBy>(Expression<Func<TEntity, bool>> criteria,
Expression<Func<TEntity, TOrderBy>> orderBy, int pageIndex, int pageSize,
SortOrder sortOrder = SortOrder.Ascending) where TEntity : class;
IEnumerable<TEntity> Get<TEntity, TOrderBy>(ISpecification<TEntity> specification,
Expression<Func<TEntity, TOrderBy>> orderBy, int pageIndex, int pageSize,
SortOrder sortOrder = SortOrder.Ascending) where TEntity : class;
int Count<TEntity>() where TEntity : class;
int Count<TEntity>(Expression<Func<TEntity, bool>> criteria) where TEntity : class;
int Count<TEntity>(ISpecification<TEntity> criteria) where TEntity : class;
}
这个接口属于一个通用存储库的修改版本,由huyrua的博客实现。我需要有一些方法的异步版本。例如,我有以下GetWithRawSql方法的实现:
public IEnumerable<TEntity> GetWithRawSql<TEntity>(string query, params object[] parameters) where TEntity : class
{
return DbContext.Set<TEntity>().SqlQuery(query, parameters).ToList();
}
和Async版本我已经实现了以下内容:
public async Task<IEnumerable<TEntity>> GetWithRawSqlAsync<TEntity>(string query, params object[] parameters) where TEntity : class
{
return await Task.Run(() => GetWithRawSql<TEntity>(query, parameters));
}
或相同的GetByKey方法:
public async Task<TEntity> GetByKeyAsync<TEntity>(object keyValue) where TEntity : class
{
return await Task.Run(() => GetByKey<TEntity>(keyValue));
}
上面的实现看起来像一个快速和肮脏的工作。您将如何实现上述方法?使用
可能会遇到哪些问题?await Task.Run(() => GetWithRawSql<TEntity>(query, parameters));
在我的存储库中吗?对于完整的植入,你可以看看博客,我使用实体框架6.1.1。
你所做的是async over sync,当处理异步工作时,这是一个反模式。
EF6已经开箱即用了一个async api,它不会在后台使用任何新的线程,而是使用数据库公开的异步IO工作来消耗其工作。
当你去异步而不是同步,你通常结束了一堆线程,基本上坐在那里等待查询返回,这不能很好地扩展,并使用冗余线程,这是不需要的,当处理IO绑定操作。此外,当人们看到async
方法时,他们从不说"他可能使用了一个新线程来运行同步版本",他们通常会说"这个async
实现将为IO绑定工作节省不必要的线程使用"
这是一个简单的UpdateAsync
方法完成EF6:
public static async Task<string> UpdateAsync(Customer obj)
{
NorthwindEntities db = new NorthwindEntities();
// This is an async method
Customer existing = await db.Customers.FindAsync(obj.CustomerID);
existing.CompanyName = obj.CompanyName;
existing.ContactName = obj.ContactName;
existing.Country = obj.Country;
await db.SaveChangesAsync(); // This is an async method
return "Customer updated successfully!";
}
你可以阅读更多关于EF6和async方法:
- 使用实体框架执行异步操作 异步查询&保存(EF6起)