檢視原始碼 Config.Provider 行為 (Elixir v1.16.2)
指定在開機期間載入組態的提供者 API。
組態提供者通常在發行版中用於在系統開機時載入外部組態。這是透過以最少數量的應用程式啟動 VM,然後呼叫所有提供者,再重新啟動系統來完成的。這需要磁碟上有一個可變動的組態檔案,因為提供者的結果會寫入檔案系統。如需執行時期組態的更多資訊,請參閱 mix release
。
多個組態檔案
組態提供者的其中一個常見用途是在發行版中指定多個組態檔案。Elixir 內建一個稱為 Config.Reader
的提供者,它能夠處理 Elixir 內建的組態檔案。
例如,假設您要在 Mix 內建的 config/runtime.exs
檔案中列出一些基本組態,但您也想要支援其他組態檔案。為此,您可以在 mix.exs
的 def project
部分中新增這段程式碼
releases: [
demo: [
config_providers: [
{Config.Reader, {:system, "RELEASE_ROOT", "/extra_config.exs"}}
]
]
]
您可以用多種方式將這個 extra_config.exs
檔案放置在您的發行版中
如果在組裝發行版時它在主機上可用,您可以將它放在 "rel/overlays/extra_config.exs",它會自動複製到發行版根目錄
如果在部署期間它在目標上可用,您可以在部署步驟中將它複製到發行版根目錄
現在,一旦系統開機,它將在開機程序的早期載入 config/runtime.exs
和 extra_config.exs
。您可以在 Config.Reader
中瞭解更多選項。
自訂組態提供者
您也可以實作自訂組態提供者,類似於 Config.Reader
的運作方式。例如,假設您需要從 JSON 檔案載入一些組態,並將其載入系統。所述組態提供者會如下所示
defmodule JSONConfigProvider do
@behaviour Config.Provider
# Let's pass the path to the JSON file as config
@impl true
def init(path) when is_binary(path), do: path
@impl true
def load(config, path) do
# We need to start any app we may depend on.
{:ok, _} = Application.ensure_all_started(:jason)
json = path |> File.read!() |> Jason.decode!()
Config.Reader.merge(
config,
my_app: [
some_value: json["my_app_some_value"],
another_value: json["my_app_another_value"],
]
)
end
end
然後,在指定您的版本時,您可以在版本組態中指定提供者
releases: [
demo: [
config_providers: [
{JSONConfigProvider, "/etc/config.json"}
]
]
]
摘要
類型
回呼函式
在初始化組態提供者時呼叫。
組態提供者通常在組裝系統的機器上初始化,而不是在目標機器上初始化。 init/1
回呼函式可協助驗證提供給提供者的引數,並準備將提供給 load/2
的狀態。
此外,由於 init/1
傳回的狀態可以寫入基於文字的組態檔案,因此應該僅限於簡單的資料類型,例如整數、字串、原子、叢集、對應和清單。無法序列化 PID、參照和函式等項目。
載入組態(通常在系統開機期間)。
它會接收 init/1
傳回的目前 config
和 state
。然後,您通常會從外部來源讀取額外的組態,並將其併入接收到的 config
中。併入應使用 Config.Reader.merge/2
進行,因為它會執行深度併入。它應傳回已更新的組態。
請注意,load/2
通常在開機過程中很早就會呼叫,因此如果您需要在提供者中使用應用程式,您有責任啟動它。
函數
@spec resolve_config_path!(config_path()) :: binary()
將 config_path/0
解析為實際路徑。
@spec validate_config_path!(config_path()) :: :ok
驗證 config_path/0
。