控制 nginx
更改配置 旋转日志文件 在运行时升级可执行文件 |
nginx 可以通过信号进行控制。默认情况下,主进程的进程ID会被写入文件 /usr/local/nginx/logs/nginx.pid
。这个名称可以在配置时更改,或者在 nginx.conf
中使用 pid 指令进行更改。主进程支持以下信号:
TERM, INT 快速关闭 QUIT 优雅关闭 HUP 更改配置,跟踪更改的时区(仅适用于 FreeBSD 和 Linux),使用新配置启动新的工作进程,优雅关闭旧的工作进程 USR1 重新打开日志文件 USR2 升级可执行文件 WINCH 优雅关闭工作进程
单个工作进程也可以通过信号进行控制,但这不是必需的。支持的信号包括:
TERM, INT 快速关闭 QUIT 优雅关闭 USR1 重新打开日志文件 WINCH 用于调试的异常终止(需要启用 debug_points)
更改配置
为了让 nginx 重新读取配置文件,应向主进程发送一个 HUP 信号。主进程首先检查语法的有效性,然后尝试应用新的配置,即打开日志文件和新的监听套接字。如果失败,则回滚更改并继续使用旧配置工作。如果成功,则启动新的工作进程,并向旧的工作进程发送消息请求它们优雅地关闭。旧的工作进程关闭监听套接字并继续服务旧的客户端。在所有客户端服务完成后,旧的工作进程被关闭。
让我们通过例子来说明这一点。想象一下,nginx 在 FreeBSD 上运行,并且执行以下命令:
ps axw -o pid,ppid,user,%cpu,vsz,wchan,command | egrep '(nginx|PID)'
产生以下输出:
PID PPID USER %CPU VSZ WCHAN COMMAND 33126 1 root 0.0 1148 pause nginx: master process /usr/local/nginx/sbin/nginx 33127 33126 nobody 0.0 1380 kqread nginx: worker process (nginx) 33128 33126 nobody 0.0 1364 kqread nginx: worker process (nginx) 33129 33126 nobody 0.0 1364 kqread nginx: worker process (nginx)
如果向主进程发送 HUP 信号,则输出变为:
PID PPID USER %CPU VSZ WCHAN COMMAND 33126 1 root 0.0 1164 pause nginx: master process /usr/local/nginx/sbin/nginx 33129 33126 nobody 0.0 1380 kqread nginx: worker process is shutting down (nginx) 33134 33126 nobody 0.0 1368 kqread nginx: worker process (nginx) 33135 33126 nobody 0.0 1368 kqread nginx: worker process (nginx) 33136 33126 nobody 0.0 1368 kqread nginx: worker process (nginx)
具有 PID 33129 的一个旧的工作进程仍然在工作。过一段时间后它退出:
PID PPID USER %CPU VSZ WCHAN COMMAND 33126 1 root 0.0 1164 pause nginx: master process /usr/local/nginx/sbin/nginx 33134 33126 nobody 0.0 1368 kqread nginx: worker process (nginx) 33135 33126 nobody 0.0 1368 kqread nginx: worker process (nginx) 33136 33126 nobody 0.0 1368 kqread nginx: worker process (nginx)
日志文件轮转
为了轮转日志文件,它们需要首先被重命名。之后应该向主进程发送 USR1 信号。主进程将重新打开所有当前打开的日志文件,并为它们分配一个非特权用户,即工作进程正在以该用户身份运行的所有者。成功重新打开后,主进程关闭所有打开的文件,并向工作进程发送消息,要求它们重新打开文件。工作进程也会立即打开新文件并关闭旧文件。因此,旧文件几乎立即可用于后续处理,例如压缩。
动态升级可执行文件
为了升级服务器可执行文件,首先应该将新的可执行文件放在旧文件的位置。然后应该向主进程发送 USR2 信号。主进程首先将其带有进程 ID 的文件重命名为带有 .oldbin
后缀的新文件,例如 /usr/local/nginx/logs/nginx.pid.oldbin
,然后启动一个新的可执行文件,该文件又启动新的工作进程:
PID PPID USER %CPU VSZ WCHAN COMMAND 33126 1 root 0.0 1164 pause nginx: master process /usr/local/nginx/sbin/nginx 33134 33126 nobody 0.0 1368 kqread nginx: worker process (nginx) 33135 33126 nobody 0.0 1380 kqread nginx: worker process (nginx) 33136 33126 nobody 0.0 1368 kqread nginx: worker process (nginx) 36264 33126 root 0.0 1148 pause nginx: master process /usr/local/nginx/sbin/nginx 36265 36264 nobody 0.0 1364 kqread nginx: worker process (nginx) 36266 36264 nobody 0.0 1364 kqread nginx: worker process (nginx) 36267 36264 nobody 0.0 1364 kqread nginx: worker process (nginx)
之后,所有工作进程(旧的和新的)继续接受请求。如果向第一个主进程发送 WINCH 信号,则它将向其工作进程发送消息,要求它们正常关闭,并且它们将开始退出:
PID PPID USER %CPU VSZ WCHAN COMMAND 33126 1 root 0.0 1164 pause nginx: master process /usr/local/nginx/sbin/nginx 33135 33126 nobody 0.0 1380 kqread nginx: worker process is shutting down (nginx) 36264 33126 root 0.0 1148 pause nginx: master process /usr/local/nginx/sbin/nginx 36265 36264 nobody 0.0 1364 kqread nginx: worker process (nginx) 36266 36264 nobody 0.0 1364 kqread nginx: worker process (nginx) 36267 36264 nobody 0.0 1364 kqread nginx: worker process (nginx)
过一段时间后,只有新的工作进程会处理请求:
PID PPID USER %CPU VSZ WCHAN COMMAND 33126 1 root 0.0 1164 pause nginx: master process /usr/local/nginx/sbin/nginx 36264 33126 root 0.0 1148 pause nginx: master process /usr/local/nginx/sbin/nginx 36265 36264 nobody 0.0 1364 kqread nginx: worker process (nginx) 36266 36264 nobody 0.0 1364 kqread nginx: worker process (nginx) 36267 36264 nobody 0.0 1364 kqread nginx: worker process (nginx)
应该注意,旧的主进程不会关闭其监听套接字,如果需要,它可以管理重新启动其工作进程。如果由于某种原因新的可执行文件无法接受,则可以执行以下操作之一:
-
向旧的主进程发送 HUP 信号。旧的主进程将启动新的工作进程,而不重新读取配置。之后,所有新进程可以通过向新的主进程发送 QUIT 信号来正常关闭。
-
向新的主进程发送 TERM 信号。然后,它将向其工作进程发送消息,要求它们立即退出,它们将几乎立即全部退出。(如果由于某种原因新进程没有退出,则应向它们发送 KILL 信号以强制它们退出。)新的主进程退出后,旧的主进程将自动启动新的工作进程。
如果新的主进程退出,则旧的主进程会丢弃带有进程 ID 的文件名中的 .oldbin
后缀。
如果升级成功,则应向旧的主进程发送 QUIT 信号,只有新的进程会保留:
PID PPID USER %CPU VSZ WCHAN COMMAND 36264 1 root 0.0 1148 pause nginx: master process /usr/local/nginx/sbin/nginx 36265 36264 nobody 0.0 1364 kqread nginx: worker process (nginx) 36266 36264 nobody 0.0 1364 kqread nginx: worker process (nginx) 36267 36264 nobody 0.0 1364 kqread nginx: worker process (nginx)