.NET Core读取配置文件的方法
作者:畅饮无绪 发布时间:2024-06-05 09:31:38
配置文件是每个项目最基础的部分,也是不可或缺的部分,比如:数据库连接、中间件属性等常见的配置。
提前准备
appsettings.json 文件
{
"User": {
"userName": "赵一",
"userAge": 18
}
}
对应实体模型
public class UserOption
{
public string userName { get; set; }
public int userAge { get; set; }
}
常规读取
1、注册
在 startup 类中注册,主要用到的是 Configure 方法:
services.Configure<UserOption>(Configuration.GetSection("User"));
2、控制器中注入并读取
public class HomeController : ControllerBase
{
private readonly UserOption user;
public HomeController(IOptions<UserOption> userOptions)
{
user = userOptions.Value;
}
[HttpGet]
public string Get()
{
return $"姓名:{user.userName},年龄:{user.userAge} ";
}
}
输出结果:姓名:赵一,年龄:18
嵌套读取
我们对 appsettings.json 文件做一点小小的改动,增加一个子节点 child
:
{
"User": {
"userName": "赵一",
"userAge": 18,
"child": {
"userName": "赵一的崽",
"userAge": 2
}
}
}
再对注册的代码做一点小小的修改:
services.Configure<UserOption>(Configuration.GetSection("User:child"));
输出结果:姓名:赵一的崽,年龄:2
分实例读取
这个时候需求又有变化了,需要同时读取 User
与 child
节点的数据,我们试试下面的方法看可行不可行:
// 注册
services.Configure<UserOption>(Configuration.GetSection("User"));
services.Configure<UserOption>(Configuration.GetSection("User:child"));
// 控制器
public class HomeController : ControllerBase
{
private readonly UserOption user;
private readonly UserOption child;
public HomeController(IOptions<UserOption> userOptions, IOptions<UserOption> childOptions)
{
user = userOptions.Value;
child = childOptions.Value;
}
[HttpGet]
public string Get()
{
return $"姓名:{user.userName},年龄:{user.userAge} \r\n姓名:{child.userName},年龄:{child.userAge}";
}
}
输出结果很显然满足不了我们的需求:
姓名:赵一的崽,年龄:2
姓名:赵一的崽,年龄:2
有的小伙伴肯定会说,在实体模型内在加一个子节点字段。这样肯定是没问题的,但是与常规读取方式就没什么两样了。
这里我要说的是分实例读取,引入 Configure
的另一个重载方法,与之前不同的是多了一个参数 name
:
public static IServiceCollection Configure<TOptions>(this IServiceCollection services, string name, IConfiguration config) where TOptions : class;
下面我们重新注册:
services.Configure<UserOption>("father", Configuration.GetSection("User"));
services.Configure<UserOption>("son", Configuration.GetSection("User:child"));
在控制器构造函数中注入,也引入了一个新的接口对象:IOptionsMonitor
public class HomeController : ControllerBase
{
private readonly UserOption user;
private readonly UserOption child;
public HomeController(IOptionsMonitor<UserOption> userOptions, IOptionsMonitor<UserOption> childOptions)
{
user = userOptions.Get("father");
child = childOptions.Get("son");
}
[HttpGet]
public string Get()
{
return $"姓名:{user.userName},年龄:{user.userAge} \r\n姓名:{child.userName},年龄:{child.userAge}";
}
输出结果:
姓名:赵一,年龄:18
姓名:赵一的崽,年龄:2
其实还有一个接口对象能实现这样的效果:IOptionsSnapshot
,那 IOptionsMonitor
与 IOptionsSnapshot
有什么不同呢?请接着往下看。
IOptionsMonitor与IOptionsSnapshot的不同之处
我们先来看看微软官方的注释:
IOptionsMonitor
//
// 摘要:
// Used for notifications when TOptions instances change.
//
// 类型参数:
// TOptions:
// The options type.
public interface IOptionsMonitor<out TOptions>
{
//
// 摘要:
// Returns the current TOptions instance with the Microsoft.Extensions.Options.Options.DefaultName.
TOptions CurrentValue { get; }
//
// 摘要:
// Returns a configured TOptions instance with the given name.
TOptions Get(string name);
//
// 摘要:
// Registers a listener to be called whenever a named TOptions changes.
//
// 参数:
// listener:
// The action to be invoked when TOptions has changed.
//
// 返回结果:
// An System.IDisposable which should be disposed to stop listening for changes.
IDisposable OnChange(Action<TOptions, string> listener);
}
IOptionsSnapshot
//
// 摘要:
// Used to access the value of TOptions for the lifetime of a request.
//
// 类型参数:
// TOptions:
// Options type.
public interface IOptionsSnapshot<out TOptions> : IOptions<TOptions> where TOptions : class, new()
{
//
// 摘要:
// Returns a configured TOptions instance with the given name.
TOptions Get(string name);
}
从字面上理解,IOptionsMonitor
建议在配置信息更改后需要通知的场景下使用,所以多了个 OnChange
的方法;而 IOptionsSnapshot
翻译过来的意思是:用于在请求的生命周期内访问配置,有点难以理解哈,我们接下来用代码来验证一下。
IOptionsMonitor 与 IOptionsSnapshot的生命周期
我们对实体模型再做一点小小的修改,增加一个 guid 字段,并给上默认值:
public class UserOption
{
public string userName { get; set; }
public int userAge { get; set; }
public Guid guid { get; set; } = Guid.NewGuid();
}
我们再次运行程序:
father — 姓名:赵一,年龄:19,编号:e0d71f47-e8f1-4a6d-875e-2074c985f4a0
son — 姓名:赵一的崽,年龄:3,编号:d865151b-f9bf-4eff-bb4e-8ab6dc61160c
然后不停的刷新页面会发现,father
的编号没有发生任何编号,而 son
的编号每次刷新都会改变。这是不是比较像我们注册时所用到的三种模式:
services.AddScoped();
services.AddTransient();
services.AddSingleton()
其中 father
类似 AddSingleton
,son
则类似 AddScoped
与 AddTransient
。
大家可以在同一个方法里多次调用 childOptions.Get("son")
看看 son
到底时类似 AddScoped
还是 AddTransient
。
IOptionsMonitor的OnChange调用方式
userOptions.OnChange((user,name)=> { Console.WriteLine(user.userName +"-"+ name); });
无文件配置
无文件配置就是不需要以静态文件的方式进行配置。相关信息在配置一次后就不用再做修改,我们可以采用无文件配置的方式,比如我们熟悉的 AddCors
跨域配置
services.AddCors(op => {
op.AddPolicy(CorsName, set => {
set.SetIsOriginAllowed(origin => true).AllowAnyHeader().AllowAnyMethod().AllowCredentials();
});
});
我们对之前的注册方法进行一下改动:
services.Configure<UserOption>(c =>
{
c.userName = "钱二";
c.userAge = 60;
});
控制器注入采用常规的注入方式,最终输出结果:姓名:钱二,年龄:60
分享一个源码查看网站:https://source.dot.net/
来源:https://www.cnblogs.com/cool-net/p/15594583.html


猜你喜欢
- 公司的一个项目中,有许多地方需要延时执行一些可重复性的函数(动作),就写了下面这段函数。 呵呵,不知道取什么意思更为确切些,就定为了:Loo
- 1. CBV加装饰器CBV加装饰器有三种方法,案例:要求登录(不管get请求还是post请求)后才可以访问HTML代码index.html&
- 软件测试面试如何测试网页的登录页面这个面试题碰到过很多次, 再次总结下来。具体需求: 有一个登陆页面, 上面有2个textbox, 一个提交
- 问题产生描述使用子进程处理一个大的日志文件,并对文件进行分析查询,需要等待子进程执行的输出结果,进行下一步处理。出问题的代码# 启用子进程执
- 需提前安装好pyzbar和opencv-python库(博主的电脑安装opencv-python库比较麻烦,但大部分都不会出现该问题)安装方
- 所以就为FCKeditor写了个InsertCode的插件。整个插件的制作过程非常简单:FCKeditor插件开发请参考FCKeditor官
- 要想创建一个iterator,必须实现一个有__iter__()和__next__()方法的类,类要能够跟踪内部状态并且在没有元素返回的时候
- MySQL中常用到判断符号,而不等于是比较常用的符号,下面讲解以下三种不等于符号符号意义<>不等于的最早用法,可移植性优于下面两
- MAC下MYSQL5.7.17无法连接的问题,下载安装完SQLBench_community 6.3.9后新建MYSQL CONNECTIO
- select nid,ntitle,nreadtimes,Row_number() over(order by nreadtimes des
- 有1张表, Wages 表 ------------------------------------------- Emp_id&
- Python 关于a=[[]]*3的反思之前用python做了一个关于交通大数据的项目,由于之前比较赶进度,故现在会陆续更新对项目代码的一些
- 最近在工作中涉及到判断服务器所在ip反馈程序使用情况的程序主要要求就是,本机或局域网调试程序时,不反馈其域名(localhost)或ip站长
- 使用正则提取数据,请求库requests,看代码,在存入数据库时,报错ERROR 1054 (42S22): Unknown column
- 本文实例讲述了go语言base64用法。分享给大家供大家参考。具体如下:这里展示golang base64 的一个小例子,代码如下:pack
- 主要功能在copyFiles()函数里实现,如下:def copyFiles(src, dst): sr
- 代码编辑环境Win10+(Pycharmm or Vscode)+PyQt 5.14.2功能实现静态作图:数据作图,取决于作图函数,可自行修
- import numpy as npimport pandas as pdfrom pandas_datareader import dat
- 一 web框架的本质及自定义web框架我们可以这样理解:所有的Web应用本质上就是一个socket服务端,而用户的浏览器就是一个socket
- 前言上篇介绍了go-grpc-middleware的grpc_zap、grpc_auth和grpc_recovery使用,本篇将介绍grpc