Systemd 环境和 EnvironmentFile 不起作用

Kee*_*ker 12 systemd centos7

我已经为它构建了一个应用程序和一个 systemd 单元。systemd 单元工作正常,但随着开发和生产环境的不同,我开始将配置移到环境变量中,但似乎无法让它们在 systemd 中工作。

我已经尝试过系统范围的环境变量,它们对操作系统可见,但对程序不可见,所以我开始考虑将它们构建到 systemd 单元中。

首先我尝试使用 EnvironmentFile

我创建了一个简单的环境文件

LCSQLH=localhost
LCSQLU=application
Run Code Online (Sandbox Code Playgroud)

在它作为/etc/lc.sh

[Unit]
Description=Service for this app

[Service]
EnvironmentFile=/etc/lc.sh
ExecStart=/usr/bin/env python /opt/app/__init__.py
Run Code Online (Sandbox Code Playgroud)

做了systemctl --system daemon-reload但没有,我的应用程序出错:

Jan 27 14:24:59 machine.host env[630]: KeyError: 'LCSQLU'

我看到一些有:

EnvironmentFile=-/etc/lc.sh

我试过了……不……

所以我试着把它们单独放进去

[Service]
Environment="LCSQLH=localhost"
Environment="LCSQLU=application"
ExecStart=/usr/bin/env python /opt/app/__init__.py
Run Code Online (Sandbox Code Playgroud)

再一次,没有...

所以我听说了这样的想法,/etc/systemd/service_name.service.d所以我在那里放了一个 service.conf 和环境(与上面的格式相同)但没有......

我的应用程序无法访问这些环境变量。

如果我导出它们(在我的 shell 中手动或使用 /etc/profile.d/)并直接运行我的应用程序,它就可以工作,所以这些不是被设置而不是应用程序问题。

这是 Centos 7.3,我选择了环境变量而不是硬编码的配置,因为它可以在 linux 或 windows 上运行,所以不想将配置文件埋在 /etc/ 中

Cam*_*err 30

EnvironmentEnvironmentFile设置单元可用的变量,但与sh命令一样,不会将其导出到子进程。为此,您还需要将其列在 中PassEnvironment,就像使用exportshell 命令一样。请参阅有关 EnvironmentFile 和 PassEnvironment 的 systemd 文档

另请注意,EnvironmentFile 的内容不是 shell 脚本,而是键值对看起来太像 sh,因此用.sh扩展名命名它会产生误导。

  • 还值得注意的是,仔细阅读这些文档还揭示了为什么这些变量似乎在某些配置中会通过`“系统服务默认情况下不会自动继承任何环境变量 [...] 但是,在用户服务管理器的情况下,所有环境变量传递给执行的进程"` (2认同)
  • 我刚刚使用 `ExecStartPre=/bin/bash -l -c 'env >/tmp/ingest.err'` 和 env 对此进行了测试。使用 `Environment=` 和 `EnvironmentFile=` 和 `systemctl set-environment...` 设置的 var *do* 显示在单元的 env 中...即使它是一个系统单元。我唯一能解释的就是“PassEnvironment”意味着在环境中传递变量。systemd 进程本身的“通过”(参见评论 https://superuser.com/a/728962/39364)。前言... (2认同)

小智 6

我在 RHEL 7.3 上遇到了同样的问题,发现了这个

然后,您可以/etc/sysconfig/httpd使用${FOOBAR}$FOOBAR,ExecStart在行(和相关行)中引用文件中设置的变量。

这让我觉得目的EnvironmentEnvironmentFile完全不是你和我所期望的(为由 systemd 单元启动的进程设置环境变量),而仅适用于行的立即扩展ExecStart

也许我完全不在基地,这是 systemd 中的一个错误(我希望如此)。但是我停止沿着你正在尝试的路径走下去,而是以另一种方式去做:在我的情况下,我需要设置LD_LIBRARY_PATH,所以我通过创建/etc/ld.so.conf.d/new_file.conf然后运行来做到这一点ldconfig。我还尝试在 中使用系统范围的变量/etc/profile.d/new_file.sh,但显然设置LD_LIBRARY_PATH对于该服务 (mariadb)来说已经足够了,所以我实际上不知道我设置的变量/etc/profile.d/new_file.sh是否正常工作。