AspectCore-Framework
AspectCore-Framework copied to clipboard
使用aspectCore做SqlSugar的事务拦截器,发现获取ISqlSugarClient对象变了
问题描述: 使用aspectCore做SqlSugar的事务拦截器,发现获取ISqlSugarClient对象变了。 使用FromServiceContext或者 context.ServiceProvider.GetService<ISqlSugarClient>()获取ISqlSugarClient的对象发生变化; SqlSugarClient是AsyncLocal共享存储,发生线程变化就会重新对象,一般Task.Run开启线程才会发生变化呀
注入方式:
services.AddSingleton<ISqlSugarClient>()
[AttributeUsage(AttributeTargets.Method, AllowMultiple = true)]
public class TransactionAopAttribute : AbstractInterceptorAttribute
{
[FromServiceContext]
public ILogger<TransactionAopAttribute> Logger { get; set; }
[FromServiceContext]
public ISqlSugarClient SqlSugarClient { get; set; }
public string Name { get; set; }
public IsolationLevel Level { get; set; } = IsolationLevel.Unspecified;
public override async Task Invoke(AspectContext context, AspectDelegate next)
{
// var sqlSugarClient = context.ServiceProvider.GetService<ISqlSugarClient>();
Console.WriteLine($"{Name}:{SqlSugarClient.ContextID}");
var notTran = SqlSugarClient.Ado.IsNoTran();
if (!notTran)
{
await next.Invoke(context);
return;
}
try
{
await SqlSugarClient.Ado.BeginTranAsync(Level);
await next(context);
await SqlSugarClient.Ado.CommitTranAsync();
}
catch
{
await SqlSugarClient.Ado.RollbackTranAsync();
throw;
}
}
}
public interface ITestService
{
Task Say();
}
public class TestService : ITestService, IScopedDependency
{
private readonly ISqlSugarClient _sqlSugarClient;
public TestService(ISqlSugarClient sqlSugarClient)
{
_sqlSugarClient = sqlSugarClient;
}
[TransactionAop(Name = "TestService=>AOP")]
public virtual Task Say()
{
Console.WriteLine($"TestService=>Say:{_sqlSugarClient.ContextID}");
return Task.CompletedTask;
}
}
private readonly ITestService _testService;
public DelayRefundJob(ITestService testService)
{
_testService = testService;
}
//[TransactionAop(Name = "Execute")]
public virtual async Task Execute()
{
await _testService.Say();
await Task.Delay(1000);
Console.WriteLine("========================");
await _testService.Say();
}
两次调用 _testService.Say() ContextId居然不一致。如果把AOP特性去掉,ContextID是一致的
拦截器本身是异步的。ISqlSugarClient 建议使用单例或者scoped吧
用了拦截器相当于就开了新的异步,对于每个await内部相当于是独立线程了