zoukankan      html  css  js  c++  java
  • 类库使用ConfigureAwait.Fody配置全局ConfigureAwait (false)取消异步上下文切换

    在.net中(包括.net core和.net framework)异步任务默认的会带有一个上下文关联的一个状态机,也就是配置的ConfigureAwait为ture,微软官方文档解释为:尝试将延续任务封送回原始上下文
    譬如一个异步方法:

    async Task MethodWithContextAsync () {
        await Task.Delay (TimeSpan.FromSeconds (1));
        // 默认会获取一个上下文(上下文会获取一个调度者,没有则从线程池中获取),并在该上下文中回调,
    }
    

    默认的方法等同于

    async Task MethodWithContextAsync () {
        await Task.Delay (TimeSpan.FromSeconds (1)).ConfigureAwait(true);
        // 等同与没加.ConfigureAwait方法
    }
    

    如果只是在类库中使用异步方法,则可以加.ConfigureAwait(false);

    async Task MethodWithoutContextAsync () {
        await Task.Delay (TimeSpan.FromSeconds (1)).ConfigureAwait(false);
        // 去掉掉任务的上下文,没有了上下文对象的开销,也就能提高性能
    }
    

    如果每一个异步方法调用都加上ConfigureAwait(false)则改动比较大,这时候就可以利用ConfigureAwait.Fody来做全局配置,
    编译后的就会在项目里的每一个异步调用后面加上ConfigureAwait(false),相当于AOP静态织入。

    添加nuget包:

    PM> Install-Package Fody
    PM> Install-Package ConfigureAwait.Fody
    

    然后在VS项目中右键生成,会看到多了一个FodyWeavers.xml文件

    默认是没有设置ConfigureAwait(false),需要在FodyWeavers.xml的ConfigureAwait节点添加 ContinueOnCapturedContext="false"

    <Weavers xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="FodyWeavers.xsd">
      <ConfigureAwait ContinueOnCapturedContext="false" />
    </Weavers>
    

    使用ILSpy反编译下程序集生成的dll,可以看到ConfigureAwait.Fody已经在编译期间自动在异步方法调用后面加上了.ConfigureAwait(continueOnCapturedContext: false)

    ConfigureAwait相关参考资料:
    https://www.cnblogs.com/xiaoxiaotank/p/13529413.html
    https://www.cnblogs.com/AlienXu/archive/2019/07/12/11177434.html
    https://github.com/Fody/ConfigureAwait

  • 相关阅读:
    vue2.0 keep-alive最佳实践
    Vue解决安卓4.4不兼容的问题
    体验异步的终极解决方案-ES7的Async/Await
    axios在vue中的简单配置与使用
    AngularJS-UI-Router
    SignalR 填坑记
    小心C# 5.0 中的await and async模式造成的死锁
    使用BCP导出导入数据
    关闭正在执行的事务 Kill
    C# 正则表达式
  • 原文地址:https://www.cnblogs.com/townsend/p/13748954.html
Copyright © 2011-2022 走看看