从 Jinja2 模板访问操作系统环境变量

问题描述 投票:0回答:7

是否可以直接从 Jinja2 模板访问操作系统环境变量?

python jinja2
7个回答
20
投票

按照@Renier 在评论中关于自定义过滤器的指针,我找到了一个可能的解决方案。

定义自定义过滤器

def env_override(value, key):
  return os.getenv(key, value)

安装过滤器的环境:

env.filters['env_override'] = env_override

按如下方式使用过滤器:

"test" : {{ "default" | env_override('CUSTOM') }}

适当的环境变量可以设置为:

export CUSTOM=some_value

如果设置了环境变量,输出将是:

"test" : some_value

否则:

"test" : default

12
投票

答案here效果很好,但你仍然可以摆脱 cat 的无用使用并将其压缩为单个语句:

python -c 'import os
import sys
import jinja2
sys.stdout.write(
    jinja2.Template(sys.stdin.read()
).render(env=os.environ))' <$CONFIGTEMPLATE >$CONFIGFILE
  

P.S.:Stack Overflow 不允许在注释中使用格式化代码。因此,我必须将其作为单独的答案发布,而不是评论https://stackoverflow.com/a/27984610/1070890


10
投票

我相信你可以像这样访问环境变量:

{{ env['XMPP_DOMAIN'] or "localhost" }}

这是我最近看到的配置文件中的一个示例,用于 ejabberd 的 Docker 部署。

hosts: - "{{ env['XMPP_DOMAIN'] or "localhost" }}"

注意: 您可以在 Github 存储库的 run 文件中查看示例的其余部分。

据我了解,繁重的工作是由这段代码完成的:

readonly PYTHON_JINJA2="import os; import sys; import jinja2; sys.stdout.write( jinja2.Template (sys.stdin.read() ).render(env=os.environ)) """
此代码用于生成模板文件:

cat ${CONFIGTEMPLATE} \ | python -c "${PYTHON_JINJA2}" \ > ${CONFIGFILE}
参考文献

  • rroemhild/docker-ejabberd docker 镜像来自 github

4
投票
在 bash 中让我们设置我们的示例

export MYENVVAR=foo
$ 纳米示例.py

from jinja2 import Template import os template = Template("Hello {{ env['MYENVVAR'] or 'DefaultVal' }}") r = template.render(env=os.environ, name='somethingelse') print(r)
运行模板

$ python3 example.py

https://jinja.palletsprojects.com/en/2.11.x/intro/


0
投票

这里是您可以从模板访问的变量列表。 我试图访问一些 app.config

 变量,我设法通过调用 
config
:
来做到这一点

{% if current_user.id == config['ADMIN_ID'] %} ######## SOME HTML ######## {% endif %}
Flask-Login 将 

current_user

 变量添加到您的模板中


0
投票
我最简单的 FastAPI 解决方案

templates.env.globals.update(getenv=os.getenv)

在金贾2

{{ getenv("FOO") }}


0
投票

最佳答案按以下格式解析环境变量:

my_secret: "{{ 'default value' | env('ENV_VAR') }}"


我注意到其他工具(例如 DBT)使用另一种格式,例如:

my_secret: "{{ env('ENV_VAR', 'default value') }}"


我设法通过将 env 函数渲染为模板变量并将参数传递给 lambda 函数中的 os.getenv 来实现与最佳答案类似的解决方案:

def read_yaml_with_env(yaml_str: str) -> dict: # Apply Jinja Template and load environment variables env = Environment() template = env.from_string(yaml_str) yaml_vars = template.render(env=lambda x, y: os.getenv(x, y)) # Load YAML json_from_yaml = yaml.safe_load(yaml_vars) return json_from_yaml
    
最新问题
© www.soinside.com 2019 - 2025. All rights reserved.