为什么要对 nginx 平滑升级,会有什么影响
1、为什么要对 nginx 平滑升级
随着 nginx 热度越来越高,并且其优势愈发显著,在这一过程中( nginx)的版本迭代也正以更加积极的姿态推进。1.9.0版的 nginx 推出了多项全新功能( stream)四层代理功能,在这一背景下( nginx)的功能更新频率也相应提高。伴随其在各个领域的广泛应用( nginx)的版本升级频率也越来越高。“线上业务不能停”在此背景下对 ( nginx) 进行升级便是运维工作的重点所在。
nginx 方便地帮助我们实现了平滑升级。其原理简单概括,就是:
(1)在不停掉老进程的情况下,启动新进程。
(2)老进程负责处理仍然没有处理完的请求,但不再接受处理请求。
(3)新进程接受新请求。
(4)老进程处理完所有请求,关闭所有连接后,停止。
通过这种方式实现了较为顺畅的升级过程。通常会有以下两种情况需要对 nginx 进行升级:其一是直接更新其版本信息;其二是引入新的功能模块。
Nginx信号简介
主进程支持的信号
- term, int: 立即终止
- quit: 将被延迟到工作进程完成后再执行
- kill: 强行终止当前运行的所有子进程
- hup: 首先重新加载配置文件后使用新配置启动主进程中止了这个过程
- usr1: 恢复日志文件的访问权限并打开现有日志记录
- usr2: 开始一个新的主进程中止了这个过程以实现热升级
- winch: 逐步地关闭当前运行的所有子进程中止了这个过程
工作进程支持的信号
TERM,INT: 立即终止QUIT: 在请求处理完成后再退出USR1: 重新开启日志文件
3、nginx 平滑升级实战
1、查看现有的 nginx 编译参数
[root@nginx-server ~]# cd /usr/local/nginx/sbin/nginx -V
按照原有的编译配置安装Nginx的方法进行操作,请确保只执行以下命令:只需运行bash make即可。切记不要执行bash make install!因为这可能会导致原有的配置文件被覆盖。
[root@nginx-server ~]# cd /usr/local/nginx-1.16.0/
[root@nginx-server nginx-1.16.0]# ./configure --prefix=/usr/local/nginx --group=nginx --user=nginx --sbin-path=/usr/local/nginx/sbin/nginx --conf-path=/etc/nginx/nginx.conf --error-log-path=/var/log/nginx/error.log --http-log-path=/var/log/nginx/access.log --http-client-body-temp-path=/tmp/nginx/client_body --http-proxy-temp-path=/tmp/nginx/proxy --http-fastcgi-temp-path=/tmp/nginx/fastcgi --pid-path=/var/run/nginx.pid --lock-path=/var/lock/nginx --with-http_stub_status_module --with-http_ssl_module --with-http_gzip_static_module --with-pcre --with-http_realip_module --with-stream --with-http_image_filter_module
[root@nginx-server nginx-1.16.0]# make
3、备份原 nginx 二进制文件
备份二进制文件和 nginx 的配置文件(期间nginx不会停止服务)
[root@nginx-server nginx-1.16.0]# mv /usr/local/nginx/sbin/nginx /usr/local/nginx/sbin/nginx_$(date +%F)
4、复制新的nginx二进制文件,进入新的nginx源码包
[root@nginx-server nginx-1.16.0]# cp /usr/local/nginx-1.16.0/objs/nginx /usr/local/nginx/sbin/
5、测试新版本的nginx是否正常
[root@nginx-server nginx-1.16.0]# /usr/local/nginx/sbin/nginx -t
6、给nginx发送平滑迁移信号(若不清楚pid路径,请查看nginx配置文件)
[root@nginx-server ~]# kill -USR2 `cat /var/run/nginx.pid`
7、查看nginx pid,会出现一个nginx.pid.oldbin
[root@nginx-server ~]# ll /var/run/nginx.pid*
-rw-r--r-- 1 root root 5 Jul 1 11:29 /var/run/nginx.pid
-rw-r--r-- 1 root root 5 Jul 1 09:54 /var/run/nginx.pid.oldbin
8、从容关闭旧的Nginx进程
[root@nginx-server ~]# kill -WINCH `cat /var/run/nginx.pid.oldbin`
9、此时不重载配置启动旧的工作进程
[root@nginx-server ~]# kill -HUP `cat /var/run/nginx.pid.oldbin`
10、结束工作进程,完成此次升级
[root@nginx-server ~]# kill -QUIT `cat /var/run/nginx.pid.oldbin`
11、验证Nginx是否升级成功
[root@nginx-server ~]# /usr/local/nginx/sbin/nginx -V
4、升级实验
1、安装配置1.6版本的 nginx ,重新开启一台机器
[root@localhost ~]# yum install -y gcc gcc-c++ pcre-devel openssl-devel zlib-devel
[root@localhost ~]# tar xzf nginx-1.6.3.tar.gz -C /usr/local/
[root@localhost ~]# cd /usr/local/nginx-1.6.3
[root@localhost nginx-1.6.3]# ./configure --prefix=/usr/local/nginx --user=nginx --group=nginx --with-http_stub_status_module
[root@localhost nginx-1.6.3]# make && make install
[root@localhost nginx-1.6.3]# useradd -M -s /sbin/nologin nginx
[root@localhost nginx-1.6.3]# /usr/local/nginx/sbin/nginx -t
nginx: the configuration file /usr/local/nginx/conf/nginx.conf syntax is ok
nginx: configuration file /usr/local/nginx/conf/nginx.conf test is successful
[root@localhost nginx-1.6.3]# /usr/local/nginx/sbin/nginx
[root@localhost nginx-1.6.3]# netstat -lntp
Proto Recv-Q Send-Q Local Address Foreign Address State PID/Program name
tcp 0 0 0.0.0.0:80 0.0.0.0:* LISTEN 13989/nginx: master
2、查看版本和模块
[root@localhost nginx-1.6.3]# /usr/local/nginx/sbin/nginx -V
nginx version: nginx/1.6.3
built by gcc 4.8.5 20150623 (Red Hat 4.8.5-36) (GCC)
configure arguments: --prefix=/usr/local/nginx --user=nginx --group=nginx --with-http_stub_status_module
[root@localhost nginx-1.6.3]# echo "nginx1.6" > /usr/local/nginx/html/index.html
[root@localhost nginx-1.6.3]# yum install -y elinks
4、访问验证
[root@localhost nginx-1.6.3]# elinks 10.0.105.189

