简介
Supervisor 是一个用 Python 写的进程管理工具,当进程意外终止或服务器宕机重启后,希望进程能够自动运行,supervisord可以很好的为我们做这件事情。
除了对单个进程的控制,还可以同时启动、关闭多个进程,比如很不幸的服务器出问题导致所有应用程序都被杀死,此时可以用 supervisor 同时启动所有应用程序而不是一个一个地敲命令启动。
同时supervisord自带web监控界面,可以通过浏览器查看、操作。
官方文档:http://www.supervisord.org/installing.html
原理:
supervisor管理进程,就是通过fork/exec的方式把这些被管理的进程,当作supervisor的子进程来启动。当子进程挂掉的时候,父进程可以准确获取子进程挂掉的信息的。
安装
1、python --version && pip --version
2、easy_install supervisor
3、echo_supervisord_conf && echo_supervisord_conf > /etc/supervisord.conf
组件
-
supervisord
supervisord是supervisor的服务端程序。
干的活:启动supervisor程序自身,启动supervisor管理的子进程,响应来自clients的请求,重启闪退或异常退出的子进程,把子进程的stderr或stdout记录到日志文件中,生成和处理Event
-
supervisorctl
这东西还是有点用的,如果说supervisord是supervisor的服务端程序,那么supervisorctl就是client端程序了。supervisorctl有一个类型shell的命令行界面,我们可以利用它来查看子进程状态,启动/停止/重启子进程,获取running子进程的列表等等。。。最牛逼的一点是,supervisorctl不仅可以连接到本机上的supervisord,还可以连接到远程的supervisord,当然在本机上面是通过UNIX socket连接的,远程是通过TCP socket连接的。supervisorctl和supervisord之间的通信,是通过xml_rpc完成的。 相应的配置在[supervisorctl]块里面
-
Web Server
Web Server主要可以在界面上管理进程,Web Server其实是通过XML_RPC来实现的,可以向supervisor请求数据,也可以控制supervisor及子进程。配置在[inet_http_server]块里面
配置说明
启动停止命令
supervisord默认以daemon守护进程的方式后台启动
supervisord -c /etc/supervisord.conf
查看pid,停止进程
ps -ef | grep supervisord
kill -9 pid
-n选项:前台启动
program 配置
上面我们已经把 supervisrod 运行起来了,现在可以添加我们要管理的进程的配置文件。这些配置可以都写到 supervisord.conf 文件里,如果应用程序很多,最好通过 include 的方式把不同的程序(组)写到不同的配置文件里。
为了举例,我们新建一个目录 /etc/supervisor/ 用于存放这些配置文件,相应的,把 /etc/supervisord.conf 里 include 部分的的配置修改一下:
[include]
files = /etc/supervisor/*.conf
假设有个用 Flask 开发的用户系统 usercenter, 生产环境使用 gunicorn 运行。项目代码位于 /home/leon/projects/usercenter,WSGI 对象位于 wsgi.py。在命令行启动的方式是这样的:
cd /home/leon/projects/usercenter
gunicorn -w 8 -b 0.0.0.0:17510 wsgi:app
对应的配置文件可能是:
[program:usercenter]
directory = /home/leon/projects/usercenter ; 程序的启动目录
command = gunicorn -w 8 -b 0.0.0.0:17510 wsgi:app ; 启动命令
autostart = true ; 在 supervisord 启动的时候也自动启动
startsecs = 5 ; 启动 5 秒后没有异常退出,就当作已经正常启动了
autorestart = true ; 程序异常退出后自动重启
startretries = 3 ; 启动失败自动重试次数,默认是 3
user = leon ; 用哪个用户启动
redirect_stderr = true ; 把 stderr 重定向到 stdout,默认 false
stdout_logfile_maxbytes = 20MB ; stdout 日志文件大小,默认 50MB
stdout_logfile_backups = 20 ; stdout 日志文件备份数
; stdout 日志文件,需要注意当指定目录不存在时无法正常启动,所以需要手动创建目录(supervisord 会自动创建日志文件)
stdout_logfile = /data/logs/usercenter_stdout.log其中 [program:usercenter] 中的 usercenter 是应用程序的唯一标识,不能重复。对该程序的所有操作(start, restart 等)都通过名字来实现。
Tips 1: Python 环境
有两种方式指定程序使用的 Python 环境:
command 使用绝对路径。假设使用 pyenv 来管理 Python 环境,上面例子中的 gunicorn 路径可以替换为 /home/leon/.pyenv/versions/usercenter/bin/gunicorn. 这种方式一目了然,推荐。
通过 environment 配置 PYTHONPATH. environment=PYTHONPATH=$PYTHONPATH:/home/leon/.pyenv/versions/usercenter/bin/. environment 这个配置项非常有用,可以用来给程序传入环境变量。Tips 2: 后台进程
Supervisor 只能管理在前台运行的程序,所以如果应用程序有后台运行的选项,需要关闭。Tips 3: 子进程
有时候用 Supervisor 托管的程序还会有子进程(如 Tornado),如果只杀死主进程,子进程就可能变成孤儿进程。通过这两项配置来确保所有子进程都能正确停止:
stopasgroup=true
killasgroup=true
命令行工具supervisorctl
status # 查看程序状态
stop program_name # 关闭 指定的程序
start program_name # 启动 指定的程序
restart program_name # 重启 指定的程序
tail -f program_name # 查看 该程序的日志
update # 重启配置文件修改过的程序(修改了配置,通过这个命令加载新的配置)
也可以直接通过 shell 命令操作:
supervisorctl status
supervisorctl update
web界面
[inet_http_server]
port=192.168.255.124:9001