如何在不使用 @hydra.main() 的情况下获取 Hydra 配置

fla*_*awr 13 python-3.x hydra-python fb-hydra

假设我们有以下设置(从Hydra 文档中复制和缩短):

配置文件: config.yaml

db:
  driver: mysql
  user: omry
  pass: secret
Run Code Online (Sandbox Code Playgroud)

蟒文件: my_app.py

import hydra
@hydra.main(config_path="config.yaml")
def my_app(cfg):
    print(cfg.pretty())
if __name__ == "__main__":
    my_app()
Run Code Online (Sandbox Code Playgroud)

当我们可以在函数上使用装饰器时,这很有效my_app。现在我想(为了小脚本和测试目的,但这并不重要)cfg在任何函数之外获取这个对象,只是在一个普通的 python 脚本中。据我了解装饰器的工作原理,应该可以调用

import hydra
cfg = hydra.main(config_path="config.yaml")(lambda x: x)()
print(cfg.pretty())
Run Code Online (Sandbox Code Playgroud)

但 thencfg只是None而不是所需的配置对象。所以看起来装饰器没有传递返回值。有没有另一种方法可以做到这一点cfg

Omr*_*dan 17

使用Compose API

from hydra import compose, initialize
from omegaconf import OmegaConf

initialize(config_path="conf", job_name="test_app")
cfg = compose(config_name="config", overrides=["db=mysql", "db.user=me"])
print(OmegaConf.to_yaml(cfg))
Run Code Online (Sandbox Code Playgroud)

这只会组合配置,不会产生副作用,例如更改工作目录或配置 Python 日志记录系统。

  • 抱歉耽搁了!顺便说一句:我刚刚注意到 [tag:Hydra] 标签与您的包无关,您介意为其创建一个标签吗?(或者您对如何称呼此标签有任何建议吗? [tag:Hydra] 和 [tag:Hydra-core] 都已使用。) (2认同)

for*_*tso 14

上述解决方案都不适合我。他们给出了错误:

“builtin_function_or_method”对象没有属性“ code

GlobalHydra 已经初始化,如果想重新初始化,请调用 GlobalHydra.instance().clear()

我进一步研究 Hydra 并意识到我可以使用 OmegaConf 直接加载文件。你不会被覆盖,但我对此并不大惊小怪。

import omegaconf
cfg = omegaconf.OmegaConf.load(path)
Run Code Online (Sandbox Code Playgroud)

  • 这个答案适用于常规配置文件,但可以说,如果您有不同的结构和路径/目录/配置用于阶段/生产/开发配置,那么您必须将它们放在一个文件中,这对于维护 Hydra 解决了这个问题是很繁琐的。否则,如果您只有一种配置,那么请寻求这种更好更快的解决方案。 (3认同)