.net core系列之《新一代的配置系统Configuration在支持多数据源,热更新,层级化方面代码快速实践》
在我们之前.Net Framework的项目中,配置文件是WebConfig或AppcConfig文件,而当我们想要添加我们自定义的节点时,还需要在这个文件中的section中定义我们自定义的节点,这样的配置文件中的系统配置和我们自定义的配置耦合度也很高。
而在.Net Core中,配置系统改变了,它支持多种数据源,让配置文件变的不再单一化:json,xml,ini,memory,command, env
以下项目都是以控制台项目为基础
一、Json
1、要想加载json文件中的数据,就必须要安装它所依赖的包,我们打开NuGet包管理器,搜索并安装 Microsoft.Extensions.Configuration.Json
2、我们在项目中新增一个 appSettings.json 文件,并且设置始终复制到输出目录
3、接下来我们看以下代码:
static void Main(string[] args) { IConfiguration configuration = new ConfigurationBuilder() .SetBasePath(Environment.CurrentDirectory) .AddJsonFile("appSettings.json") .Build(); var info = configuration["username"]; Console.WriteLine(info); Console.ReadKey(); }
最后我们可以看到控制台上输入json文件中的结果
二、Xml
1、要想加载xml文件中的数据,就必须要安装它所依赖的包,我们打开NuGet包管理器,搜索并安装 Microsoft.Extensions.Configuration.Xml
2、我们在项目中新增一个 appSettings.xml 文件,并且设置始终复制到输出目录
3、接下来我们看以下代码:
static void Main(string[] args) { IConfiguration configuration = new ConfigurationBuilder() .SetBasePath(Environment.CurrentDirectory) .AddXmlFile("appSettings.xml") .Build(); var info = configuration["username"]; Console.WriteLine(info); Console.ReadKey(); }
最后我们可以看到控制台上输入xml文件中的结果
三、Ini
1、要想加载ini文件中的数据,就必须要安装它所依赖的包,我们打开NuGet包管理器,搜索并安装 Microsoft.Extensions.Configuration.Ini
2、我们在项目中新增一个 appSettings.ini文件,并且设置始终复制到输出目录
3、接下来我们看以下代码:
static void Main(string[] args) { IConfiguration configuration = new ConfigurationBuilder() .SetBasePath(Environment.CurrentDirectory) .AddIniFile("appSettings.ini") .Build(); var info = configuration["[user] username"]; Console.WriteLine(info); Console.ReadKey(); }
最后我们可以看到控制台上输入ini文件中的结果
四、Memory
1、要想加载MemoryCollection中的数据,就必须要安装它所依赖的包,我们打开NuGet包管理器,搜索并安装 Microsoft.Extensions.Configuration 由于以上数据源安装的时候的包都依赖于它,所有这里不需要安装
2、接下来看代码:
static void Main(string[] args) { List<KeyValuePair<string, string>> initialData = new List<KeyValuePair<string, string>>(); initialData.Add(new KeyValuePair<string, string>("username", "tom")); IConfiguration configuration = new ConfigurationBuilder() .SetBasePath(Environment.CurrentDirectory) .AddInMemoryCollection(initialData) .Build(); var info = configuration["username"]; Console.WriteLine(info); Console.ReadKey(); }
最后得出结果tom
五、CommandLine
目录还没用过,待研究
六、EnviromentVariables
这个是从环境变量中获取值
1、我们打开NuGet包管理器,搜索并安装 Microsoft.Extensions.Configuration.EnvironmentVariables
2、打开你的电脑,右键属性,选择高级,选择环境变量,随便复制一个环境变量名
3、然后将你复制的变量名作为你要获取该环境变量值的Key
4、以下代码:
static void Main(string[] args) { IConfiguration configuration = new ConfigurationBuilder() .SetBasePath(Environment.CurrentDirectory) .AddEnvironmentVariables() .Build(); var info = configuration["ASPNETCORE_ENVIRONMENT"]; Console.WriteLine(info); Console.ReadKey(); }
以AddJsonFile这个方法为例,我们可以看出,这个方法有多个重载:
public static IConfigurationBuilder AddJsonFile(this IConfigurationBuilder builder, string path);
public static IConfigurationBuilder AddJsonFile(this IConfigurationBuilder builder, string path, bool optional); public static IConfigurationBuilder AddJsonFile(this IConfigurationBuilder builder, string path, bool optional, bool reloadOnChange);
optional这个参数表示这个文件是否是可选的,reloadOnChange这个表示文件改变时,是否重新加载这个文件(热加载)
reloadOnChange=true时,项目在运行,获取到username这个值为tom,当我们从json文件中改变username的值为lucy时,项目读取它的值也会立马发生改变
七、弱类型读取
以上获取json文件中的数据都是一维的,那么二维,三维,多维的时候我们该怎么获取呢?
接下来我们调试下,看看最终得到的IConfiguration里面是什么样子的,我在json文件中写了一个person数组
1、用:运算符的方式获取想要的数据
我们可以看出,数据是Key,Value类型的,是不是只要我们根据前面的key就可以获取后面的 Value呢?
static void Main(string[] args) { IConfiguration configuration = new ConfigurationBuilder() .SetBasePath(Environment.CurrentDirectory) .AddJsonFile("appSettings.json") .Build(); var info = configuration["person:0:name"]; Console.WriteLine(info); Console.ReadKey(); }
结果:
2、使用GetSection ()方法进行获取
static void Main(string[] args) { IConfiguration configuration = new ConfigurationBuilder() .SetBasePath(Environment.CurrentDirectory) .AddJsonFile("appSettings.json") .Build(); var info = configuration.GetSection("person").GetSection("0").GetSection("name").Value; var info1 = configuration.GetSection("person").GetSection("0")["name"]; Console.WriteLine(info); Console.WriteLine(info1); Console.ReadKey(); }
结果如下:
八、强类型读取
安装 Microsoft.Extensions.Configuration.Binder 包
1、GetValue<T>
static void Main(string[] args) { IConfiguration configuration = new ConfigurationBuilder() .SetBasePath(Environment.CurrentDirectory) .AddJsonFile("appSettings.json") .Build(); var info = configuration.GetValue<string>("username"); Console.WriteLine(info); Console.ReadKey(); } }
结果如下:
2、Bind()
public class Rootobject { public string username { get; set; } public Person[] person { get; set; } } public class Person { public string id { get; set; } public string name { get; set; } } static void Main(string[] args) { IConfiguration configuration = new ConfigurationBuilder() .SetBasePath(Environment.CurrentDirectory) .AddJsonFile("appSettings.json") .Build(); Rootobject rootobject = new Rootobject(); configuration.Bind(rootobject); Console.WriteLine(rootobject.username); Console.ReadKey(); }
结果如下:
3、Get<T>()
static void Main(string[] args) { IConfiguration configuration = new ConfigurationBuilder() .SetBasePath(Environment.CurrentDirectory) .AddJsonFile("appSettings.json") .Build(); Rootobject rootobject=configuration.Get<Rootobject>(); Console.WriteLine(rootobject.username); Console.ReadKey(); }
结果如下:
那么Bind()和Get<T>()有什么区别呢?
通过源码分析这两个方法,主要区别在于,Get<T>()方法主要用到了反射,通过反射创建T的一个对象返回