.NET 中的設定提供者

.NET 的設定可用設定提供者來進行。 不同類型的提供者需要各式各樣的設定來源。 本文會詳細說明各種不同的設定提供者和其對應的來源。

檔案設定提供者。

FileConfigurationProvider 是用於從檔案系統載入設定的基底類別。 下列設定提供者衍生自 FileConfigurationProvider

金鑰不區分大小寫。 在單一提供者中找到重複的索引鍵時,所有檔案設定提供者都會擲回 FormatException

JSON 設定提供者

類別 JsonConfigurationProvider 會從 JSON 檔案載入設定。 安裝 Microsoft.Extensions.Configuration.Json NuGet 套件。

多載可以指定:

  • 檔案是否為選擇性。
  • 檔案變更時是否要重新載入設定。

請考慮下列程式碼:

using Microsoft.Extensions.Configuration;
using Microsoft.Extensions.Hosting;
using ConsoleJson.Example;

HostApplicationBuilder builder = Host.CreateApplicationBuilder(args);

builder.Configuration.Sources.Clear();

IHostEnvironment env = builder.Environment;

builder.Configuration
    .AddJsonFile("appsettings.json", optional: true, reloadOnChange: true)
    .AddJsonFile($"appsettings.{env.EnvironmentName}.json", true, true);

TransientFaultHandlingOptions options = new();
builder.Configuration.GetSection(nameof(TransientFaultHandlingOptions))
    .Bind(options);

Console.WriteLine($"TransientFaultHandlingOptions.Enabled={options.Enabled}");
Console.WriteLine($"TransientFaultHandlingOptions.AutoRetryDelay={options.AutoRetryDelay}");

using IHost host = builder.Build();

// Application code should start here.

await host.RunAsync();

上述 程式碼:

  • 清除 CreateApplicationBuilder(String[]) 方法中目前所有預設要新增的設定提供者。
  • 設定 JSON 設定提供者以載入具有下列選項的 appsettings.jsonappsettings.Environment.json 檔案:
    • optional: true:檔案為選擇性。
    • reloadOnChange: true:儲存變更時會重新載入該檔案。

重要

使用 IConfigurationBuilder.Add新增設定提供者時,新增的設定提供者會新增到 IConfigurationSource 清單結尾。 當有多個提供者找到金鑰時,最後一個讀取金鑰的提供者會覆寫先前的提供者。

具有各種組態設定的 appsettings.json 檔案範例如下:

{
    "SecretKey": "Secret key value",
    "TransientFaultHandlingOptions": {
        "Enabled": true,
        "AutoRetryDelay": "00:00:07"
    },
    "Logging": {
        "LogLevel": {
            "Default": "Information",
            "Microsoft": "Warning",
            "Microsoft.Hosting.Lifetime": "Information"
        }
    }
}

IConfigurationBuilder 執行個體新增設定提供者之後,您可以呼叫 IConfigurationBuilder.Build() 以取得 IConfigurationRoot 物件。 設定根目錄代表設定階層的根目錄。 設定中的區段可以繫結至物件 .NET 的執行個體,然後以 IOptions<TOptions> 的形式透過相依性插入提供。

注意

JSON 檔案的 [建置動作] 和 [複製到輸出目錄] 屬性必須分別設定為 [內容] 和 [有更新時才複製 (或一律複製)]

請考慮定義如下的 TransientFaultHandlingOptions 類別:

namespace ConsoleJson.Example;

public sealed class TransientFaultHandlingOptions
{
    public bool Enabled { get; set; }
    public TimeSpan AutoRetryDelay { get; set; }
}

下列程式碼會建置設定根目錄、將區段繫結至 TransientFaultHandlingOptions 類別,並在主控台視窗中列印繫結的值:

TransientFaultHandlingOptions options = new();
builder.Configuration.GetSection(nameof(TransientFaultHandlingOptions))
    .Bind(options);

Console.WriteLine($"TransientFaultHandlingOptions.Enabled={options.Enabled}");
Console.WriteLine($"TransientFaultHandlingOptions.AutoRetryDelay={options.AutoRetryDelay}");

應用程式會寫入以下輸出範例:

// Sample output:
//    TransientFaultHandlingOptions.Enabled=True
//    TransientFaultHandlingOptions.AutoRetryDelay=00:00:07

XML 設定提供者

類別 XmlConfigurationProvider 會在執行階段內從 XML 檔案載入設定。 安裝 Microsoft.Extensions.Configuration.Xml NuGet 套件。

下列程式碼示範如何用 XML 設定提供者來設定 XML 檔案。

using Microsoft.Extensions.Configuration;
using Microsoft.Extensions.Hosting;

HostApplicationBuilder builder = Host.CreateApplicationBuilder(args);

builder.Configuration.Sources.Clear();