5、升级nginx
将 nginx 版本进行升级 并在不影响业务的情况下添加 SSL 和 pcre 模块
[root@localhost ~]# tar xzf nginx-1.12.2.tar.gz -C /usr/local/
[root@localhost ~]# cd /usr/local/nginx-1.12.2/
[root@localhost nginx-1.12.2]# ./configure --prefix=/usr/local/nginx --user=nginx --group=ngiinx --with-http_stub_status_module --with-http_ssl_module --with-pcre
[root@localhost nginx-1.12.2]# make
[root@localhost nginx-1.12.2]# cd
[root@localhost ~]# mv /usr/local/nginx/sbin/nginx /usr/local/nginx/sbin/nginx_lod
[root@localhost ~]# cp /usr/local/nginx-1.12.2/objs/nginx /usr/local/nginx/sbin/
[root@localhost ~]# mv /usr/local/nginx/conf/nginx.conf /usr/local/nginx/conf/nginx.conf.bak
[root@localhost ~]# kill -USR2 `cat /usr/local/nginx/logs/nginx.pid`
[root@localhost ~]# ls /usr/local/nginx/logs/
access.log error.log nginx.pid
[root@localhost ~]# ps aux | grep nginx
root 13989 0.0 0.0 24860 952 ? Ss 13:55 0:00 nginx: master process /usr/local/nginx/sbin/nginx
nginx 13990 0.0 0.1 25284 1720 ? S 13:55 0:00 nginx: worker process
root 16525 0.0 0.0 112708 976 pts/2 S+ 14:09 0:00 grep --color=auto nginx

16、nginx 错误页面配置
nginx错误页面包括404 403 500 502 503 504等页面,只需要在server中增加以下配置即可:
#error_page 404 403 500 502 503 504 /404.html;
location = /404.html {
root /usr/local/nginx/html;
}
注意:
/usr/local/nginx/html/ 路径下必须有404.html这个文件!!!
当在404.html中引用其他文件中的png或css时会遇到问题,并且无法正确显示;这是因为访问其他文件也需要配置相关参数。为了简化处理流程,建议将css代码嵌入到页面资源中,并使用base64编码的方式将图片嵌入到页面资源中。如下:
[root@localhost html]# vim 404.html
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1, maximum-scale=1" />
<title>404</title>
<style>
.layout-table{display:table;height:100%;width:100%;vertical-align: middle;margin-top:150px}
.layout-table-cell{display: table-cell;vertical-align: middle;text-align:center}
.layout-tip{font-size:28px;color:#373737;margin: 0 auto;margin-top:16px;border-bottom: 1px solid #eee;padding-bottom: 20px;width: 360px;}
#tips{font-size:18px;color:#666666;margin-top:16px;}
</style>
</head>
<body class="layui-layout-body">
<div class="layui-layout layui-layout-admin">
<div class="layui-body">
<div class="layout-table">
<div class="layout-table-cell">
<img src="" class="layout-img">
<p class="layout-tip">哎呀,找不到该页面啦!</p>
<p id="tips">请检查您的网络连接是否正常或者输入的网址是否正确</p>
</div>
</div>
</div>
</div>
</body>
</html>
展示效果;

