共享范围等待
我有一个UserScope
类,其function类似于TransactionScope
,即它将当前状态存储在本地线程中。 这当然不适用于await
调用,在.NET 4.5.1中添加TransactionScope
之前, TransactionScopeAsyncFlowOption
也没有。
我可以使用什么替代线程本地,以便UserScope
可以在单线程和multithreading场景中使用相同的? (如果我安装了4.5.1,我会反编译以查看TransactionScope
是如何做到的。)这是我所拥有的简化版本:
class User { readonly string name; public User(string name) { this.name = name; } public string Name { get { return this.name; } } } class UserScope : IDisposable { readonly User user; [ThreadStatic] static UserScope currentScope; public UserScope(User user) { this.user = user; currentScope = this; } public static User User { get { return currentScope != null ? currentScope.user : null; } } public void Dispose() { ///... } }
这是我期望工作的测试:
static async Task Test() { var user = new User("Thread Flintstone"); using (new UserScope(user)) { await Task.Run(delegate { Console.WriteLine("Crashing with NRE..."); Console.WriteLine("The current user is: {0}", UserScope.User.Name); }); } } static void Main(string[] args) { Test().Wait(); Console.ReadLine(); }
在.NET 4.5完整框架中,您可以使用逻辑调用上下文:
static async Task Test() { CallContext.LogicalSetData("Name", "Thread Flintstone"); await Task.Run(delegate { //Console.WriteLine("Crashing with NRE..."); Console.WriteLine("The current user is: {0}", CallContext.LogicalGetData("Name")); }); } static void Main(string[] args) { Test().Wait(); Console.ReadLine(); }
但是,您应该只在逻辑调用上下文中存储不可变数据。 我的博客上有更多细节 。 我一直AsyncLocal
包装成一个AsyncLocal
库,但还没有找到时间。