builder.Configuration
    .AddXmlFile("appsettings.xml", optional: true, reloadOnChange: true)
    .AddXmlFile("repeating-example.xml", optional: true, reloadOnChange: true);

builder.Configuration.AddEnvironmentVariables();

if (args is { Length: > 0 })
{
    builder.Configuration.AddCommandLine(args);
}

using IHost host = builder.Build();

// Application code should start here.

await host.RunAsync();

上述 程式碼:

  • 清除 CreateApplicationBuilder(String[]) 方法中目前所有預設要新增的設定提供者。
  • 設定 XML 設定提供者以載入具有下列選項的 appsettings.xmlrepeating-example.xml 檔案:
    • optional: true:檔案為選擇性。
    • reloadOnChange: true:儲存變更時會重新載入該檔案。
  • 設定環境變數設定提供者。
  • 如果指定的 args 包含引數,請設定命令列設定提供者。

XML 設定會由環境變數設定提供者命令列設定提供者中的設定覆寫。

具有各種組態設定的 appsettings.xml 檔案範例如下:

<?xml version="1.0" encoding="utf-8" ?>
<configuration>
  <SecretKey>Secret key value</SecretKey>
  <TransientFaultHandlingOptions>
    <Enabled>true</Enabled>
    <AutoRetryDelay>00:00:07</AutoRetryDelay>
  </TransientFaultHandlingOptions>
  <Logging>
    <LogLevel>
      <Default>Information</Default>
      <Microsoft>Warning</Microsoft>
    </LogLevel>
  </Logging>
</configuration>

提示

若要在WinForms 應用程式中使用 IConfiguration 類型,請在 Microsoft.Extensions.Configuration.Xml NuGet 套件中新增參考。 具現化 ConfigurationBuilder 和對 AddXmlFileBuild() 的鏈結呼叫。 如需詳細資訊,請參閱 .NET 文件問題 #29679

在 .NET 5 和更早版本中,請新增 name 屬性以分辨使用相同元素名稱的重複項目。 在 .NET 6 和更新版本中,XML 設定提供者會自動為重複項目編制索引。 這表示您不需要指定 name 屬性,除非您只有一個項目而且希望索引鍵中有索引「0」。 (如果您要升級至 .NET 6 或更新版本,可能會發生因此行為變更所造成的中斷。如需詳細資訊,請參閱重複的 XML 元素包含索引。)

<?xml version="1.0" encoding="UTF-8"?>
<configuration>
  <section name="section0">
    <key name="key0">value 00</key>
    <key name="key1">value 01</key>
  </section>
  <section name="section1">
    <key name="key0">value 10</key>
    <key name="key1">value 11</key>
  </section>
</configuration>

下列程式碼會讀取先前的設定檔,並顯示機碼與值:

IConfigurationRoot configurationRoot = builder.Configuration;

string key00 = "section:section0:key:key0";
string key01 = "section:section0:key:key1";
string key10 = "section:section1:key:key0";
string key11 = "section:section1:key:key1";

string? val00 = configurationRoot[key00];
string? val01 = configurationRoot[key01];
string? val10 = configurationRoot[key10];
string? val11 = configurationRoot[key11];

Console.WriteLine($"{key00} = {val00}");
Console.WriteLine($"{key01} = {val01}");
Console.WriteLine($"{key10} = {val10}");
Console.WriteLine($"{key10} = {val11}");

應用程式會撰寫下列輸出範例:

// Sample output:
//    section:section0:key:key0 = value 00
//    section:section0:key:key1 = value 01
//    section:section1:key:key0 = value 10
//    section:section1:key:key0 = value 11

屬性可用來提供值:

<?xml version="1.0" encoding="UTF-8"?>
<configuration>
  <key attribute="value" />
  <section>
    <key attribute="value" />
  </section>
</configuration>

先前的設定檔會使用 value 載入下列機碼:

  • key:attribute
  • section:key:attribute

INI 設定提供者

類別 IniConfigurationProvider 會在執行階段內從 INI 檔案載入設定。 安裝 Microsoft.Extensions.Configuration.Ini NuGet 套件。

下列程式碼會清除所有設定提供者,並以兩個 INI 檔案作為來源新增 IniConfigurationProvider

using Microsoft.Extensions.Configuration;
using Microsoft.Extensions.Hosting;

HostApplicationBuilder builder = Host.CreateApplicationBuilder(args);
builder.Configuration.Sources.Clear();

IHostEnvironment env = builder.Environment;

builder.Configuration
    .AddIniFile("appsettings.ini", optional: true, reloadOnChange: true)
    .AddIniFile($"appsettings.{env.EnvironmentName}.ini", true, true);

using IHost host = builder.Build();

// Application code should start here.

await host.RunAsync();

具有各種組態設定的 appsettings.ini 檔案範例如下:

