net Core 读取和修改json文件
定义一个IOptions<T>的扩展接口IWritableOptions<T>来进行读写设置
public interface IWritableOptions<out T> : IOptionsSnapshot<T> where T : class, new() { void Update(Action<T> applyChanges); }
接口实现类WritableOptions<T>
public interface IWritableOptions<out T> : IOptionsSnapshot<T> where T : class, new() { void Update(Action<T> applyChanges); } public class WritableOptions<T> : IWritableOptions<T> where T : class, new() { private readonly IHostingEnvironment _environment; private readonly IOptionsMonitor<T> _options; private readonly string _section; private readonly string _file; public WritableOptions( IHostingEnvironment environment, IOptionsMonitor<T> options, string section, string file) { _environment = environment; _options = options; _section = section; _file = file; } public T Value => _options.CurrentValue; public T Get(string name) => _options.Get(name); public void Update(Action<T> applyChanges) { var fileProvider = _environment.ContentRootFileProvider; var fileInfo = fileProvider.GetFileInfo(_file); var physicalPath = fileInfo.PhysicalPath; var jObject = JsonConvert.DeserializeObject<JObject>(File.ReadAllText(physicalPath)); var sectionObject = jObject.TryGetValue(_section, out JToken section) ? JsonConvert.DeserializeObject<T>(section.ToString()) : (Value ?? new T()); applyChanges(sectionObject); jObject[_section] = JObject.Parse(JsonConvert.SerializeObject(sectionObject)); File.WriteAllText(physicalPath, JsonConvert.SerializeObject(jObject, Formatting.Indented)); } }
IServiceCollection扩展方法
public static class ServiceCollectionExtensions { public static void ConfigureWritable<T>( this IServiceCollection services, IConfigurationSection section, string file = "appsettings.json") where T : class, new() { services.Configure<T>(section); services.AddTransient<IWritableOptions<T>>(provider => { var environment = provider.GetService<IHostingEnvironment>(); var options = provider.GetService<IOptionsMonitor<T>>(); return new WritableOptions<T>(environment, options, section.Key, file); }); } }
创建json文件(默认appsettings.json)
{ "MySection": { "Name": "abc", "Age": 22 } }
在startup中绑定json文件节点MySection到MyClass
services.ConfigureWritable<MyClass>(Configuration.GetSection("MySection"));
也可以自定义要保存的json文件
services.ConfigureWritable<MyClass>(Configuration.GetSection("MySection"), "appsettings.custom.json");
当自定义保存到json文件的时候,要在项目启动时候添加自定义文件
public class Program { public static void Main(string[] args) { // BuildWebHost(args).Run(); var host = BuildWebHost(args) .Migrate();//初始化数据 host.Run(); } public static IWebHost BuildWebHost(string[] args) => WebHost.CreateDefaultBuilder(args) .ConfigureAppConfiguration(config => config.AddJsonFile("appsettings.custom.json", optional: true, reloadOnChange: true)) .UseStartup<Startup>() .Build(); }
控制器中注入
public class HomeController : BaseController { private readonly IWritableOptions<MyClass> _options; public HomeController(IWritableOptions<MyClass> options) { _options = options; } public IActionResult Index() { _options.Update(opt => { opt.Name = "value1"; opt.Age =1; }); } }
更新节点的Name为value1 ,Age为1
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· Linux系列:如何用heaptrack跟踪.NET程序的非托管内存泄露
· 开发者必知的日志记录最佳实践
· SQL Server 2025 AI相关能力初探
· Linux系列:如何用 C#调用 C方法造成内存泄露
· AI与.NET技术实操系列(二):开始使用ML.NET
· 无需6万激活码!GitHub神秘组织3小时极速复刻Manus,手把手教你使用OpenManus搭建本
· C#/.NET/.NET Core优秀项目和框架2025年2月简报
· Manus爆火,是硬核还是营销?
· 终于写完轮子一部分:tcp代理 了,记录一下
· 【杭电多校比赛记录】2025“钉耙编程”中国大学生算法设计春季联赛(1)