进程守护 Supervisor

Info

Supervisor(官网)是一个 C/S 架构的进程管理工具,可以在类 UNIX 系统上启动、停止、监控进程,并在进程异常退出时自动拉起。

安装

# CentOS 7 的 supervisor 位于 EPEL 源
> yum install -y epel-release
> yum install -y supervisor

安装后的主要文件:

  • 主配置:/etc/supervisord.conf
  • 子配置目录:/etc/supervisor/conf.d/*.conf
  • 命令行工具:supervisorctl

服务管理

> systemctl enable supervisord    # 开机自启
> systemctl start supervisord     # 启动
> systemctl stop supervisord      # 停止
> systemctl restart supervisord   # 重启(修改主配置后使用)
> systemctl status supervisord    # 查看运行状态

新增守护进程

在 /etc/supervisor/conf.d/ 下新建 *.conf 文件,例如:

/etc/supervisor/conf.d/my_test.conf
[program:my_test]
command=python3 test.py
directory=/root/
user=root
autostart=true
autorestart=true
startretries=10
stopsignal=TERM
stopwaitsecs=10
redirect_stderr=true
stdout_logfile=/data/log/supervisor/my_test.log
stdout_logfile_maxbytes=50MB
stdout_logfile_backups=10

加载配置:

> supervisorctl reread    # 读取新增或修改的配置
> supervisorctl update    # 将变更应用到进程,重启受影响的程序

supervisorctl 常用命令

执行 supervisorctl 进入交互式 shell,也可以直接用 supervisorctl <command> 执行单条命令。

命令说明
status查看所有程序状态
start <program>启动指定程序
stop <program>停止指定程序
restart <program>重启指定程序
start all / stop all启动 / 停止全部程序
tail -f <program>实时查看程序日志
reread读取配置文件变更,不重启进程
update应用配置变更,重启配置被修改的程序
help查看帮助

直接命令行执行:

> supervisorctl status
> supervisorctl restart my_test

主配置说明

/etc/supervisord.conf 中需要关注的部分:

/etc/supervisord.conf
[unix_http_server]
file=/var/run/supervisor.sock
chmod=0700

[supervisord]
logfile=/var/log/supervisord.log
pidfile=/var/run/supervisord.pid

[supervisorctl]
serverurl=unix:///var/run/supervisor.sock

; 必须保留,否则 supervisorctl 无法使用
[rpcinterface:supervisor]
supervisor.rpcinterface_factory = supervisor.rpcinterface:make_main_rpcinterface

; 子配置目录,放在这里面的 *.conf 会被自动加载
[include]
files = /etc/supervisor/conf.d/*.conf

说明:

  • /var/run 是 tmpfs,重启后会清空,socket 与 pid 文件由 supervisord 启动时重建。
  • 日志目录(如例子中的 /data/log/supervisor)需要提前创建,并保证运行用户有写权限。
  • chmod=0700 表示只有属主(通常是 root)能访问 socket,因此执行 supervisorctl 需要 root 或 sudo。

program 配置项

[program:my_test]
; 启动命令
command=python3 test.py
; 执行命令的工作目录
directory=/root/
; 运行用户
user=root
; 启动顺序,数字越小越先启动、越后停止,默认 999
priority=999
; 进程数量;大于 1 时 command 中需用 %(process_num)02d 区分
numprocs=1
; supervisord 启动时是否自动拉起
autostart=true
; 退出后是否自动重启:false / unexpected / true
autorestart=true
; 启动后持续运行超过该秒数才认为启动成功
startsecs=1
; 启动失败的重试次数
startretries=3
; 视为正常退出的退出码
exitcodes=0,2
; 停止时发送的信号;KILL 无法被捕获,一般使用 TERM
stopsignal=TERM
; 发送 stopsignal 后等待的秒数,超时后发送 SIGKILL
stopwaitsecs=10
; 把 stderr 重定向到 stdout
redirect_stderr=true
; 日志文件、单文件大小上限、保留份数
stdout_logfile=/data/log/supervisor/my_test.log
stdout_logfile_maxbytes=50MB
stdout_logfile_backups=10

常见问题

  • unix:///var/run/supervisor.sock no such file:supervisord 未启动,执行 systemctl start supervisord。
  • 修改或新增配置后进程没有变化:执行 supervisorctl reread,再执行 supervisorctl update。
  • 修改了主配置 /etc/supervisord.conf:需要 systemctl restart supervisord 才生效。
  • 程序启动即退出:查看 stdout_logfile 中的日志,或执行 supervisorctl tail -f <program>。

参考