SecretKey="Secret key value"

[TransientFaultHandlingOptions]
Enabled=True
AutoRetryDelay="00:00:07"

[Logging:LogLevel]
Default=Information
Microsoft=Warning

下列程式碼會將上述組態設定寫入主控台視窗以顯示:

foreach ((string key, string? value) in
    builder.Configuration.AsEnumerable().Where(t => t.Value is not null))
{
    Console.WriteLine($"{key}={value}");
}

應用程式會撰寫下列輸出範例:

// Sample output:
//    TransientFaultHandlingOptions:Enabled=True
//    TransientFaultHandlingOptions:AutoRetryDelay=00:00:07
//    SecretKey=Secret key value
//    Logging:LogLevel:Microsoft=Warning
//    Logging:LogLevel:Default=Information

環境變數設定提供者

EnvironmentVariablesConfigurationProvider 會利用預設設定,在讀取 appsettings.jsonappsettings.Environment.json 和秘密管理員後,從環境變數機碼值組中載入設定。 因此,從環境讀取的索引鍵值會覆寫從 appsettings.jsonappsettings.Environment.json 和秘密管理員讀取的值。

: 分隔符號不適用於所有平台上的環境變數階層式機碼。 例如,Bash 不支援 : 分隔符號。 所有平台皆支援的雙底線 (__) 會自動取代環境變數中的任何 : 分隔符號。

請考慮 TransientFaultHandlingOptions 類別:

public class TransientFaultHandlingOptions
{
    public bool Enabled { get; set; }
    public TimeSpan AutoRetryDelay { get; set; }
}

下列 set 命令會設定 SecretKeyTransientFaultHandlingOptions 的環境索引鍵和值。

set SecretKey="Secret key from environment"
set TransientFaultHandlingOptions__Enabled="true"
set TransientFaultHandlingOptions__AutoRetryDelay="00:00:13"

這些環境設定只會在從其所設定命令視窗啟動的處理序中進行設定。 它們不會由使用 Visual Studio 啟動的 Web 應用程式讀取。

使用 Visual Studio 2019 和更新版本時,您可以使用 [啟動設定檔] 對話來指定環境變數。

Launch Profiles dialog showing environment variables

下列 setx 命令也可用來在 Windows 上設定環境機碼與值。 不同於 setsetx 設定會予以保存。 /M 會在系統環境中設定該變數。 如果未使用 /M 切換開關,則會設定使用者環境變數。

setx SecretKey "Secret key from setx environment" /M
setx TransientFaultHandlingOptions__Enabled "true" /M
setx TransientFaultHandlingOptions__AutoRetryDelay "00:00:05" /M

若要測試上述命令是否可覆寫任何 appsettings.jsonappsettings.Environment.json 設定:

  • 使用 Visual Studio:結束並重新啟動 Visual Studio。
  • 使用 CLI:啟動新的命令視窗,然後輸入 dotnet run

首碼

若要指定環境變數的前置詞,請使用字串呼叫 AddEnvironmentVariables

using Microsoft.Extensions.Configuration;
using Microsoft.Extensions.Hosting;

HostApplicationBuilder builder = Host.CreateApplicationBuilder(args);

builder.Configuration.AddEnvironmentVariables(prefix: "CustomPrefix_");

using IHost host = builder.Build();

// Application code should start here.

await host.RunAsync();

在上述程式碼中:

  • config.AddEnvironmentVariables(prefix: "CustomPrefix_") 會在預設設定提供者之後新增。 如需有關排定設定提供者優先順序的範例,請參閱 XML 設定提供者
  • 使用 CustomPrefix_ 前置詞設定的環境變數會覆寫預設設定提供者。 這包括沒有前置詞的環境變數。

讀取設定機碼值組時,會移除前置詞。

預設設定會載入具有 DOTNET_ 前置詞的環境變數與命令列引數。 .NET 會為主機應用程式設定使用 DOTNET_ 前置詞,但不會為使用者設定使用。

如需主機與應用程式設定的詳細資訊,請參閱 .NET 泛型主機 (部分機器翻譯)。

連接字串前置詞

設定 API 具有四個連接字串環境變數的特殊處理規則。 這些連接字串涉及為應用程式環境設定 Azure 連接字串。 資料表中所顯示具有前置詞的環境變數會使用預設設定載入應用程式,或是當未提供任何前置詞給 AddEnvironmentVariables 時。

連接字串前置詞 Provider
CUSTOMCONNSTR_ 自訂提供者
MYSQLCONNSTR_ MySQL
SQLAZURECONNSTR_ Azure SQL Database
SQLCONNSTR_ SQL Server

