.NET 6 Web App中IOptionsMonitor如何监控程序目录下的appsettings.json?
场景与现有实现
我正在开发一个.NET 6.0 ASP.NET Core Web应用,应用启动后需编辑appsettings.json以实现管理功能,待编辑内容如下:
{ "Admin": { "WhiteList": ["::1",.....] }, .... }
对应的模型类为:
public class AdminOptions { public const string Admin = "Admin"; public string[] WhiteList { get; set; } }
并在Program.cs中进行如下配置:
... var builder = WebApplication.CreateBuilder(args); builder.Services.Configure<AdminOptions>( builder.Configuration.GetSection(AdminOptions.Admin));
AdminOptions通过构造函数注入到单例服务WhiteChecker中:
public class WhiteChecker: IWhiteChecker { private readonly IOptionsMonitor<AdminOptions> optionsMonitor; public WhiteChecker(IOptionsMonitor<AdminOptions> monitor) { optionsMonitor = monitor; } .....[此处使用optionsMonitor.CurrentValue.WhiteList]..... }
遇到的问题
当修改项目根目录下的appsettings.json时,IOptionsMonitor.CurrentValue能正确返回Admin节点下WhiteList的修改后值,但修改**AppContext.BaseDirectory(程序运行目录)**下的该文件时,IOptionsMonitor无响应。
我曾尝试在Program.cs中创建WebApplicationBuilder后修改WebApplicationBuilder.Environment.ContentRootPath为AppContext.BaseDirectory,但结果依旧。
解决方案与更新(2022/10/11)
我之前设置Environment.ContentRootPath的方式有误:
- 错误写法:
var builder = WebApplication.CreateBuilder(args); builder.Environment.ContentRootPath = AppContext.BaseDirectory;
- 正确写法:
var builder = WebApplication.CreateBuilder(new WebApplicationOptions { ContentRootPath = AppContext.BaseDirectory });
设置正确后,IOptionsMonitor开始监控AppContext.BaseDirectory下的appsettings.json。
正确写法遵循ASP.NET CORE 6.0迁移文档中3.1/5.0代码迁移至6.0的指导。
错误写法无效的原因,根据ASP.NET CORE 6.0基础配置文档说明:
初始化主机生成器时,以下变量会被提前锁定,无法通过应用配置修改:
- 应用名称
- 环境名称,例如Development、Production和Staging
- 内容根目录
- Web根目录...
补充说明(2022/10/13)
上述行为在ASP.NET CORE 6.0迁移文档(5.0至6.0)中被明确重申:
创建WebApplicationBuilder后,无法修改任何主机设置,如应用名称、环境或内容根目录。
需要注意的是,使用错误写法时不会抛出异常,系统会默认静默忽略该修改。
内容的提问来源于stack exchange,提问作者Ryo

