虽然有些晚了,但在阅读了所有有用的答案和评论后,我最终使用了Microsoft.Extensions.Configuration.Binder扩展包,并做了一些调整来摆脱硬编码的配置键。
我的解决方案:
IConfigSection.cs
public interface IConfigSection
{
}
ConfigurationExtensions.cs
public static class ConfigurationExtensions
{
public static TConfigSection GetConfigSection<TConfigSection>(this IConfiguration configuration) where TConfigSection : IConfigSection, new()
{
var instance = new TConfigSection();
var typeName = typeof(TConfigSection).Name;
configuration.GetSection(typeName).Bind(instance);
return instance;
}
}
appsettings.json
{
"AppConfigSection": {
"IsLocal": true
},
"ConnectionStringsConfigSection": {
"ServerConnectionString":"Server=.;Database=MyDb;Trusted_Connection=True;",
"LocalConnectionString":"Data Source=MyDb.db",
},
}
要访问强类型配置,您只需要创建一个类来实现接口(注意:类名和字段名应与中的部分完全匹配)。
AppConfigSection.cs
public class AppConfigSection: IConfigSection
{
public bool IsLocal { get; set; }
}
ConnectionStringsConfigSection.cs
public class ConnectionStringsConfigSection : IConfigSection
{
public string ServerConnectionString { get; set; }
public string LocalConnectionString { get; set; }
public ConnectionStringsConfigSection()
{
ServerConnectionString = string.Empty;
LocalConnectionString = string.Empty;
}
}
最后,一个使用示例:
Startup.cs
public class Startup
{
public Startup(IConfiguration configuration)
{
Configuration = configuration;
}
public IConfiguration Configuration { get; }
public void ConfigureServices(IServiceCollection services)
{
var app = Configuration.GetConfigSection<AppConfigSection>();
var connectionStrings = Configuration.GetConfigSection<ConnectionStringsConfigSection>();
services.AddDbContext<AppDbContext>(options =>
{
if (app.IsLocal)
{
options.UseSqlite(connectionStrings.LocalConnectionString);
}
else
{
options.UseSqlServer(connectionStrings.ServerConnectionString);
}
});
}
}
为了使代码整洁,您可以将上述代码移入扩展方法中。
就这样,没有硬编码的配置键。