Nginx 进阶
Nginx 请求处理流程
Nginx 的请求处理流程大体是这样的:接收到 WEB、EMAIL、TCP 流量后,因为 Nginx 采用的非阻塞的事件驱动处理引擎,所以会有传输层状态机处理 TCP 流量,HTTP 状态机处理 WEB 流量,MAIL 状态机处理 EMAIL 流量,然后进行静态资源访问,如果是反向代理还能加入磁盘缓存,当分配的内存不足以完全缓存文件内容时,例如 sendfile 等大文件时,会退化成阻塞的磁盘调用,所以还会使用线程池处理磁盘阻塞调用,对于每一个处理完成的请求,会记录 Access 访问日志和 Error 错误日志,Nginx 作为负载均衡使用时,可以把请求通过协议机传输到后面的服务器。
Nginx 架构
Nginx 可以分为单进程和多进程模式,单进程一般作为调试开发使用,在生产环境一般用多进程。
Nginx 多进程模式,有一个主进程和其他子进程(包括 Worker 进程 和 cache 相关进程:Cache manager、Cache loader)。主进程的主要工作是加载和执行配置文件,并且驻留子进程。子进程用来作为实际的请求处理。Nginx 采取基于事件的模型和 OS 依赖的机制,在多个子进程之间高效的分配请求。子进程的个数会直接写在配置文件中,并且对于给定的配置可以是固定的,也可以根据可用的 CPU 核数自动进行调整。缓存相关的内容是各进程共享的,反向代理时,Cache manager 进程管理上游的缓存,Cache loader 进程载入上游的缓存。
Nginx 进程管理:信号
Nginx 的多进程通信是使用的共享内存方式,Nginx 的进程管理使用的是信号。
Master 进程
监控 Worker 进程
Master 进程会监控 Worker 进程有没有发来的 CHLD 信号,Linux 系统规定,当子进程终止时,会向父进程发送 CHLD 信号。当 Worker 进程因为某些原因报错终止时,会向 Master 进程发送 CHLD 信号,Master 进程接收到信号后,会拉起一个新的 Worker 进程。
管理 Worker 进程
Master 进程会接收到一些信号来管理 Worker 进程。
既可以使用 Nginx 命令行,也可以使用 kill 指令的方式接收的信号有以下几种:
TERM,INT 立刻停止 Nginx 进程,对应
nginx -s stop
QUIT 优雅停止,对应
nginx -s quit
HUP 重新载入配置文件,对应
nginx -s reload
USR1 重新打开日志文件,做日志切割,对应
nginx -s reopen
以上几种信号用 Nginx 命令行可以起到同样的作用是因为,Nginx 在启动时,一般会默认在 Nginx 安装目录的 logs 文件夹下 nginx.pid 中记录 Nginx 的 Master 进程 pid,在执行 nginx -s 命令时,这个命令行工具会向 nginx.pid 记录的 pid 发送相应的信号。
只能使用 kill 指令的方式接收的信号:
USR2
WINCH
Worker 进程
Worker 进程也可以接收一些信号,只能使用 kill + 进程 id 的方式:
TERM,INT
QUIT
USR1
WINCH
通常我们不直接对 Worker 进程发送信号,因为规范的方式是通过 Master 进程来管理 Worker 进程
Nginx reload 流程
向 Master 进程发送 HUP 信号(reload 命令)
Master 进程校验配置语法是否正确
Master 进程打开新的监听端口(如果有新端口的话,因为子进程的端口会继承父进程的端口)
Master 进程用新配置启动新的 Worker 子进程
Master 进程向老 Worker 子进程发送 QUIT 信号
老 Worker 子进程关闭监听句柄,处理完当前连接后结束进程(为了避免老 Worker 子进程长时间存在,可以设置 worker_shutdown_timeout 超时时间)
Nginx 热升级流程
将旧 Nginx 文件换成新 Nginx 文件(注意备份)
向 master 进程发送 USR2 信号
master 进程修改 pid 文件名,加后缀 .oldbin
master 进程用新 Nginx 文件启动新 master 进程
向老 master 进程发送 QUIT 信号,关闭老 master 进程
回滚:向老 master 发送 HUP,向新 master 发送 QUIT
worker 进程优雅关闭(quit)
设置定时器 worker_shutdown_timeout
关闭监听句柄
关闭空闲连接
在循环中等待全部连接关闭(时间可能会较长,当超过 worker_shutdown_timeout 设置的时间,worker 进程会把剩下的连接直接关闭)
退出进程
共享内存
跨 worker 进程通信的关键是共享内存,官方 Nginx 模块使用了共享内存的有以下几个:
ngx_http_lua_api
rbtree 数据结构
ngx_stream_limit_conn_module
ngx_http_limit_conn_module
ngx_stream_limit_req_module
http cache 相关
ngx_http_file_cache
ngx_http_proxy_module
ngx_http_scgi_module
ngx_http_uwsgi_module
ngx_http_fastcgi_module
ssl 相关
ngx_http_ssl_module
ngx_mail_ssl_module
ngx_stream_ssl_module
单链表数据结构
ngx_http_upstream_zone_module
ngx_stream_upstream_zone_module
Last updated
Was this helpful?