在 .NET Core 專案中,我們可以使用 appsettings.json
配置檔來儲存應用程式的配置信息。在這篇文章中,我們將學習如何使用 appsettings.json
配置檔。
appsettings.json
是一個相較於 App.config
更加靈活的配置檔,是 .NET Core 以來新增的一種配置方式,提供了更多的靈活性。
快速入門#
我們可以在專案中創建一個 appsettings.json
檔案,然並將其生成操作設定為「較新時複製」或「總是複製」,這樣在專案建置時,appsettings.json
檔案會被複製到輸出目錄中。
然後我們可以在其中添加如下內容:
{
"AppSettings": {
"LogLevel":"Warning",
"ConnectionStrings": {
"Default": "this is the connection string"
}
}
}
這樣我們就可以嘗試讀取了。我們使用 NuGet 套件管理器安裝 Microsoft.Extensions.Configuration.Json
套件。它會隱式安裝 Microsoft.Extensions.Configuration
等依賴項,這些我們不需要顯式安裝。
然後我們可以在程式碼中讀取配置檔:
using Microsoft.Extensions.Configuration;
var configuration = new ConfigurationBuilder()
.AddJsonFile("appsettings.json", optional: false, reloadOnChange: true)
.Build();
這樣我們就可以獲取上面的配置信息了:
var logLevel = configuration["AppSettings:LogLevel"];
var connectionString = configuration["AppSettings:ConnectionStrings:Default"];
這裡的形如 AppSettings.LogLevel
是一種特殊的寫法,簡單來說就是借助 :
來表示 JSON 中的層級關係。
如果要獲取的配置項是一個數字,我們除了可以先通過上述方式獲取到字串,進而使用 int.Parse
或 Convert.ToInt32
等方法進行轉換,還可以使用 GetValue
方法:
// 傳統方法
var logLevel = int.Parse(configuration["AppSettings:LogLevel"]);
// 使用 GetValue 方法
var logLevel = configuration.GetValue<int>("AppSettings:LogLevel");
對於連接字串,我們還可以使用 GetConnectionString
方法:
var connectionString = configuration.GetConnectionString("Default");
可選與自動重載#
在上面的程式碼中,我們可以看到 AddJsonFile
方法有兩個參數,optional
和 reloadOnChange
:
optional
參數表示是否允許配置檔不存在,如果設定為false
,則會拋出異常,否則會忽略。reloadOnChange
參數表示是否在配置檔發生變化時重新載入配置檔。如果設定為true
,則會在配置檔發生變化時重新載入配置檔。
比如我們可以用下面的例子測試自動重載的效果:
var configuration = new ConfigurationBuilder()
.AddJsonFile("appsettings.json", optional: false, reloadOnChange: true)
.Build();
while (true)
{
Console.WriteLine(configuration["AppSettings:LogLevel"]);
Thread.Sleep(1000);
}
在運行程式後,我們可以修改 appsettings.json
檔案中的 LogLevel
配置,然後我們會發現程式會自動重新載入配置檔。注意這裡我們修改的是輸出目錄(也就是 .exe
檔案所在位置)下的 appsettings.json
檔案,而不是專案中的 appsettings.json
檔案。
添加多個 JSON 檔案#
如果只能添加一個 JSON 檔案,那麼配置檔的靈活性就大大降低了。事實上,我們可以通過多次調用 AddJsonFile
方法來添加多個 JSON 檔案。一個典型的情形是添加一個 appsettings.Development.json
檔案,用於儲存開發環境的配置信息。
var configuration = new ConfigurationBuilder()
.AddJsonFile("appsettings.json", optional: false, reloadOnChange: true)
.AddJsonFile("appsettings.Development.json", optional: true, reloadOnChange: true)
.Build();
這樣我們就可以在 appsettings.Development.json
檔案中儲存開發環境的配置信息,而在 appsettings.json
檔案中儲存通用的配置信息。
不僅如此,這二者之間存在優先級,或者說覆蓋關係。具體來說:
- 如果
appsettings.json
和appsettings.Development.json
中都有相同的配置項,那麼appsettings.Development.json
中的配置項會覆蓋appsettings.json
中的配置項 - 如果
appsettings.Development.json
中沒有某個配置項,而appsettings.json
中有,那麼會使用appsettings.json
中的配置項 - 如果
appsettings.Development.json
中有某個配置項,而appsettings.json
中沒有,那麼會使用appsettings.Development.json
中的配置項
使用強類型配置#
在上面的例子中,我們使用 configuration["AppSettings:LogLevel"]
來獲取配置信息,這種方式是一種弱類型的方式。我們也可以使用強類型的方式來獲取配置信息。
我們修改一下 appsettings.json
檔案中的配置項:
{
"UserSettings": {
"Name": "Alice",
"Age": 18,
"IsActive": true
}
}
然後我們定義一個強類型的配置類:
public class UserSettings
{
public string Name { get; set; }
public int Age { get; set; }
public bool IsActive { get; set; }
}
在獲取配置前,我們還需要安裝一個 NuGet 套件:Microsoft.Extensions.Options.ConfigurationExtensions
。然後我們就可以這樣獲取配置信息:
var userSettings = configuration.GetSection("UserSettings").Get<UserSettings>();
這樣我們就可以獲取到 UserSettings
物件了,然後就可以使用 userSettings.Name
、userSettings.Age
、userSettings.IsActive
來獲取配置信息了。
但是需要注意,因為這裡的 userSettings
實例已經初始化,所以前面提到的自動重載功能不再生效。如果需要自動重載,我們需要重新獲取 userSettings
物件。
添加環境變數和命令行參數#
在 .NET Core 中,我們還可以通過環境變數和命令行參數來覆蓋配置檔中的配置信息。我們需要再安裝兩個 NuGet 套件:
Microsoft.Extensions.Configuration.EnvironmentVariables
Microsoft.Extensions.Configuration.CommandLine
然後我們可以這樣添加環境變數和命令行參數:
var configuration = new ConfigurationBuilder()
.AddJsonFile("appsettings.json", optional: false, reloadOnChange: true)
.AddEnvironmentVariables()
.AddCommandLine(args)
.Build();
這樣我們就可以通過環境變數和命令行參數來覆蓋配置檔中的配置信息了。
比如我們可以創建一個 .bat
批處理檔:
@echo off
set UserSettings__Name=Bob
set UserSettings__Age=20
.\Demo.exe
或者還可以使用 PowerShell:
$env:UserSettings__Name = "Bob"
$env:UserSettings__Age = 20
.\Demo.exe
總結#
相信通過這篇文章,大家已經認識到了 appsettings.json
配置檔的強大之處。它不僅提供了一種靈活的配置方式,還提供了多種配置方式的組合,使得我們可以更加靈活地配置應用程式。
但是它也有一些局限性。最重要的一條就是它的配置項是「只讀」的,也就是不能像 App.config
那樣在運行時方便地修改配置項。畢竟,一個專案中可能存在多個配置項,而不是只有一個 appsettings.json
檔案。此時如果修改了,該保存到哪個檔案呢?
當然,如果只有一個配置檔,那麼 appsettings.json
是一個不錯的選擇。比如我們可以使用 Newtonsoft.Json
來輕鬆地寫入 JSON 檔案,這樣就可以實現配置項的修改了。
最後,其實通常情況下,我們並不會使用上面的方式讀取配置項,而是會更進一步,使用 Host
作為整個程式的入口,並讀取配置、注入服務等。在之後的文章中,我們會學習如何使用 Host
來構建一個 .NET 應用程式。