systemd服务运行失败时触发执行指定动作的标准方法是什么?
systemd服务运行失败时触发指定命令的标准实现方案
systemd原生提供了非临时的标准化配置方式实现该需求,无需额外封装ExecStart脚本,常用实现方式如下:
方案1:使用OnFailure触发独立处理单元(更规范,适合多服务统一监控)
这是systemd官方推荐的失败处理方案,通过单元依赖实现逻辑解耦:
- 首先创建全局失败处理服务单元
/etc/systemd/system/service-failure-alert@.service,内容如下:
[Unit] Description=Failure alert handler for service %i [Service] Type=oneshot # 替换为你的告警逻辑,可以是发邮件、推送Nagios被动告警等 ExecStart=/usr/local/bin/nagios-passive-alert.sh %i # 示例:直接调用mailx发送告警邮件 # ExecStart=/usr/bin/mailx -s "告警:服务%i运行失败" ops@yourdomain.com <<< "主机$(hostname)上的服务%i异常退出,请排查" User=root
- 在需要监控的业务服务的
[Unit]配置段添加如下配置即可:
[Unit] # 其他原有配置... OnFailure=service-failure-alert@%n.service
配置中的%n会自动替换为当前异常退出的服务单元完整名称,作为参数传递给告警处理服务,无需为每个服务单独写处理逻辑。配置修改后执行systemctl daemon-reload生效。
方案2:使用ExecStopPost内置状态判断(适合单服务自定义告警)
如果仅需要给单个服务加失败触发逻辑,无需统一处理,可以直接在服务配置的[Service]段添加如下配置:
[Service] # 其他原有配置... ExecStopPost=/bin/bash -c 'if [ $$EXIT_STATUS -ne 0 ]; then /usr/local/bin/your-alert-script.sh %n; fi'
说明:
ExecStopPost会在服务主进程退出后无论成功失败都执行,因此需要通过判断$EXIT_STATUS(systemd内置环境变量,存储服务主进程退出码)是否非0来识别异常退出场景- systemd单元配置中
$符号需要转义为$$避免被提前解析
可选增强配置
如果需要避免服务偶发退出就触发告警,可以配合启动限流配置使用,仅在多次重启失败后才触发告警:
- 在被监控服务的
[Unit]段添加:
StartLimitIntervalSec=300 StartLimitBurst=3
上述配置代表5分钟内服务重启超过3次就触发启动上限,此时才会执行OnFailure指定的处理逻辑。
内容的提问来源于stack exchange,提问作者j4nd3r53n
相关产品推荐
相关产品推荐

