supervisor管理服务器的进程——守护进程

前言

最近因为公司产线服务器发生了kafka进程崩溃的情况。查了查,官网跟我说是个bug,升级版本就好了。有的时候,情况就是这么崩溃。于是,守护进程的事就这么提上日程了。同事研究了supervisor,现在我们进程的状态查询,守护,开机启动都可以用它做。这让我看到了服务器进程的管理。之前我研究写shell脚本那叫一个头疼呀,直到这次我看到了这个东西,我看到了光。然后,我意识到,之前或许我的运维连门都还没有入。怎么办呢?学吧。学习下平头哥嘛,不是在学习就是在寻找学习的目标。

安装

很奇怪的是官网居然找不到下载地址。官网的下载地址我居然是在百度搜到的。放在这里吧,以防我以后找不到: https://pypi.org/project/supervisor/
我们下tar包即可。
考到/opt里面
补充一句,我的系统是centos8

tar zxvf supervisor-4.1.0.tar.gz
mv supervisor-4.1.0 supervisor
cd supervisor
#这时我发现我没装python
sudo dnf install python2
python2 setup.py install

值得注意的是,这里需要用python2,因为我试过python3了,不可以,嗯,就是这样。
然后,我们输入这个命令:echo_supervisord_conf 可以看到一大啪啦的信息,就说明我们成功了。

配置

创建初始化配置文件

mkdir /usr/supervisor #创建配置文件目录
echo_supervisord_conf > /usr/supervisor/supervisord.conf   #创建初始配置文件
mkdir /usr/supervisor/supervisord.d/  #为了不将所有新增配置信息全写在一个配置文件里,这里新建一个文件夹

在/usr/supervisor/supervisord.conf 引入/usr/supervisor/supervisord.d/中的配置文件 。开放配置末尾的include注释,改为:

[include]
files = /usr/supervisor/supervisord.d/*.conf

去掉[inet_http_server]的注释,使用web查看进程

[inet_http_server]         ; inet (TCP) server disabled by default
port=*:9001        ; ip_address:port specifier, *:port for all iface
username=root              ; default is no username (open server)
password=123456              ; default is no password (open server)

把所有的/tmp的目录改到一个你指定的目录中去,在/tmp中文件会被删除,会导致使用命令对进程进行操作时操作失败,因为找不到对应的sock文件了。

启动

supervisord -c /usr/supervisor/supervisord.conf

开机启动

vim /lib/systemd/system/supervisor.service

[Unit]
Description=supervisor
After=network.target

[Service]
Type=forking
ExecStart=/usr/bin/supervisord -c /usr/supervisor/supervisord.conf
PrivateTmp=true

[Install]
WantedBy=multi-user.target


systemctl enable supervisor.service
systemctl start supervisor.service

配置进程

##kafka
kafka配置文件/usr/supervisor/supervisord.d/kafka.conf

[program:kafka-service] ;程序名称,终端控制时需要的标识
command=/opt/kafka/bin/kafka-server-start.sh /opt/kafka/config/server.properties
directory=/opt/kafka/bin ; 命令执行的目录
numprocs=1 ; 启动几个进程
autorestart=true ; 程序意外退出是否自动重启
user=root ; 进程执行的用户身份
priority=2 ;
stderr_logfile=/home/supervisorlog/kafka-service.log ;日志文件

zookeeper

zookeeper配置文件/usr/supervisor/supervisord.d/zookeeper.conf

[program:zookeeper-service] ;程序名称,终端控制时需要的标识
command=/opt/zookeeper/bin/zkServer.sh start-foreground
directory=/opt/zookeeper/bin ; 命令执行的目录
numprocs=1 ; 启动几个进程
autorestart=true ; 程序意外退出是否自动重启
user=root ; 进程执行的用户身份
priority=1 ;
stderr_logfile=/home/supervisorlog/zookeeper-service.log ;日志文件

redis

redis配置文件/usr/supervisor/supervisord.d/redis-6379.conf

[program:redis-6379] ;程序名称,终端控制时需要的标识
command=/usr/local/bin/redis-server /etc/redis/6379.conf
directory=/opt/redis/src ; 命令执行的目录
numprocs=1 ; 启动几个进程
autorestart=true ; 程序意外退出是否自动重启
user=root ; 进程执行的用户身份
stderr_logfile=/home/supervisorlog/redis-6379.log ;日志文件

这里redis有一个注意事项,就是必须把配置文件里的daemon改成no。如果后台启动,则supervisor会认为进程起了就挂了,然后反复启动,但是其实redis是启动起来了,后来反复启动的都会因为端口占用而启动失败。

重启进程后,访问web端,就可以看到进程启动起来了。以后就可以通过网页看服务器有哪些进程,手动点击重启了。

tomcat

[program:jenkins] ;程序名称,终端控制时需要的标识
command=/opt/jenkins/apache-tomcat-9.0.30/bin/catalina.sh run
directory=/opt/jenkins/apache-tomcat-9.0.30/bin ; 命令执行的目录
numprocs=1 ; 启动几个进程
autorestart=true ; 程序意外退出是否自动重启
user=root ; 进程执行的用户身份
priority=2 ;
stderr_logfile=/home/supervisorlog/jenkins.log ;日志文件

这个tomcat是我之前为了配置jenkins的开机启动而配成了使用tomcat启动,而不是直接启动war包。懒得该回去了。同样的,tomcat的也存在后台启动导致重复启动最后失败的情况。解决方法是,把start.sh替换成catalina.sh run 即可。

常用操作

  • update 更新新的配置到supervisord(不会重启原来已运行的程序)
  • reload,载入所有配置文件,并按新的配置启动、管理所有进程(会重启原来已运行的程序)
  • start xxx: 启动某个进程
  • restart xxx: 重启某个进程
  • stop xxx: 停止某一个进程(xxx),xxx为[program:theprogramname]里配置的值
  • stop groupworker: 重启所有属于名为groupworker这个分组的进程(start,restart同理)
  • stop all,停止全部进程,注:start、restart、stop都不会载入最新的配置文
  • reread,当一个服务由自动启动修改为手动启动时执行一下就ok

备注

关于supervisor的使用我主要参考了这篇博客: https://www.cnblogs.com/toutou/p/supervisor.html 非常感谢。

错误排查

No module named setuptools

yum install python-setuptools

重启报错

supervisor是有命令可以重新加载配置文件,并重启相关进程的,但是,我发现执行这些命令的时候报了找不到sock文件的错误。经过检索,发现sock、pid和log文件默认都是放在tmp的,把它们挪到我们准备好的目录里面去,就可以了。具体就是,修改你的supervisor.conf配置文件

上一篇:enter_supervisor_mode


下一篇:Docker环境部署Django+Supervisor+Nginx