當探索到具有下表所顯示之任何四個前置詞的環境變數並將其載入到設定中時:

  • 會透過移除環境變數前置詞並新增設定機碼區段 (ConnectionStrings) 來移除具有下表顯示之前置詞的環境變數。
  • 會建立新的設定機碼值組以代表資料庫連線提供者 (CUSTOMCONNSTR_ 除外,這沒有所述提供者)。
環境變數機碼 已轉換的設定機碼 提供者設定項目
CUSTOMCONNSTR_{KEY} ConnectionStrings:{KEY} 設定項目未建立。
MYSQLCONNSTR_{KEY} ConnectionStrings:{KEY} 機碼:ConnectionStrings:{KEY}_ProviderName
值:MySql.Data.MySqlClient
SQLAZURECONNSTR_{KEY} ConnectionStrings:{KEY} 機碼:ConnectionStrings:{KEY}_ProviderName
值:System.Data.SqlClient
SQLCONNSTR_{KEY} ConnectionStrings:{KEY} 機碼:ConnectionStrings:{KEY}_ProviderName
值:System.Data.SqlClient

launchSettings.json 中設定的環境變數

launchSettings.json 中設定的環境變數會覆寫系統環境的環境變數值。

Azure App Service 設定

Azure App Service 上,選取 [設定]>[組態] 頁面上的 [新增應用程式設定]。 Azure App Service 應用程式設定為:

  • 在待用及透過加密通道傳輸時加密。
  • 公開為環境變數。

命令列設定提供者

使用預設設定,CommandLineConfigurationProvider 會在下列設定來源之後,從命令列引數機碼值組載入設定:

  • appsettings.jsonappsettings.Environment.json 檔案。
  • Development 環境中的應用程式秘密 (秘密管理員)。
  • 環境變數。

根據預設,在命令列上設定的設定值會覆寫使用所有其他設定提供者設定的設定值。

使用 Visual Studio 2019 和更新版本時,您可以使用 [啟動設定檔] 對話來指定命令列引數。

Launch Profiles dialog showing command-line arguments

命令列引數

下列命令會使用 = 設定機碼與值:

dotnet run SecretKey="Secret key from command line"

下列命令會使用 / 設定機碼與值:

dotnet run /SecretKey "Secret key set from forward slash"

下列命令會使用 -- 設定機碼與值:

dotnet run --SecretKey "Secret key set from double hyphen"

機碼值:

  • 必須跟在 = 後面,或當值後面接著空格時,機碼必須有 --/ 前置詞。
  • 如果使用 =,則不是必要項。 例如: SomeKey=

在相同的命令中,請不要混用使用 = 的命令列引數機碼值組與使用空格的機碼值組。

每個檔案機碼設定提供者

KeyPerFileConfigurationProvider 使用目錄的檔案做為設定機碼值組。 機碼是檔案名稱。 值為檔案的內容。 每個檔案機碼設定提供者是在 Docker 裝載案例中使用。

若要啟用每個檔案機碼設定,請在 ConfigurationBuilder 的執行個體上呼叫 AddKeyPerFile 延伸模組方法。 檔案的 directoryPath 必須是絕對路徑。

多載允許指定:

  • 設定來源的 Action<KeyPerFileConfigurationSource> 委派。
  • 目錄是否為選擇性與目錄的路徑。

雙底線 (__) 是做為檔案名稱中的設定金鑰分隔符號使用。 例如,檔案名稱 Logging__LogLevel__System 會產生設定金鑰 Logging:LogLevel:System

建置主機時呼叫 ConfigureAppConfiguration 以指定應用程式的設定:

.ConfigureAppConfiguration((_, configuration) =>
{
    var path = Path.Combine(
        Directory.GetCurrentDirectory(), "path/to/files");

    configuration.AddKeyPerFile(directoryPath: path, optional: true);
})

記憶體設定提供者

MemoryConfigurationProvider 使用記憶體內集合做為設定機碼值組。

下列程式碼會將記憶體收集新增至設定系統:

using Microsoft.Extensions.Configuration;
using Microsoft.Extensions.Hosting;

HostApplicationBuilder builder = Host.CreateApplicationBuilder(args);

builder.Configuration.AddInMemoryCollection(
    new Dictionary<string, string?>
    {
        ["SecretKey"] = "Dictionary MyKey Value",
        ["TransientFaultHandlingOptions:Enabled"] = bool.TrueString,
        ["TransientFaultHandlingOptions:AutoRetryDelay"] = "00:00:07",
        ["Logging:LogLevel:Default"] = "Warning"
    });

using IHost host = builder.Build();

// Application code should start here.

await host.RunAsync();

在上述程式碼中,MemoryConfigurationBuilderExtensions.AddInMemoryCollection(IConfigurationBuilder, IEnumerable<KeyValuePair<String,String>>) 會在預設設定提供者之後新增記憶體提供者。 如需有關排定設定提供者優先順序的範例,請參閱 XML 設定提供者

另請參閱