一尘不染

如何在nginx后面正常重启运行fcgi的django?

django

我正在使用fcgi(通过使用manage.py runfcgi命令)连接的nginx后面运行django实例。由于代码已加载到内存中,因此我无法在不终止并重新启动django fcgi进程的情况下重新加载新代码,从而中断了实时网站。重新启动本身非常快。但是通过首先终止fcgi进程,某些用户的操作将被打断,这是不好的。我想知道如何在不引起任何中断的情况下重新加载新代码。忠告将不胜感激!


阅读 295

收藏
2020-04-02

共2个答案

一尘不染

我将在新端口上启动一个新的fcgi进程,将nginx配置更改为使用新端口,进行nginx重载配置(其本身是正常的),然后最终停止旧进程(可以使用netstat来查找何时与旧端口的最后一个连接已关闭)。

或者,你可以更改fcgi实现以派生一个新进程,关闭子进程中除fcgi服务器套接字之外的所有套接字,关闭父进程中的fcgi服务器套接字,在子进程中执行一个新的django进程(使其使用fcgi服务器套接字),并在所有fcgi连接都关闭后终止父进程。IOW,为runfcgi实现正常重启。

2020-04-02
一尘不染

因此,我继续执行了马丁的建议。这是我想到的bash脚本。

pid_file=/path/to/pidfile
port_file=/path/to/port_file
old_pid=`cat $pid_file`

if [[ -f $port_file ]]; then
    last_port=`cat $port_file`
    port_to_use=$(($last_port + 1))
else
    port_to_use=8000
fi

# Reset so me don't go up forever
if [[ $port_to_use -gt 8999 ]]; then
    port_to_use=8000
fi

sed -i "s/$old_port/$port_to_use/g" /path/to/nginx.conf

python manage.py runfcgi host=127.0.0.1 port=$port_to_use maxchildren=5 maxspare=5 minspare=2 method=prefork pidfile=$pid_file

echo $port_to_use > $port_file

kill -HUP `cat /var/run/nginx.pid`

echo "Sleeping for 5 seconds"
sleep 5s

echo "Killing old processes on $last_port, pid $old_pid"
kill $old_pid
2020-04-02