3.2 配置系统

举报
步步为营 发表于 2023/02/14 11:35:03 2023/02/14
【摘要】 .Net Core配置系统支持文件(Json、XML、INI)、注册表、环境变量、命令行、AZure Key Vault等。

3.2 配置系统

配置系统基本使用

.Net Core配置系统支持文件(Json、XML、INI)、注册表、环境变量、命令行、AZure Key Vault等。

案例,使用jsonwen文件来配置。

新建config.json文件,程序默认加载exe同目录下的配置文件,所以应设置config.json“复制到输出目录”属性为“如果较新则复制”

{
  "name": "zack",
  "proxy": {
    "address": "192.168.1.9",
    "port": 1088
  }
}

.net core系统配置开发包为Microsoft.Extensions.Configuration,读取JSON文件应使用Microsoft.Extensions.Configuration.Json。

using Microsoft.Extensions.Configuration;

//配置创建器
ConfigurationBuilder configBuilder = new ConfigurationBuilder();
//添加一个待解析的JSON文件,option,为true时文件不存在也不会报错;reloadOnChange:文件修改是否重新加载配置
configBuilder.AddJsonFile("config.json", optional: false, reloadOnChange: false);
//通过它读取配置项
IConfigurationRoot config = configBuilder.Build();
string name = config["name"];
string proxyAddress = config.GetSection("proxy:address").Value;//配置分级方式的读取

选项方式读取配置

选项方式可以和依赖注入结合,同时可以实现修改配置后自动刷新。

需要安装Microsoft.Extensions.Options和Microsoft.Extensions.Binder。

案例:

  1. 新建appsettings.json文件
{
  "Logging": { "LogLevel": { "Default": "Warning" } },
  "DB": {
    "DbType": "SQLServer",
    "ConnectionString": "Data Source=.;Initial Catalog=DemoDB; Integrated Security=True"
  },
  "Smtp": {
    "Server": "smtp.youzack.com",
    "UserName": "zack",
    "Password": "hello888"
  },
  "AllowedHosts": "*"
}
  1. 我们只对DB和Smtp感兴趣,建立另个对应的模型类
public class DbSettings
{
    public string DbType { get; set; }
    public string ConnectionString { get; set; }
}
public class SmtpSettings
{
    public string Server { get; set; }
    public string UserName { get; set; }
    public string Password { get; set; }
}

使用选项方式读取配置时需要和依赖注入一起使用,所以创建一个类哟用于获取注入的选项值。接收选项注入的对象有:

IOptions<T>:配置改变后,不能读取新的值,必须重启程序

IOptionsMonitor<T>:配置改变后可以读取新的值,A、B两处都读取某个选项值,在A之后B之前配置项改变,A仍然是旧值,B是新值

IOptionsSnapshot<T>:和IOptionsMonitor<T>不同之处在于AB都是旧值,再次进入这个范围才会读到新值

  1. 测试读取Demo类
using Microsoft.Extensions.Options;

class Demo
{
    //在构造方法中声明所依赖的类
	private readonly IOptionsSnapshot<DbSettings> optDbSettings;
	private readonly IOptionsSnapshot<SmtpSettings> optSmtpSettings;
	public Demo(IOptionsSnapshot<DbSettings> optDbSettings,
		IOptionsSnapshot<SmtpSettings> optSmtpSettings)
	{
		this.optDbSettings = optDbSettings;
		this.optSmtpSettings = optSmtpSettings;
	}
	public void Test()
	{
		var db = optDbSettings.Value;//通过value属性获取对象具体的值
		Console.WriteLine($"数据库:{db.DbType},{db.ConnectionString}");
		var smtp = optSmtpSettings.Value;
		Console.WriteLine($"Smtp:{smtp.Server},{smtp.UserName},{smtp.Password}");
	}
}
  1. 注入服务到容器
using Microsoft.Extensions.Configuration;
using Microsoft.Extensions.DependencyInjection;

ConfigurationBuilder confi   gBuilder = new ConfigurationBuilder();
configBuilder.AddJsonFile("appsettings.json", optional: false, reloadOnChange: true);//reloadOnChange要设置为true
IConfigurationRoot config = configBuilder.Build();
ServiceCollection services = new ServiceCollection();//容器
services.AddOptions()//注册与选项相关的服务
	.Configure<DbSettings>(e=>config.GetSection("DB").Bind(e))//将DB节点的内容绑定到DbSettings上
	.Configure<SmtpSettings>(e => config.GetSection("Smtp").Bind(e));
//上面定义的IOptionsSnapshot<T>为范围,所以Demo不能是单例,因为Demo中需要Option,所以Demo不能比Option声明周期短
services.AddTransient<Demo>();
using (var sp = services.BuildServiceProvider())
{
	while (true)
	{
		using (var scope = sp.CreateScope())//option设置为范围声明周期,在这里,创建一个新范围
		{
			var spScope = scope.ServiceProvider;
			var demo = spScope.GetRequiredService<Demo>();
			demo.Test();
		}
		Console.WriteLine("可以改配置啦");
		Console.ReadKey();
	}
}

从命令行读取配置

适合容器化的运行环境

//NuGet安装Microsoft.Exensions.Configuration.CommandLine
ConfigurationBuilder configBuilder = new ConfigurationBuilder();
configBuilder.AddCommandLine(args);
IConfigurationRoot config = configBuilder.Build();
string server = config["server"];
Console.WriteLine($"server:{server}");

从环境变量读取配置

//NuGet安装Microsoft.Exensions.Configuration.EnvironmentVariables
ConfigurationBuilder configBuilder = new ConfigurationBuilder();
//AddEnvironmentVariables存在无参数和prefix参数两个版本
//无参数表示将所有环境变量加载,prefix表示将带有某前缀的环境便令读入
configBuilder.AddEnvironmentVariables("TEST_");
IConfigurationRoot configRoot = configBuilder.Build();
string name = configRoot["Name"];//环境变量TEST_Name
Console.WriteLine(name);

多配制源

场景:开发的软件可以从服务器中读取配置,但是我们想临时更改配置又不影响其他用户,并且日后不想用了可以直接删除本地配置即可。

ConfigurationBuilder configBuilder = new ConfigurationBuilder();
//增加json、环境变量、命令行配置
//后添加的配置程序覆盖之前的配置程序
configBuilder.AddJsonFile("appsettings.json")
    .AddEnvironmentVariables("Test1_").AddCommandLine(args);
IConfigurationRoot config = configBuilder.Build();
string server = config["Server"];
string userName = config["UserName"];
string password = config["Password"];
string port = config["Port"];
//Console.WriteLine($"server={server},port={port}");
//Console.WriteLine($"userName={userName},password={password}");
//配置源较多的时候,查看配置值来自哪个配置程序
Console.WriteLine(config.GetDebugView());
【版权声明】本文为华为云社区用户原创内容,转载时必须标注文章的来源(华为云社区)、文章链接、文章作者等基本信息, 否则作者和本社区有权追究责任。如果您发现本社区中有涉嫌抄袭的内容,欢迎发送邮件进行举报,并提供相关证据,一经查实,本社区将立刻删除涉嫌侵权内容,举报邮箱: cloudbbs@huaweicloud.com
  • 点赞
  • 收藏
  • 关注作者

评论(0

0/1000
抱歉,系统识别当前为高风险访问,暂不支持该操作

全部回复

上滑加载中

设置昵称

在此一键设置昵称,即可参与社区互动!

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。