我正在使用 ServiceStack.net 开发服务器应用程序。数据库通过 EntityFramwork 访问。现在我想要一个环境事务,如果没有错误/异常,它会自动提交,否则应该丢弃更改。
是否有一些开箱即用的东西我还没有找到,还是我需要自己动手?
如果我必须自己动手,我该怎么做?首先想到的是请求和响应过滤器。
我正在使用 ServiceStack.net 开发服务器应用程序。数据库通过 EntityFramwork 访问。现在我想要一个环境事务,如果没有错误/异常,它会自动提交,否则应该丢弃更改。
是否有一些开箱即用的东西我还没有找到,还是我需要自己动手?
如果我必须自己动手,我该怎么做?首先想到的是请求和响应过滤器。
我使用请求和响应过滤器来设置环境事务(在我的情况下实际上是一个 NHibernate 会话,但这是一个类似的想法)。我们通过添加到AppHost方法中的RequestFilters
and集合来做到这一点。ResponseFilters
Configure
我们还需要区分成功提交事务和出现任何错误时回滚/清除事务:
// normally: commit the transaction
ResponseFilters.Add((req, res, dto) => DbConnectionUtility.CleanupTransactionsAndConnections(req.RawUrl));
// rollback if unhandled exception in a service method
ServiceExceptionHandler = (request, exception) =>
{
DbConnectionUtility.ClearSessions();
// run the default code that sends a nicely serialized error response
return DtoUtils.HandleException(this, request, exception);
};
// rollback if unhandled exception outside of service (e.g. in a filter)
var defaultExceptionHandler = ExceptionHandler;
ExceptionHandler = (httpReq, httpRes, operationName, ex) =>
{
DbConnectionUtility.ClearSessions();
// run the default code that sends a nicely serialized error response
defaultExceptionHandler(httpReq, httpRes, operationName, ex);
};
@esker 感谢您为我指明正确的方向
由于TransactionScope
默认情况下如果未调用则回滚,Complete()
因此我不需要为ServiceExceptionHandler
and附加处理程序ExceptionHandler
我当前的解决方案在 AppHost 文件中如下所示:
public void ConfigureFilters(Container container)
{
RequestFilters.Add(
(req, res, dto) =>
req.Items.Add("transaction", new TransactionScope(TransactionScopeOption.RequiresNew)));
ResponseFilters.Add((req, res, dto) =>
{
TransactionScope transaction = null;
var error = dto as HttpError;
try
{
transaction = req.Items["transaction"] as TransactionScope;
if (error == null)
{
container.Resolve<TierDbEntitiesContainer>().SaveChanges();
if (transaction == null)
throw new AmbientTransactionException("Transaction not found.");
transaction.Complete();
}
}
finally
{
if (transaction != null)
transaction.Dispose();
}
});
}