python - 如何使用python脚本替换要解析的yaml文件中的环境变量值

标签 python python-2.7 pyyaml

我需要在需要用脚本解析的 yaml 文件中使用环境变量“PATH”。

这是我在终端上设置的环境变量:

$ echo $PATH
/Users/abc/Downloads/tbwork

这是我的 sample.yml:

---
Top: ${PATH}/my.txt
Vars:
- a
- b

当我用我的脚本解析这个 yaml 文件时,我没有看到 PATH 变量的实际值。

这是我的脚本:

import yaml
import os
import sys

stream = open("sample.yml", "r")
docs = yaml.load_all(stream)
for doc in docs:
    for k,v in doc.items():
        print k, "->", v
    print "\n",

输出:

Top -> ${PATH}/my.txt
Vars -> ['a', 'b']

预期输出是:

Top -> /Users/abc/Downloads/tbwork/my.txt
Vars -> ['a', 'b']

如果我做错了,有人能帮我找出正确的方法吗?

最佳答案

PY-yaml 库默认不解析环境变量。您需要定义一个隐式解析器,它将找到定义环境变量的正则表达式并执行一个函数来解析它。

您可以通过 yaml.add_implicit_resolveryaml.add_constructor 来完成。在下面的代码中,您定义了一个将匹配 YAML 值中的 ${ env variable } 的解析器,并调用函数 path_constructor 来查找环境变量。

import yaml
import re
import os

path_matcher = re.compile(r'\$\{([^}^{]+)\}')
def path_constructor(loader, node):
  ''' Extract the matched value, expand env variable, and replace the match '''
  value = node.value
  match = path_matcher.match(value)
  env_var = match.group()[2:-1]
  return os.environ.get(env_var) + value[match.end():]

yaml.add_implicit_resolver('!path', path_matcher)
yaml.add_constructor('!path', path_constructor)

data = """
env: ${VAR}/file.txt
other: file.txt
"""

if __name__ == '__main__':
  p = yaml.load(data, Loader=yaml.FullLoader)
  print(os.environ.get('VAR')) ## /home/abc
  print(p['env']) ## /home/abc/file.txt

警告:如果您不是指定 env 变量(或任何其他不受信任的输入)的人,请不要运行此命令,因为截至 2020 年 7 月,FullLoader 存在远程代码执行漏洞。

关于python - 如何使用python脚本替换要解析的yaml文件中的环境变量值,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/52412297/

相关文章:

python - 如何拥有一个没有距离较近的元素对的数组

python - 在 python 的自定义错误类中调用 super 有什么意义?

python-3.x - PyYaml 将 '9:00' 解析为 int

python - 找不到满足 pyyaml>=5.3 要求的版本,但 PyYAML 是版本 5.3.1

python - 解析 yaml 文件并获取字典

python - R的relevel()和 Pandas 线性回归中的因子变量

python - pypdf python工具

python - 程序负责在从 Keras 加载 InceptionV3 时显示 ETA

python - 在python中删除列表中的项目

python - PyParsing 和多行系统日志消息