在启动文件中,我需要一种方式来访问另一个项目中的IConfiguration。有人告诉我业务逻辑不应该知道IConfiguration。如果是这样,那么我如何将appsettings中的数据注入到业务逻辑项目中呢。
appsettings.json
{
"AdminEmail": "myemail@gmail.com"
}
如何在我创建的类库中访问同一解决方案中的AdminEmail?
在启动文件中,我需要一种方式来访问另一个项目中的IConfiguration。有人告诉我业务逻辑不应该知道IConfiguration。如果是这样,那么我如何将appsettings中的数据注入到业务逻辑项目中呢。
appsettings.json
{
"AdminEmail": "myemail@gmail.com"
}
如何在我创建的类库中访问同一解决方案中的AdminEmail?
定义一个设置模型
public sealed class EmailSettings
{
public string AdminEmail { get; set; }
}
配置设置
public sealed class Startup
{
private readonly IConfiguration configuration;
public Startup(IConfiguration configuration) => this.configuration = configuration;
public void ConfigureServices(IServiceCollection services)
{
services
.Configure<EmailSettings>(configuration)
.AddSingleton(sp => sp.GetRequiredService<IOptions<EmailSettings>>().Value);
}
}
注入并使用它
public class ClassLibraryInTheSameSolution
{
public ClassLibraryInTheSameSolution(EmailSettings emailSettings)
{
}
}
EmailSettings
, 因为该类型在构造函数public ClassLibraryInTheSameSolution(EmailSettings emailSettings)
中被使用。只需在类库项目或其他单独的项目(例如Infrastructure.Settings)中定义类EmailSettings
即可。 - Andriy TolstoyClassLibraryInTheSameSolution(EmailSettings emailSettings) { }
将隐藏没有参数的默认构造函数。这就是为什么您在尝试使用它时会出现错误的原因。 - Andriy TolstoyMicrosoft.Extensions.Configuration
来实现此目的。详见 https://learn.microsoft.com/en-us/aspnet/core/fundamentals/configuration/?tabs=basicconfiguration。
1 - 为设置创建一个模型
public class AppSettings
{
public string AdminEmail { get; set; }
}
2 - Configure it on Startup.cs
services.Configure<AppSettings>(Configuration);
第三步 - 在类库中使用 DI 获取设置
private readonly AppSettings _appSettings;
public MyClass(IOptions<AppSettings> appSettings)
{
_appSettings = appSettings.Value;
}
public class EmailSettings
{
public string AdminEmail { get; set; } // encapsulate as needed
}
public void ConfigureServices(IServiceCollection services)
{
var settings = new EmailSettings
{
AdminEmail = Configuration["AdminEmail"]
};
services.AddSingleton(settings);
}
public class WhereverYouNeedThis
{
private readonly EmailSettings _emailSettings;
public WhereverYouNeedThis(EmailSettings emailSettings)
{
_emailSettings = emailSettings;
}
public void Use()
{
Debug.Log(_emailSettings.AdminEmail);
}
}
这个辅助类提供者:
public class AppSettings
{
private static AppSettings _appSettings;
public string appSettingValue { get; set; }
public static string Get(string Key)
{
_appSettings = GetCurrentSettings(Key);
return _appSettings.appSettingValue;
}
public AppSettings(IConfiguration config, string Key)
{
this.appSettingValue = config.GetValue<string>(Key);
}
public static AppSettings GetCurrentSettings(string Key)
{
var builder = new ConfigurationBuilder()
.SetBasePath(Directory.GetCurrentDirectory())
.AddJsonFile("appsettings.json", optional: false, reloadOnChange: true)
.AddEnvironmentVariables();
IConfigurationRoot configuration = builder.Build();
var settings = new AppSettings(configuration, Key);
return settings;
}
}
要使用该帮助程序,您应该安装所有这些包:
Microsoft.Extensions.Configuration
Microsoft.Extensions.Configuration.Binder
Microsoft.Extensions.Configuration.EnvironmentVariables
Microsoft.Extensions.Configuration.FileExtensions
Microsoft.Extensions.Configuration.Json
以下是如何在您的代码中使用它的示例:
AppSettings.Get("SomeKey");
AppSettings.Get("Redis:Host");
AppSettings.Get("ConnectionString:mssql");
IConfiguration
来指定应将哪些部分重新注入到哪些对象中。如果您想使用DI填充配置设置,则需要将它们包装到IOption<>中。另一方面,如果您只是将设置作为普通旧对象注入,则只有主项目需要处理IConfiguration。 - Panagiotis KanavosEmailSettings
。如果您只想传递一个EmailSettings
类,为什么要模拟或启动整个中间件呢? - Panagiotis Kanavos