NGINX 能在 web 性能中取得领先地位,这是由于其软件设计所决定的。许多 web 服务器和应用程序服务器使用一个简单的线程或基于流程的架构,NGINX 立足于一个复杂的事件驱动的体系结构,使它能够在现代硬件上扩展到成千上万的并发连接。
下面这张深入 NGINX 的信息图从高层次的流程架构深度挖掘说明了 NGINX 如何在单一进程里保持多个连接。这篇博客进一步详细地解释了这一切是如何工作的。
知识 – NGINX进程模型为了更好的理解这个设计,你需要理解 NGINX 如何运行的。NGINX 有一个主进程(它执行特权操作,如读取配置和绑定端口)和一些工作进程与辅助进程。
# service nginx restart
*Restarting nginx
# ps -ef --forest | grep nginx
root 324751013:36?00:00:00 nginx: master process /usr/sbin/nginx \
-c /etc/nginx/nginx.conf
nginx 3247632475013:36?00:00:00 \_ nginx: worker process
nginx 3247732475013:36?00:00:00 \_ nginx: worker process
nginx 3247932475013:36?00:00:00 \_ nginx: worker process
nginx 3248032475013:36?00:00:00 \_ nginx: worker process
nginx 3248132475013:36?00:00:00 \_ nginx: cache manager process
nginx 3248232475013:36?00:00:00 \_ nginx: cache loader process
在四核服务器,NGINX 主进程创建了4个工作进程和两个管理磁盘内容缓存的缓存辅助进程。
为什么架构很重要?任何 Unix 应用程序的根本基础是线程或进程。(从 Linux 操作系统的角度来看,线程和进程大多是相同的,主要的区别是他们共享内存的程度。)一个线程或进程是一个自包含的指令集,操作系统可以在一个 CPU 核心上调度运行它们。大多数复杂的应用程序并行运行多个线程或进程有两个原因:
它们可以同时使用更多的计算核心。
线程或进程可以轻松实现并行操作。(例如,在同一时刻保持多连接)。
进程和线程消耗资源。他们每个都使用内存和其他系统资源,他们会在 CPU 核心中换入和换出(一个操作可以叫做上下文切换)。大多数现代服务器可以并行保持上百个小型的、活动的线程或进程,但是一旦内存耗尽或高 I/O 压力引起大量的上下文切换会导致性能严重下降。
网络应用程序设计的常用方法是为每个连接分配一个线程或进程。此体系结构简单、容易实现,但是当应用程序需要处理成千上万的并发连接时这种结构就不具备扩展性。
NGINX 如何工作?NGINX 使用一种可预测的进程模式来分配可使用的硬件资源:
主进程(master)执行特权操作,如读取配置和绑定端口,然后创建少量的子进程(如下的三种类型)。
缓存加载器进程(cache loader)在加载磁盘缓存到内存中时开始运行,然后退出。适当的调度,所以其资源需求很低。
缓存管理器进程(cache manager)定期裁剪磁盘缓存中的记录来保持他们在配置的大小之内。
工作进程(worker)做所有的工作!他们保持网络连接、读写内容到磁盘,与上游服务器通信。