ASP.NET Core支持很多不同的配置选项。应用程序配置数据可以来自于JSON,XML和INI格式的文件,以及来自环境变量或者内存中的集合。

ASP.NET Core的配置系统在以前ASP.NET版本的基础上进行了重构。新的配置模型提供了可从各种来源获取基于键值对设置的简化访问。

在ASP.NET应用程序里面,建议在应用程序的Startup类中只实例化一个Configuration实例。然后,使用选择模式来访问各自的设置。Configuration只是一个提供了读写名/值对的一个集合。

使用内置提供程序

配置框架已经内置对JSON,XML和INI配置文件的支持,以及对内存配置的支持(直接通过代码设置值)和从环境变量和命令行参数摘取配置的能力。

通过扩展方法可以实现对添加额外的配置提供程序的支持。这些方法可以在ConfigurationBuilder实例上以单独的或者链式方式进行调用。

// work with with a builder using multiple calls
var builder = new ConfigurationBuilder();
builder.SetBasePath(Directory.GetCurrentDirectory());
builder.AddJsonFile("appsettings.json");
var connectionStringConfig = builder.Build();

// chain calls together as a fluent API
var config = new ConfigurationBuilder()
    .SetBasePath(Directory.GetCurrentDirectory())
    .AddJsonFile("appsettings.json")
    .AddEntityFrameworkConfig(options =>
        options.UseSqlServer(connectionStringConfig.GetConnectionString("DefaultConnection"))
    )
    .Build();

在配置程序中指定的顺序是很重要的,如果存在于多个位置的话会影响设置被应用的优先级。下面的代码,如果相同的设置存在于appsettings.json和环境变量中,环境变量中的设置最终会被使用。如果一个设置存在于多个位置,那么最后指定的配置提供程序将“获胜”。

ASP.NET团队建议最后指定环境变量,这样本地环境就可以覆盖任何部署在配置文件中的设置,这对于指定环境的配置文件非常有用,这可以通过如下代码实现:

public Startup(IHostingEnvironment env)
{
    var builder = new ConfigurationBuilder()
        .SetBasePath(env.ContentRootPath)
        .AddJsonFile("appsettings.json", optional: true, reloadOnChange: true)
        .AddJsonFile($"appsettings.{env.EnvironmentName}.json", optional: true);  //<====

    if (env.IsDevelopment())
    {
        // For more details on using the user secret store see http://go.microsoft.com/fwlink/?LinkID=532709
        builder.AddUserSecrets();
    }

    builder.AddEnvironmentVariables();
    Configuration = builder.Build();
}

IHostingEnvironment服务用于获取当前环境。在Development环境中,上面的代码将查找一个名为appsettings.Development.json的文件,并使用这里面的值覆盖其它地方设置的值。

使用选项和配置对象

通过选择模式可将任何自定义的类转换成一个相关配置的组。一个类要作为选项类,那么类中每个配置要有一个对应的公开可读写属性和一个没有任何参数的构造函数。建议你创建与应用程序中某些功能相对应的良好构造的配置对象,因此遵循接口分离原则(Interface Segregation Principle,ISP)和关注分离(Separation of Concerns,SoC)。

一个简单的MyOptions类:

public class MyOptions
{
    public string Option1 { get; set; }
    public int Option2 { get; set; }
}

通过使用IOptions<TOptions>访问服务可以将选项注入到你的应用中。比如,下面的Controller将使用IOptions<MyOptions>来访问需要在Index视图中渲染的配置:

public class HomeController : Controller
{
    private readonly IOptions<MyOptions> _optionsAccessor;

    public HomeController(IOptions<MyOptions> optionsAccessor)
    {
        _optionsAccessor = optionsAccessor;
    }

    // GET: /<controller>/
    public IActionResult Index() => View(_optionsAccessor.Value);
}

你需要在启动期间ConfigureServices方法内调用AddOptions扩展方法来设置IOptions<TOptions>服务:

public void ConfigureServices(IServiceCollection services)
{
    // Setup options with DI
    services.AddOptions();
}

配置选项可以通过使用Configure<TOptions>扩展方法:

public void ConfigureServices(IServiceCollection services)
{
    // Setup options with DI
    services.AddOptions();

    // Configure MyOptions using config by installing Microsoft.Extensions.Options.ConfigurationExtensions
    // services.Configure<MyOptions>(Configuration);

    // Configure MyOptions using code
    services.Configure<MyOptions>(options =>
    {
        options.Option1 = "value1_from_action";
        options.Option2 = 10;
    });
}

在打开相应的Index.cshtml文件:

@using MyFirstApp.Models
@model MyOptions

<h1>Options</h1>
<p>
    <b>Option1:</b>
    @Model.Option1
</p>
<p>
    <b>Option2:</b>
    @Model.Option2
</p>

最终的显示效果:

每一次调用Configure<TOptions>将添加一个IConfigureOptions<TOptions>服务到服务容器,是为了通过IOptions<TOptions>服务来提供一个配置选项给应用程序或者框架。

总结

ASP.NET Core提供了一个非常灵活的配置模型,支持多种不同基于文件的选项以及命令行,内存和环境变量。它能配置模型无缝协作,因此你可以为你的应用程序或者框架注入强类型配置。

原文链接

Configuration

个人博客

我的个人博客