我只是好奇,在Java中,有一个@Transactional
属性可以放在方法名称上方,因为几乎每个应用程序服务方法都使用事务,因此可以简化代码。
// Java example
public class FooApplicationService {
@Transactional
public void DoSomething()
{
// do something ...
}
}
这就是目前在 .NET 中的实现方式
// .NET example
public class FooApplicationService {
public void DoSomething()
{
using (var transaction = new TransactionScope())
{
// do something ...
transaction.Complete();
}
}
}
是否也可以通过 .NET Core 中的注释属性来管理事务?
最佳答案
您可以为此目的创建操作过滤器
//filter factory is used in order to create new filter instance per request
public class TransactionalAttribute : Attribute, IFilterFactory
{
//make sure filter marked as not reusable
public bool IsReusable => false;
public IFilterMetadata CreateInstance(IServiceProvider serviceProvider)
{
return new TransactionalFilter();
}
private class TransactionalFilter : IActionFilter
{
private TransactionScope _transactionScope;
public void OnActionExecuting(ActionExecutingContext context)
{
_transactionScope = new TransactionScope();
}
public void OnActionExecuted(ActionExecutedContext context)
{
//if no exception were thrown
if (context.Exception == null)
_transactionScope.Complete();
}
}
}
像这样使用它
public class HomeController : Controller {
//...
[Transactional]
public IActionResult Test() { /*some code */ }
//...
}
注意
正如 @cmart 的评论中提到的有更优雅的解决方案可以使用 IAsyncActionFilter 来实现此目的。检查是否没有按照 @notracs 抛出异常也很重要。评论。
public class TransactionalAttribute : Attribute, IAsyncActionFilter
{
public async Task OnActionExecutionAsync(ActionExecutingContext context, ActionExecutionDelegate next)
{
using (var transactionScope = new TransactionScope())
{
ActionExecutedContext actionExecutedContext = await next();
//if no exception were thrown
if (actionExecutedContext.Exception == null)
transactionScope.Complete();
}
}
}
关于c# - .NET Core 中的事务注释属性,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/57441301/