Nginx平滑升级与回滚

Nginx平滑升级

为什么要对 Nginx 平滑升级?

Nginx作为一般互联网系统的门户,承载着巨量的流量,同时Nginx版本迭代也越来越快,新版本功能更丰富,安全性也更高。线上业务不能停,此时 Nginx 的升级就是运维的工作了。

Nginx 自带的信号量机制方便地帮助我们实现了不停机的平滑升级。其原理简单概括,就是:

  • 在不停掉旧进程的情况下,启动新进程。
  • 旧进程负责处理仍然没有处理完的请求,但不再接受处理请求。
  • 新进程接受新请求。
  • 旧进程处理完所有请求,关闭所有连接后,停止进程。

一般有两种情况下需要升级 Nginx,一种是要升级 Nginx 的版本,另一种是要为 Nginx 添加新的模块

Nginx信号简介

Nginx是多进程模型,分为主进程与工作进程。

主进程支持的信号

  • TERM, INT:立刻退出
  • QUIT:等待工作进程结束后再退出
  • KILL:强制终止进程
  • HUP:重新加载配置文件,使用新的配置启动工作进程,并逐步关闭旧进程。
  • USR1:重新打开日志文件
  • USR2:启动新的主进程,实现热升级
  • WINCH:逐步关闭工作进程

工作进程支持的信号

  • TERM, INT:立刻退出
  • QUIT:等待请求处理结束后再退出
  • USR1:重新打开日志文件

有关文档官网链接:Controlling Nginx

Nginx 不停机平滑升级实战

  • nginx-1.18.0 --> nginx-1.20.2

查看现有的 nginx 编译参数

/usr/local/nginx/sbin/nginx -V
  • 注意是大写的V

按照原来的编译参数安装 Nginx 的方法进行安装,只需要到 make,千万不要 make install。如果make install 会将原来的配置文件覆盖

本博文的 Nginx 编译参数为

./configure \
	--prefix=/usr/local/nginx \
	--pid-path=/var/run/nginx/nginx.pid \
	--lock-path=/var/lock/nginx.lock \
	--error-log-path=/var/log/nginx/error.log \
	--http-log-path=/var/log/nginx/access.log \
	--with-http_stub_status_module \
	--with-http_ssl_module

备份原 Nginx 二进制文件

备份二进制文件和 Nginx 的配置文件(期间Nginx不会停止服务)

mv /usr/local/nginx/sbin/nginx /usr/local/nginx/sbin/nginx-1.18.0

复制新的 Nginx 二进制文件,进入新的 Nginx 源码包

cp /usr/local/nginx-1.20.2/objs/nginx /usr/local/nginx/sbin/

测试新版本的 Nginx 是否正常

/usr/local/nginx/sbin/nginx -t

给 Nginx 发送平滑迁移信号

若不清楚pid路径,请查看 Nginx 配置文件

cat /var/run/nginx/nginx.pid
# 或者
ps -ef | grep nginx

发送信号

kill -USR2 $(cat /var/run/nginx/nginx.pid)

此时在/var/run/nginx下会出现一个nginx.pid.oldbin文件,存放旧master进程的pid

关闭旧的 Nginx 工作进程

kill -WINCH $(cat /var/run/nginx/nginx.pid.oldbin)

结束主进程,完成此次升级(可选)

kill -QUIT $(cat /var/run/nginx/nginx.pid.oldbin)

Nginx 版本回滚

对于升级来说,最难的不是升级,而是回滚,因为在实际生产环境回滚的机率是存在,比如:新版本由于某些未知bug导致与现有应用不兼容、或出现运行不稳定的情况等等。

所以,对运维工程师来说,故障回滚是重点。

在上面的结果中,我们也能看到老的master进程是一直存在,在没有手工关闭前,它是不会自已关闭的,这种设计是有好处的,好处就是为了升级新版本后,如果出现问题能及时快速的回滚到上一个稳定版本。

mv /usr/local/nginx/sbin/nginx /usr/local/nginx/sbin/nginx-1.20.2
mv /usr/local/nginx/sbin/nginx-1.18.0 /usr/local/nginx/sbin/nginx
kill -HUP $(cat /var/run/nginx/nginx.pid.oldbin)
kill -WINCH $(cat /var/run/nginx/nginx.pid)
  • 注意:新版本的主进程也没有关闭,同时nginx.pid中的pid也会变成回滚版本的

最后编辑时间:2023年8月28日08:39:29

posted @ 2023-08-28 06:15  tothk  阅读(196)  评论(0编辑  收藏  举报