我正在尝试为我的应用程序提供一些配置数据,以便我们在源代码管理中存储简单的设置,但是我们的部署系统将在部署时替换appsettings.json中的加密密钥。
对于开发我仍然需要一个通用密钥,但对于他们秘密中的特定用户,我想提供一个他们可以肯定是安全的值。
我的配置文件设置如下:
appsettings.json
{
"SystemConfiguration" : {
"EncryptionKey" : "weak"
}
}
appsettings.Development.json
{
"SystemConfiguration" : {
"EncryptionKey" : "devweak"
}
}
在我的用户机密
{
"SystemConfiguration" : {
"EncryptionKey" : "this is a secret"
}
}
在我的控制器构造中,我得到注入的IConfiguration configuration
。
然后
public SysConfigController(IConfiguration configuration)
{
var result = configuration["SystemConfiguration:EncryptionKey"];
}
但是结果的值总是“弱”,除非更高级别的设置文件根本不包含该值(: null
)也不起作用。
有没有办法可以检索最低级别的值?
似乎您的配置注册错误。将使用包含特定密钥的最后一次注册。
例如,在Program.cs
文件中(假设您使用的是ASP.NET Core,否则是Startup.cs
的ASP.NET Core 1.x构造函数),您可以覆盖注册(或者只是在使用默认主机构建器方法时添加您喜欢的注册) :
public static IWebHostBuilder BuildWebHost(string[] args) =>
new WebHostBuilder()
.UseKestrel()
.UseContentRoot(Directory.GetCurrentDirectory())
.ConfigureAppConfiguration((hostingContext, config) =>
{
var env = hostingContext.HostingEnvironment;
config
.AddJsonFile("appsettings.json", optional: true, reloadOnChange: true)
.AddJsonFile($"appsettings.{env.EnvironmentName}.json", optional: true)
.AddUserSecrets<Startup>()
.AddEnvironmentVariables()
.AddCommandLine(args);
})
.UseIISIntegration()
.UseStartup<Startup>()
.UseApplicationInsights();
在此示例中,已注册以下内容
.AddJsonFile("appsettings.json", optional: true, reloadOnChange: true)
:全局配置文件.AddJsonFile($"appsettings.{env.EnvironmentName}.json", optional: true)
Enviornments特定配置文件,即appsettings.Development.json
.AddUserSecrets<Startup>()
用户的秘密.AddEnvironmentVariables()
环境变量.AddCommandLine(args);
命令行参数在查找密钥时,搜索以相反的顺序进行。如果将其定义为命令行参数,它将覆盖所有其他键和值(来自环境变量,用户机密,特定于环境和全局文件)。
因此,将最不重要的文件放在开头,最重要的是(覆盖)最后一个。
在这种情况下,如果它在您的用户机密中定义,它将覆盖appsettings.Development.json
和appsettings.json
提供的值。
来自the docs
配置源按启动时指定其配置提供程序的顺序读取。本主题中描述的配置提供程序按字母顺序进行描述,而不是按照代码排列顺序进行描述。在代码中订购配置提供程序以满足底层配置源的优先级。
典型的配置提供程序序列是:
- 文件(appsettings.json,appsettings..json,应用程序当前的托管环境在哪里)
- 用户机密(秘密管理员)(仅限开发环境)
- 环境变量
- 命令行参数
通常的做法是将命令行配置提供程序最后放在一系列提供程序中,以允许命令行参数覆盖其他提供程序设置的配置。
您可以在Startup.cs中使用方法ConfigureServices(IServiceCollection services)
。
在课堂上描述你的设置属性并绑定它。例如:
services.Configure<SystemConfiguration>(options => Configuration.GetSection("SystemConfiguration").Bind(options));
public class SystemConfiguration
{
public string EncryptionKey{get;set;}
}
然后,您可以使用DI来上课
public class SomeClass
{
private readonly SystemConfiguration _systemConfiguration{get;set;}
public SomeClass (IOptions<ConfigExternalService> systemConfiguration)
{
_systemConfiguration = systemConfiguration;
}
}