一日一技:優雅地加載 Yaml 配置文件

攝影:產品經理

又到了一年一度的王品牛排時間

我在多篇文章裏面都說過,我非常喜歡使用 Yaml 格式來寫配置文件。Yaml 是一個對人非常友好的配置格式。

=========================================================

有時候,我們在開發環境、測試環境和線上環境會有多套不同的配置文件,如何在不修改代碼的情況下方便的切換配置文件呢?我以前的文章講過一種方法,使用環境變量來指定配置文件名。今天我們來介紹一個更先進的工具,專門用來高效加載配置文件。這就是 Facebook 開源的 Hydra。

這個工具有多簡單呢?我們先寫兩個配置文件,然後看看怎麼讀取它:

使用 pip 安裝 Hydra:

python3 -m pip install hydra-core

接下來,我們寫一段代碼,來讀取配置文件:

import os
import hydra
from omegaconf import DictConfig

env = os.getenv('DATA_CENTER''dev')
@hydra.main(config_path="config"config_name=env)
def main(cfg: DictConfig):
    print('MongoDB鏈接地址是:', cfg.mongo.uri)
    print('Redis的key是:', cfg.redis.key)
    print('黑名單是:', cfg.detail.black_list)


if __name__ == '__main__':
    main()

運行效果如下圖所示:

其中,裝飾器hydra.main的參數config_path指定存放配置文件的文件夾,config_name用來指定配置文件的名字(去掉. yaml)。

這樣一來,我們可以通過環境變量指定要使用哪個配置文件。

這樣看起來似乎跟我以前講的方法沒什麼區別啊。那麼,高級的功能來了。例如現在我使用 dev 環境時,臨時想修改一下 Redis 的 Key 怎麼辦呢?以前的方法,我就必須去修改 Yaml 文件,把 Key 改掉。但是,既然是臨時修改,測試完了又要改回來,顯然非常麻煩。

使用 Hydra,這個問題就不再是問題了。我們來看看直接在命令中覆蓋數據的方法:

請看圖中,我代碼沒有做任何修改,Yaml 也沒有做任何修改。只需要在啓動命令的時候增加一個參數redis.key=new_key,那麼程序讀取到的就是新的值了。這對臨時測試的時候非常有用。

除了我上面介紹的這些,Hydra 還可以實現自動補全,自動提示參數名,自動以多個不同的配置連續運行等等功能。大家可以在它的官方文檔 [1] 中看到使用方法。

最後,我補充一個點。有同學在公衆號粉絲羣提問,Hydra 爲什麼不能在調用函數的時候,傳遞額外的參數,例如下面這樣寫就會報錯:

這是因爲,Hydra 的裝飾對象應該是程序的入口函數。給入口函數傳遞參數是很奇怪的。如果你的入口函數要根據參數的不同值執行不同的邏輯,那麼這個參數你完全可以放到配置文件中。而不是用函數參數來傳入。

所以,這裏報錯應該是功能而不是 bug。本來就不應該在入口函數中添加額外的參數。

參考文獻

[1] 官方文檔: https://hydra.cc/docs/intro/

本文由 Readfog 進行 AMP 轉碼,版權歸原作者所有。
來源https://mp.weixin.qq.com/s/jEQMNxC4o0PKSrQz4rI7Lw