Я сделал нечто похожее на вашу проблему, но с nHibernate.Проверьте это (часть моего файла):
Это наиболее важные функции, которые, к сожалению, должны как-то дублироваться.Эти функции делают весь повторяемый код.Параметр действия - это то, что им действительно нужно сделать (например, вставка). Контекст - это в основном сеанс nHibernate.В nHibernate каждая операция должна быть внутри сеанса.GetContextForStatement возвращает только новый сеанс или ранее открытый действительный.
//sync version
T GeneralExecuteAction<T>(Func<ISession, T> action)
{
lastDbError = DbError.Ok;
using (var ctx = GetContextForStatement())
{
try
{
T result = action(ctx.session);
ctx.CommitTransactionIfExists();
return result;
}
catch (Exception ex)
{
ctx.RollbackTransactionIfExists();
lastDbError = new DbError(ex);
return default(T);
}
}
}
//async version
async Task<T> GeneralExecuteAction<T>(Func<ISession, Task<T>> action)
{
lastDbError = DbError.Ok;
using (var ctx = GetContextForStatement())
{
try
{
T result = await action(ctx.session);
await ctx.CommitTransactionIfExistsAsync();
return result;
}
catch (Exception ex)
{
await ctx.RollbackTransactionIfExistsAsync();
lastDbError = new DbError(ex);
return default(T);
}
}
}
Теперь вы можете просто использовать вышеуказанные функции в ваших публичных методах: Например, синхронизировать версию save:
public DbError Save<T>(T obj) where T : class
{
GeneralExecuteAction((s) =>
{
s.Save(obj); //s is nHibernate session
return true;
});
return lastDbError;
}
Иасинхронная версия сохранения
public async Task<DbError> SaveAsync<T>(T obj) where T : class
{
await GeneralExecuteAction((s) =>
{
s.Save(obj);
return Task.FromResult(true);
});
return lastDbError;
}