19

我正在关注ASP.NET 5 的一些示例,但我对如何正确读取“嵌套”配置值(如果这是正确的术语)感到困惑。

以下是相关部分config.json

{
    "ApplicationName" : "OwNextApp",
    "AppSettings": {
        "SiteTitle": "OwNext"
    },
}

和相关部分HomeController.cs

public IActionResult About()
{
    var appNestedNameFailed = _config.Get("AppSettings.SiteTitle");
    var appNestedNameSuccess = _config.Get("AppSettings:SiteTitle");
    var appName = _config.Get("ApplicationName");
    ViewBag.Message = string.Format(@"Your 
        APP NAME: {0};
        APP NESTED NAME FAILED: {1}; 
        APP NESTED NAME SUCCESS: {2}", 
            appName, appNestedNameFailed, appNestedNameSuccess);

    return View();
}

值为appNestedNameFailed空(我在研究之前的初步尝试)。并appNestedNameSuccess具有价值;在我进行了研究并在配置测试中发现之后(显示了相关代码):

// Assert
Assert.Equal("IniValue1", config.Get("IniKey1"));
Assert.Equal("IniValue2", config.Get("IniKey2:IniKey3"));

有人可以解释为什么会这样吗?为什么使用:over有意义.?从我与 JSON 数据的交互来看,通常.符号可以正常工作,例如How to access nested json data

此外,我发现了类似的SO 问题,但这并没有解释为什么:选择。

4

3 回答 3

18

这是我们第一次创建配置模型时决定的约定。我们从 json 开始,并且:是那里的分隔符。

无论如何,如果您不想担心这些约定,我建议使用将配置绑定到模型(强类型对象)的 ConfigurationBinder。以下是 GitHub上可以作为示例的测试。

于 2015-05-20T03:47:18.013 回答
12
using Microsoft.Extensions.Configuration;
using System.IO;

IConfigurationRoot configuration = new ConfigurationBuilder()
                .SetBasePath(Directory.GetCurrentDirectory())
                .AddJsonFile("appsettings.json")
                .Build();

var connectionString = configuration.GetValue<string>("ConnectionStrings:DefaultConnection");

// or

var connectionString2= configuration.GetSection("ConnectionStrings").GetSection("DefaultConnection").Value;  

appsettings.json:

{
  "ConnectionStrings": {
    "DefaultConnection": "myconnection"
  },
}
于 2020-04-08T10:39:31.937 回答
1

深入了解JsonConfigurationFileParser源的内部,并责备以下进入/退出方法:

private void VisitJObject(JObject jObject)
{
    foreach (var property in jObject.Properties())
    {
        EnterContext(property.Name);
        VisitProperty(property);
        ExitContext();
    }
}

private void EnterContext(string context)
{
    _context.Push(context);
    _currentPath = string.Join(":", _context.Reverse());
}

private void ExitContext()
{
    _context.Pop();
    _currentPath = string.Join(":", _context.Reverse());
}

似乎 ASP.NET 团队应该留下更多有启发性的签入评论:)。

我最好的猜测是 config.json 文件中可能存储了需要在.其中包含的数据,而:不太常见。例如:

"AppSettings": {
    "Site.Title": "Is .NET getting faster?"
},

这是一个不好的例子,但他们希望尽可能“安全”并使用超出规范的东西似乎是合理的。如果您想存储类型的全名,那也会稍微容易一些,而无需担心杂散期。

"AppSettings": {
    "ImportantTypeName": "WebApp.CoolStuff.Helpers.AwesomeClass"
},
于 2015-05-20T03:05:02.373 回答