CSDN|基于选项模式实现.NET Core的配置热更新( 二 )

//写法2:自动绑定 leaningOptions = Configuration.GetSection("Learning").Get<LearningOptions>; //写法3:自动绑定 + 依赖注入 services.Configure<LearningOptions>(Configuration.GetSection("Learning")); //写法4:配置的二次加工 services.PostConfigure<LearningOptions>(options => options.Years += 1); //写法5:委托绑定 services.Configure<AppInfoOptions>(options => { options.AppName = "ASP.NET Core"; options.AppVersion = "1.2.1"; }); 我们知道 , 在 .NET Core 里依赖注入被提升到了一等公民的位置 , 可谓是无处不在 。 当我们在 IoC 容器中注入LearningOptions以后 , 就可以在服务层或者控制器层直接使用它们 , 此时 , 我们就会遇到传说中的 Options 三剑客 , 即IOptions<TOptions>、IOptionsSnapshot<TOptions>和IOptionsMonitor<TOptions> 。 关于它们三个的区别 , 官方文档里给出了详细的说明:

  • IOptions:生命周期为 Singleton , 在应用启动时完成初始化 。 应用启动后 , 对配置的修改是非响应式的 。
  • IOptionsSnapshot:生命周期为 Scoped , 每次请求时会重新计算选项 。 应用启动后 , 对配置的修改是响应式的 。
  • IOptionsMonitor:生命周期为 Singleton , 可以随时检索当前配置项 。 应用启动后 , 对配置的修改是响应式的 。
是不是听起来有一点还有一点绕?长话短说就是 , 如果希望修改完配置立即生效 , 那么 , 更推荐使用IOptionsSnapshot<TOptions>和IOptionsMonitor<TOptions> , 前者是在下一次请求时生效 , 后者则是访问CurrentValue的时候生效 。 而对于像3.14或者0.618这种运行时期间不会修改的“常量” , 更推荐使用IOptions<TOptions> 。 下面是关于它们的一个例子:
[Route("[controller]")] public class WeatherForecastController : ControllerBase { private readonly ILogger<WeatherForecastController> _logger; private readonly IOptions<LearningOptions> _learningOptions; private readonly IOptionsSnapshot<LearningOptions> _learningOptionsSnapshot; private readonly IOptionsMonitor<LearningOptions> _learningOptionsMonitor; private readonly IConfiguration _configuration; public WeatherForecastController(ILogger<WeatherForecastController> logger, IOptions<LearningOptions> learningOptions, IOptionsSnapshot<LearningOptions> learningOptionsSnapshot, IOptionsMonitor<LearningOptions> learningOptionsMonitor, IConfiguration configuration ) { _logger = logger; _learningOptions = learningOptions; _learningOptionsSnapshot = learningOptionsSnapshot; _learningOptionsMonitor = learningOptionsMonitor; _configuration = configuration; _learningOptionsMonitor.OnChange((options, value) => { _logger.LogInformation($"OnChnage => {JsonConvert.SerializeObject(options)}"); });


推荐阅读