【问题标题】:Accessing settings from appsettings.json from class library in Core 2.0从 Core 2.0 的类库中访问 appsettings.json 中的设置
【发布时间】:2017-10-09 20:14:15
【问题描述】:

我在这里阅读了十几个关于 SO 的问题和至少 4 篇博客文章,但我无法让它在具有多个类库项目的 VS2017 解决方案中工作。但是,我可以让它与一个带有 Web 应用程序和一个类库的解决方案一起工作,尽管它的模式与我在文档和 SO 上找到的模式不同。

我的解决方案包含 5 个项目:WebApplication、Testing、Infrastructure、Services、Domain(后三个是类库)。

在基础设施项目中,我创建了一个名为 EmailConfigurationSettings 的类,并将其注册到 WebApp 的 StartUp 类中。

这个类在类库中:

public class EmailConfigurationSettings
{
    public string Provider { get; set; }
    public string Username { get; set; }
    public string Password { get; set; }
}

这是在 WebApp 的 StartUp.cs 中:

services.Configure<EmailConfigurationSettings>(Configuration.GetSection("EmailConfigurationSettings"));
services.AddOptions();

appsettings.json

"EmailConfigurationSettings": {
  "Provider": "gmail",
  "Username": "user@gmail.com",
  "Password": "mypassword" 
} 

我需要服务项目中的设置。但现在我只是想确保我能真正检索到它们。下面的代码遵循我找到但生成的所有代码示例:

public class LoadEmailSettingsFromAppSettings
{
    private readonly IOptions<EmailConfigurationSettings> _emailSettings;

    public LoadEmailSettingsFromAppSettings(IOptions<EmailConfigurationSettings> emailSettings)
    {
        _emailSettings = emailSettings;
        Message = "Our provider is " + _emailSettings.Value.Provider;
    }

    public string Message { get; set; }
}

_emailSettings 始终为空

所以我尝试在 TestProject 中对其进行测试:

IOptions<EmailConfigurationSettings> someOptions = Options.Create<EmailConfigurationSettings>(new EmailConfigurationSettings());

嗯,那也是空的。

在另一种解决方案中,带有 WebApp 和一个类库的解决方案, 使用我在其中一个博客上发现的稍微不同的模式,我实际上可以从 appsettings.json 中检索值:

public class AuthMessageSender : IEmailSender, ISmsSender
{
    public AuthMessageSender(IOptions<EmailConfig> emailSettings)
    {
        _emailSettings = emailSettings.Value;
    }

    public EmailConfig _emailSettings { get; }

    public Task SendEmailAsync(string email, string subject, string message)
    {
        Execute(email, subject, message).Wait();
        return Task.FromResult(0);
    }

请注意,IOptions 类与 9 个属性不同,但构造方式与上述模式相同。

但是使用这种模式在多类库项目中起作用。我如何理解如何让它在多类库场景中工作?

我不知道他们为什么放弃 ConfigurationManager,这要容易得多。

【问题讨论】:

    标签: c# json asp.net-core-2.0 appsettings


    【解决方案1】:

    在微服务中,您可以简单地绑定到与 json 定义匹配的新对象。所以你会的。

    var emailConfig = new EmailConfigurationSettings();
    Configuration.GetSection("EmailConfigurationSettings").Bind(emailConfig);
    services.AddSingleton(emailConfig);
    

    完成此操作后,您所要做的就是在服务层构造函数中请求一份 EmailConfigurationSettings 的副本。这将为您提供该对象的依赖注入单例。

    我会在“绑定”上设置一个断点并确保填充电子邮件配置。

    【讨论】:

    • 运行项目并在 AddSingleton 调用上放置一个断点(在 StartUp.cs 中)会产生一个空 emailConfig。所以这不起作用,与OP方法相同。
    • 如果产生空结果,那么他没有正确加载他的应用程序配置。此代码取自我的个人 mvc 应用程序,因此我知道它有效。如果您将变量设置为 getsection 的返回值,我将返回 null
    【解决方案2】:

    这是一个关于类库的有趣答案:Class library

    在这部分代码中:

    private readonly IOptions<EmailConfigurationSettings> _emailSettings;
    
    public LoadEmailSettingsFromAppSettings(IOptions<EmailConfigurationSettings> emailSettings)
    {
        _emailSettings = emailSettings;         
    

    依赖注入不起作用,因为你在一个类库中,所以你应该保持这种状态。

    在您的 web 应用程序中的某个位置构建 LoadEmailSettingsFromAppSettings

    public class SomeClass
    {
        public SomeClass(IOptions<EmailConfigurationSettings> emailSettings) // dependency injection works in your webapp
        {
            var loadEmail = new LoadEmailSettingsFromAppSettings(emailSettings); // send EmailSettings to your other class in your class library
    
            //(...)
        }
    }
    

    私有只读应该是:

    public IOptions<EmailConfigurationSettings> EmailSettings {get; private set;}
    

    readonly vs get/set properties

    我希望是清晰和有帮助的

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2021-11-12
      • 2017-12-15
      • 1970-01-01
      • 2017-10-22
      • 2020-09-04
      相关资源
      最近更新 更多