Web 服务基石 Nginx
NGINX
Nginx是一款由俄罗斯程序员 Igor Sysoev 开发的 轻量级、高性能的 HTTP 和反向代理服务器,同时也是一个 IMAP/POP3/SMTP 代理服务器。自 2004 年首次发布以来,Nginx 凭借其 高并发处理能力、低内存消耗和稳定性,成为全球最受欢迎的 Web 服务器之一,广泛应用于静态资源服务、反向代理、负载均衡、API 网关等场景
NGINX安装
源码编译

#解压压缩包 tar zxf nginx-1.24.0.tar.gz cd nginx-1.24.0 #编译 ./configure --prefix=/usr/local/nginx --user=nginx --group=nginx --with-http_ssl_module -- with-http_v2_module --with-http_realip_module --with-http_stub_status_module --with-pcre -- with-stream --with-stream_ssl_module --with-stream_realip_module make make install
使用make和makeinstall编译和安装
验证版本以及编译参数

查看版本信息

自定义版本(在编译前编辑文件)
#编辑版本相关文件 [root@Webserver nginx-1.26.1]# vim src/core/nginx.h #define NGINX_VERSION "" #define NGINX_VER "xixihaha/" NGINX_VERSION

平滑升级和回滚
升级
解压并编译新版本:
[root@Nginx nginx]# tar zxf nginx-1.26.1.tar.gz [root@Nginx nginx]# cd nginx-1.26.1/ #开始编译新版本 [root@Nginx nginx-1.26.1]# ./configure --with-http_ssl_module --withhttp_v2_module --with-http_realip_module --with-http_stub_status_module --withhttp_gzip_static_module --with-pcre --with-stream --with-stream_ssl_module -- with-stream_realip_module #只要make无需要make install [root@Nginx nginx-1.26.1]# make查看两个版本:

1.把之前的旧版的nginx命令备份:

2.把新版本的nginx命令复制过去:

检测一下有没有问题

3.回收旧版本

↑旧版本的mast不想看见的话可以用kill -9 旧ID干掉

回滚
如果升级的版本发现问题需要回滚,可以重新拉起旧版本的worker
回滚文件:
↓做之前要先备份新版文件cp nginx nginx.26




编写Nginx启动文件systemd
#百度搜索模板 systemd site:nginx.org #搜索内容 site:搜索网址 [root@nginx ~]# cd /lib/systemd/system [root@nginx system]# vim nginx.service [Unit] Description=The NGINX HTTP and reverse proxy server After=syslog.target network.target remote-fs.target nss-lookup.target [Service] Type=forking PIDFile=/usr/local/nginx/logs/nginx.pid #指定nginx启动的pid ExecStartPre=/usr/local/nginx/sbin/nginx -t #指定nginx -t检查配置文件命令 ExecStart=/usr/local/nginx/sbin/nginx #指定nginx启动命令 ExecReload=/bin/kill -s HUP $MAINPID ExecStop=/bin/kill -s QUIT $MAINPID PrivateTmp=true [Install] WantedBy=multi-user.target #使编写的配置生效 [root@nginx system]# systemctl daemon-reload #在启动时要确保nginx已经关闭不然会冲突导致报错 [root@nginx system]# systemctl enable --now nginx Nginx配置文件参数详解
1.nginx主配置文件说明
主配置文件结构:四部分
main block:主配置段,即全局配置段 #事件驱动相关的配置 event { ... } #http/https 作为web服务器相关配置段 http { ... } #默认配置文件不包括下面两个部分 #mail 作为邮件服务器相关配置段 mail { ... } #stream 反向代理相关配置段 stream { ... } 2.全局配置块参数
默认打开全局配置参数
user nginx nginx; #启动Nginx工作进程的用户和组 worker_processes [number | auto]; #启动Nginx工作进程的数量,一般设为和CPU核心数相同,可以设置为auto同步cpu核心数 worker_cpu_affinity 00000001 00000010 00000100 00001000 | auto ; #将worker进程与cpu核数绑定,避免进程在不同核心上来回切换造成消耗 #示例 CPU MASK: 00000001:0号CPU 00000010:1号CPU 10000000:7号CPU worker_cpu_affinity 0001 0010 0100 1000;第0号---第3号CPU worker_cpu_affinity 0101 1010; worker_rlimit_nofile 100000; # 所有worker最多打开100000个文件描述符 # 最好与ulimit -n 或者limits.conf的值保持一致 #错误日志记录配置,语法:error_log file [debug | info | notice | warn | error | crit | alert | emerg] #error_log logs/error.log; #error_log logs/error.log notice; #error_log logs/error.log info; #pid文件保存路径 #pid logs/nginx.pid; 示例:cpu与核心绑定示例
worker_processes auto; worker_cpu_affinity 01 10; [root@nginx ~]# cat /proc/cpuinfo cpu cores : 6 [root@nginx ~]# vim /usr/local/nginx/conf/nginx.conf worker_processes auto; worker_cpu_affinity 000001 000010 000100 001000 010000 100000; [root@nginx ~]# nginx -t [root@nginx ~]# nginx -s reload [root@nginx ~]# ps aux | grep nginx root 881 0.0 0.0 11148 3352 ? Ss 15:18 0:00 nginx: master process /usr/local/nginx/sbin/nginx nginx 1450 0.0 0.1 15456 5132 ? S 15:20 0:00 nginx: worker process nginx 1451 0.0 0.1 15456 5004 ? S 15:20 0:00 nginx: worker process nginx 1452 0.0 0.1 15456 5132 ? S 15:20 0:00 nginx: worker process nginx 1453 0.0 0.1 15456 5004 ? S 15:20 0:00 nginx: worker process nginx 1454 0.0 0.1 15456 5004 ? S 15:20 0:00 nginx: worker process nginx 1455 0.0 0.1 15456 5004 ? S 15:20 0:00 nginx: worker process root 1457 0.0 0.0 6636 2304 pts/0 S+ 15:20 0:00 grep --color=auto nginx [root@nginx ~]# ps axo pid,cmd,psr | grep nginx 881 nginx: master process /usr/ 4 1450 nginx: worker process 0 1451 nginx: worker process 1 1452 nginx: worker process 2 1453 nginx: worker process 3 1454 nginx: worker process 4 1455 nginx: worker process 5 1459 grep --color=auto nginx 3 3.events块配置参数
[root@nginx ~]# vim /usr/local/nginx/conf/nginx.conf events { worker_connections 10000; #单个woker工作进程最大并发数 use epoll; #使用epoll机制来实现高并发 #Nginx支持众多的事件驱动, #比如:select、poll、epoll,只能设置在events模块中设置 accept_mutex on; #同一时刻一个请求访问只激活一个work进程赖处理 #不开启则一个请求到来唤醒所有worker,称为“惊群” #默认为off,on为开启 multi_accept on; #把数据缓存多个到一定程度,同时发送给worker处理 #不开启则实时发送,打开后worker进程可以同时接受多个网络请求 #默认为off,on为开启 } 示例:实现nginx高并发配置
[root@nginx ~]# vim /usr/local/nginx/conf/nginx.conf worker_rlimit_nofile 100000; events { use epoll; worker_connections 10000; } [root@nginx ~]# nginx -s reload #测试并发 [root@nginx ~]# dnf install httpd-tools -y [root@Nginx ~]# ab -n 100000 -c10000 http://172.25.254.100/index.html This is ApacheBench, Version 2.3 <$Revision: 1913912 $> Copyright 1996 Adam Twiss, Zeus Technology Ltd, http://www.zeustech.net/ Licensed to The Apache Software Foundation, http://www.apache.org/ Benchmarking 172.25.254.100 (be patient) socket: Too many open files (24) #并发数量过多导致访问失败 #处理本地文件系统的并发文件数量 [root@nginx ~]# vim /etc/security/limits.conf #永久生效但要重启 * - nofile 100000 #打开文件最大个数 * - noproc 100000 #打开程序最大个数 [root@nginx ~]# ulimit -n 100000 #临时生效 [root@nginx ~]# ulimit -n 100000 [root@bginx ~]# ab -n 100000 -c10000 http://172.25.254.100/index.html This is ApacheBench, Version 2.3 <$Revision: 1913912 $> Copyright 1996 Adam Twiss, Zeus Technology Ltd, http://www.zeustech.net/ Licensed to The Apache Software Foundation, http://www.apache.org/ Benchmarking 172.25.254.100 (be patient) Completed 10000 requests Completed 20000 requests Completed 30000 requests Completed 40000 requests Completed 50000 requests 4.http块配置参数
http块是Nginx服务器配置中的重要部分,缓存、代理和日志格式定义等绝大多数功能和第三方模块都可以在这设置,http块可以包含多个server块,而一个server块中又可以包含多个location块。
[root@nginx ~]# vim /usr/local/nginx/conf/nginx.conf http { #在响应报文中将指定的文件扩展名映射至MIME对应的类型 include mime.types; #可以识别文本,图像,音频,视频等其他的数据 default_type application/octet-stream; #没有识别的默认类型,例如php,ngxin不识别需要安装php才能渲染呈现 log_format main '$remote_addr - $remote_user [$time_local] "$request" ' '$status $body_bytes_sent "$http_referer" ' '"$http_user_agent" "$http_x_forwarded_for"'; access_log logs/access.log main; #使用定义为main的日志格式,存放在根目录的logs/access.log中 sendfile on; #零拷贝功能,sendfile系统调用在两个文件描述符之间直接传递数据(完全在内核中操作) #tcp_nopush on; #keepalive_timeout 0; keepalive_timeout 65; #长连接超时时间,单位是s #gzip on; #开启压缩功能 server { #web服务配置 } include "/usr/local/nginx/conf.d/*.conf"; #导入其他路径的配置文件,子配置文件 #要放在默认发布文件目录下,不然会覆盖默认示例:识别php文件为text/html类型
[root@nginx ~]# vim /usr/local/nginx/html/index.php <?php phpinfo() ?> [root@nginx ~]# curl -I 172.25.254.100/index.php HTTP/1.1 200 OK Server: nginx/1.26.1 Date: Sun, 03 Aug 2025 12:31:48 GMT Content-Type: application/octet-stream #php不属于mime类型中,所以使用默认 Content-Length: 23 Last-Modified: Sun, 03 Aug 2025 11:17:36 GMT Connection: keep-alive ETag: "688f4550-17" Accept-Ranges: bytes [root@Nginx ~]# vim /usr/local/nginx/conf/nginx.conf default_type text/html; [root@nginx ~]# curl -I 172.25.254.100/index.php HTTP/1.1 200 OK Server: nginx/1.26.1 Date: Sun, 03 Aug 2025 12:35:22 GMT Content-Type: text/html #将识别类型改为text/html Content-Length: 23 Last-Modified: Sun, 03 Aug 2025 11:17:36 GMT Connection: keep-alive ETag: "688f4550-17" Accept-Ranges: bytes [root@Nginx ~]# vim /usr/local/nginx/conf/nginx.conf default_type test/php; [root@nginx ~]# curl -I 172.25.254.100/index.php HTTP/1.1 200 OK Server: nginx/1.26.1 Date: Sun, 03 Aug 2025 12:35:22 GMT Content-Type: test/php #可以自定义将识别不出来的设为想要的类型 Content-Length: 23 Last-Modified: Sun, 03 Aug 2025 11:17:36 GMT Connection: keep-alive ETag: "688f4550-17" Accept-Ranges: bytes 基于域名的web站点发布
#创建基于域名的发布根目录 [root@nginx ~]# mkdir /webdata/nginx/czg.org/czg/html -p #生成发布文件 [root@nginx ~]# echo czg.czg.org > /webdata/nginx/czg.org/czg/html/index.html #创建子配置目录 [root@nginx ~]# mkdir /usr/local/nginx/conf.d #创建子配置文件 [root@nginx ~]# vim /usr/local/nginx/conf.d/vhosts.conf server { listen 80; server_name www.czg.org; root /webdata/nginx/czg.org/czg/html/; } [root@nginx ~]# vim /usr/local/nginx/conf/nginx.conf http { ...... include "/usr/local/nginx/conf.d/*.conf"; #放在server{}下面防止识别有误 } [root@nginx ~]# nginx -t [root@nginx ~]# nginx -s reload #添加本地解析 [root@nginx ~]# vim /etc/hosts #测试 [root@nginx ~]# curl www.czg.org fjw.czg.org location中的root与alias
root:指定web的家目录,在定义location的时候,文件的绝对路径等于 root+location
alias:定义路径别名,会把访问的路径重新定义到其指定的路径,文档映射的另一种机制;
访问路径为文件指定路径也要为文件则相当于软连接
访问路径为指定路径也要为目录然后查看目录下的index.html
location 的详细使用
在一个server中location配置段可存在多个,用于实现从uri到文件系统的路径映射
ngnix会根据用户请求的URI来检查定义的所有location,按一定的优先级找出一个最佳匹配
而后应用其配置在没有使用正则表达式的时候,nginx会先在server中的多个location选取匹配度最高的一个uri
uri是用户请求的字符串,即域名后面的web文件路径
然后使用该location模块中的正则url和字符串,如果匹配成功就结束搜索,并使用此location处理此请求
#语法规则: location [ = | ~ | ~* | ^~ ] uri { ... } = 用于标准uri前,需要请求字串与uri精确匹配,大小写敏感,如果匹配成功就停止向下匹配并立 即处理请求 ^~ 用于标准uri前,表示包含正则表达式,并且匹配以指定的正则表达式开头,对uri的最左边部分做匹配检查,区分字符大小写 ~ 用于标准uri前,表示包含正则表达式,并且区分大小写 ~* 用于标准uri前,表示包含正则表达式,并且不区分大小写 \ 用于标准uri前,表示包含正则表达式并且转义字符。可以将 . * ?等转义为普通符号 不带符号 #匹配起始于此uri的所有的uri #匹配优先级从高到低: =, ^~, ~/~*, 不带符号1.示例-精准匹配
[root@nginx ~]# vim /usr/local/nginx/conf.d/vhosts.conf
server {
listen 80;
server_name www.zg.org;
root /web/html;
index index.html;
location = /test {
return 200 "punct = \n"; #returun 200.只要访问/test无论是否存在都会返回200存在成功,并输出"punct = \n"
}
}
#测试
[root@nginx ~]# curl www.zg.org/test
punct =
[root@nginx ~]# curl www.zg.org/test1
<html>
<head><title>404 Not Found</title></head>
[root@nginx ~]# curl www.zg.org/1test
<html>
<head><title>404 Not Found</title></head>
<body>
<center><h1>404 Not Found</h1></center>
2.示例-正则前缀匹配
[root@nginx ~]# vim /usr/local/nginx/conf.d/vhosts.conf
server {
listen 80;
server_name www.zg.org;
root /web/html;
index index.html;
# location = /test {
# return 200 "punct = \n";
# }
location ^~ /test {
return 200 "punct = ^~\n";
}
}
#测试
[root@nginx ~]# curl www.zg.org/test
punct = ^~
[root@nginx ~]# curl www.zg.org/test/a/b
punct = ^~
[root@nginx ~]# curl www.zg.org/testc
punct = ^~
[root@nginx ~]# curl www.zg.org/aatestc
\<html>
<head><title>404 Not Found</title></head>
<body>
<center><h1>404 Not Found</h1></center>
<hr><center>nginx/1.26.1</center>
</body>
</html>
长连接配置
keepalive_timeout timeout [header_timeout]; #设定保持连接超时时长,0表示禁止长连接, 默认为75s #通常配置在http字段作为站点全局配置 keepalive_requests 数字; #在一次长连接上所允许请求的资源的最大数量 #默认为100次,建议适当调大,比如:500



NginxWeb页面账户认证
由 ngx_http_auth_basic_module 模块提供此功能
创建加密信息
#使用不了htpasswd时要下载httpd-tools包 #创建加密信息,-c创建,-m使用md5加密,-b非交互生成 [root@nginx ~]# htpasswd -cmb /usr/local/nginx/.htpasswd czg czg #进行创建后,想要添加用户认证信息不用加-c,-c参数会覆盖 [root@nginx ~]# htpasswd -mb /usr/local/nginx/.htpasswd czr czr [root@nginx ~]# cat /usr/local/nginx/.htpasswd czr:$apr1$rYDpBBuw$x701q1axSqvBDgXFV81QM/ czg:$apr1$OZHKwo15$YKoStu20qFtVls5la9fz50 编辑配置文件
[root@nginx ~]# vim /usr/local/nginx/conf.d/vhosts.conf server { listen 80; server_name www.czg.org; root /webdata/nginx/czg.org/czg/html; location /admin { root /usr/local/nginx/html; auth_basic "login passwd"; auth_basic_user_file "/usr/local/nginx/.htpasswd"; } } [root@nginx ~]# systemctl restart nginx.service [root@nginx ~]# mkdir /usr/local/nginx/html/admin/ [root@nginx ~]# echo admin > /usr/local/nginx/html/admin/index.html 测试
[root@nginx ~]# curl www.czg.org/admin/ [root@nginx ~]# curl www.czg.org/admin/ -uczg:czg
自定义错误页面
生成测试错误页面
[root@nginx ~]# mkdir /usr/local/nginx/errorpage [root@nginx ~]# echo "先睡了" > /usr/local/nginx/errorpage/errormessage编辑配置
[root@nginx ~]# vim /usr/local/nginx/conf.d/vhosts.conf server { listen 80; server_name www.czg.org; error_page 404 405 503 502 /error; #指定location的位置 location /czg/ { #不存在页面 root /usr/local/nginx/html; } location /error { alias /usr/local/nginx/errorpage/errormessage; } } #测试 [root@nginx ~]# curl www.czg.org/czg/ 先睡了自定义错误日志
编辑配置参数
[root@nginx ~]# mkdir -p /usr/local/nginx/logs/czg.org/ [root@nginx ~]# vim /usr/local/nginx/conf.d/vhosts.conf server { listen 80; server_name www.czg.org; error_page 404 405 503 502 /errorpage/errormessage; access_log logs/czg.org/czg.access; #这里的默认发布目录是主配置文件指定的默认发布目录,相对路径指定日志路径,可加main参数指定日志格式要在主配置文件开启日志格式参数 error_log logs/czg.org/czg.error error; #error为日志错误日志级别 location /fjw/ { root /usr/local/nginx/html; } location /errorpage/ { root /usr/local/nginx/; } } Nginx的文件检测
try_files会按顺序检查文件是否存在,返回第一个找到的文件或文件夹(结尾加斜线表示为文件夹),如 果所有文件或文件夹都找不到,会进行一个内部重定向到最后一个参数。
只有最后一个参数可以引起一 个内部重定向,之前的参数只设置内部URI的指向。
最后一个参数是回退URI且必须存在,否则会出现内 部500错误。
一般为最后一个参数创建一个默认页面
创建测试页面
[root@nginx ~]# echo default > /usr/local/nginx/errorpage/default.html编辑参数
[root@nginx ~]# vim /usr/local/nginx/conf.d/vhosts.conf server { listen 80; server_name www.czg.org; root /webdata/nginx/fjw.org/czg/html/; error_page 404 405 503 502 /errorpage/errormessage; access_log logs/fjw.org/czg.access; error_log logs/fjw.org/czg.error error; try_files $uri $uri.html $uri/index.html /errorpage/default.html; #如果都不存在就看default.html,而不是跳转到错误页面 location /errorpage/ { root /usr/local/nginx/; } } #测试 #访问不存在的路径不是跳转错误页面 [root@nginx ~]# curl www.czg.org/czg default [root@nginx ~]# curl www.czg.org/abcadad default 下载服务器
生成测试文件
[root@nginx ~]# mkdir -p /usr/local/nginx/download [root@nginx ~]# cp /etc/passwd /usr/local/nginx/download/ [root@nginx ~]# dd if=/dev/zero of=/usr/local/nginx/download/bigfile bs=1M count=100 编辑配置参数
[root@nginx ~]# cat /usr/local/nginx/conf.d/vhosts.conf server { listen 80; server_name www.czg.org; root /webdata/nginx/czg.org/czg/html/; error_page 404 405 503 502 /errorpage/errormessage; access_log logs/czg.org/czg.access; error_log logs/czg.org/czg.error error; try_files $uri $uri.html $uri/index.html /errorpage/default.html; location /errorpage/ { root /usr/local/nginx/; } location /download { root /usr/local/nginx; } } Nginx的状态页
基于nginx 模块 ngx_http_stub_status_module 实现, 在编译安装nginx的时候需要添加编译参数 --with-http_stub_status_module 否则配置完成之后监测会是提示法错误
状态页显示的是整个服务器的状态,而非虚拟主机的状态
[root@nginx ~]# vim /usr/local/nginx/conf.d/vhosts.conf server { listen 80; server_name www.czg.org; location /status { stub_status; #开启状态页功能 auth_basic "status page"; auth_basic_user_file "/usr/local/nginx/.htpasswd"; allow 172.25.254.0/24; deny all; } } [root@nginx ~]# nginx -t [root@nginx ~]# nginx -s reload #状态页信息参数 Active connections: #当前处于活动状态的客户端连接数 #包括连接等待空闲连接数=reading+writing+waiting accepts: #统计总值,Nginx自启动后已经接受的客户端请求连接的总数。 handled: #统计总值,Nginx自启动后已经处理完成的客户端请求连接总数 #通常等于accepts,除非有因worker_connections限制等被拒绝的连接 requests: #统计总值,Nginx自启动后客户端发来的总的请求数 Reading: #当前状态,正在读取客户端请求报文首部的连接的连接数 #数值越大,说明排队现象严重,性能不足 Writing: #当前状态,正在向客户端发送响应报文过程中的连接数,数值越大,说明访问量很大 Waiting: #当前状态,正在等待客户端发出请求的空闲连接数开启 keep-alive的情况下,这个值等于active – (reading+writing) Nginx的压缩功能
Nginx支持对指定类型的文件进行压缩然后再传输给客户端,而且压缩还可以设置压缩比例,压缩后的文 件大小将比源文件显著变小,样有助于降低出口带宽的利用率,降低企业的IT支出,不过会占用相 应的CPU资源。
Nginx对文件的压缩功能是依赖于模块 ngx_http_gzip_module,默认是内置模块。
配置参数如下
#启用或禁用gzip压缩,默认关闭
gzip on | off;
#压缩比由低到高从1到9,默认为1,值越高压缩后文件越小,但是消耗cpu比较高。基本设定未4或者5
gzip_comp_level 4;
#禁用IE6 gzip功能,早期的IE6之前的版本不支持压缩
gzip_disable "MSIE [1-6]\.";
#gzip压缩的最小文件,小于设置值的文件将不会压缩
gzip_min_length 1k;
#启用压缩功能时,协议的最小版本,默认HTTP/1.1
gzip_http_version 1.0 | 1.1;
#指定Nginx服务需要向服务器申请的缓存空间的个数和大小,平台不同,默认:32 4k或者16 8k;
gzip_buffers number size;
#指明仅对哪些类型的资源执行压缩操作;默认为gzip_types text/html,不用显示指定,否则出错
gzip_types mime-type ...;
#如果启用压缩,是否在响应报文首部插入“Vary: Accept-Encoding”,一般建议打开
gzip_vary on | off;
#预压缩,即直接从磁盘找到对应文件的gz后缀的式的压缩文件返回给用户,无需消耗服务器CPU
#注意: 来自于ngx_http_gzip_static_module模块
gzip_static on | off;
生成测试文件
[root@nginx ~]# echo smallfile > /usr/local/nginx/html/small.html [root@nginx ~]# cp /usr/local/nginx/logs/access.log /usr/local/nginx/html/bigfile.txt #大文件后缀为txt才被识别 开启压缩功能
[root@nginx ~]# vim /usr/local/nginx/conf/nginx.conf ...... gzip on; gzip_comp_level 4; gzip_disable "MSIE [1-6]\."; gzip_min_length 1024k; gzip_buffers 32 1024k; gzip_types text/plain application/javascript application/x-javascript text/css application/xml text/javascript application/x-httpd-php image/gif image/png; gzip_vary on; gzip_static on; ...... [root@nginx ~]# nginx -t [root@nginx ~]# nginx -s reload #做好主机的解析 [root@nginx ~]# vim /etc/hosts 测试
#--head 仅获取响应头,不下载正文 --compressed告知服务器可接受压缩格式的响应 [root@nginx ~]# curl --head --compressed www.czg.com/bigfile.txt [root@nginx ~]# curl --head --compressed www.czg.com/small.html Nginx 变量使用
常用内置变量
$remote_addr; #存放了客户端的地址,注意是客户端的公网IP $args; #变量中存放了URL中的所有参数 #例如:https://search.jd.com/Search?keyword=手机&enc=utf-8 #返回结果为: keyword=手机&enc=utf-8 $is_args #如果有参数为? 否则为空 $document_root; #保存了针对当前资源的请求的系统根目录,例如:/webdata/nginx/timinglee.org/lee。 $document_uri; #保存了当前请求中不包含参数的URI,注意是不包含请求的指令 #比如:http://lee.timinglee.org/var?\id=11111会被定义为/var #返回结果为:/var $host; #存放了请求的host名称 limit_rate 10240; echo $limit_rate; #如果nginx服务器使用limit_rate配置了显示网络速率,则会显示,如果没有设置, 则显示0 $remote_port; #客户端请求Nginx服务器时随机打开的端口,这是每个客户端自己的端口 $remote_user; #已经经过Auth Basic Module验证的用户名 $request_body_file; #做反向代理时发给后端服务器的本地资源的名称 $request_method; #请求资源的方式,GET/PUT/DELETE等 $request_filename; #当前请求的资源文件的磁盘路径,由root或alias指令与URI请求生成的文件绝对路径, #如:webdata/nginx/timinglee.org/lee/var/index.html $request_uri; #包含请求参数的原始URI,不包含主机名,相当于:$document_uri?$args, #例如:/main/index.do?id=20190221&partner=search $scheme; #请求的协议,例如:http,https,ftp等 $server_protocol; #保存了客户端请求资源使用的协议的版本,例如:HTTP/1.0,HTTP/1.1,HTTP/2.0等 $server_addr; #保存了服务器的IP地址 $server_name; #虚拟主机的主机名 $server_port; #虚拟主机的端口号 $http_user_agent; #客户端浏览器的详细信息 $http_cookie; #客户端的所有cookie信息 $cookie_<name> #name为任意请求报文首部字部cookie的key名 $http_<name> #name为任意请求报文首部字段,表示记录请求报文的首部字段,name的对应的首部字段名需要为小写,如果有 横线需要替换为下划线先备份原本的主和子配置文件
systemctl stop nginx
编译中添加插件:

make & make install 重新编译安装
将原来的主和子配置文件覆盖新的主和子配置文件
systemctl restart nginx
编辑配置文件:

自定义变量
[root@nginx ~]# vim /usr/local/nginx/conf.d/vhosts.conf server { listen 80; server_name www.czg.org; root /web/html; location /var { default_type text/html; set $name czg; echo $name; set $tomcat_port 8080; #手动设定 echo $tomcat_port; set $web_port $server_port #变量传递 } } #测试 [root@nginx ~]# curl www.czg.org/var czg 8080 80 Nginx Rewrite相关功能
Nginx服务器利用 ngx_http_rewrite_module 模块解析和处理rewrite请求
此功能依靠 PCRE(perl compatible regular expression),因此编译之前要安装PCRE库
rewrite是nginx服务器的重要功能之一,用于实现URL的重写,URL的重写是非常有用的功能
比如它可以在我们改变网站结构之后,不需要客户端修改原来的书签,也无需其他网站修改我们的 链接,就可以设置为访问
另外还可以在一定程度上提高网站的安全性。
if指令
用于条件匹配判断,并根据条件判断结果选择不同的Nginx配置,可以配置在server或location块中进行 配置,Nginx的if语法仅能使用if做单次判断,不支持使用if else或者if elif这样的多重判断
使用正则表达式对变量进行匹配,匹配成功时if指令认为条件为true,否则认为false,变量与表达式之间 使用以下符号链接:
= #比较变量和字符串是否相等,相等时if指令认为该条件为true,反之为false != #比较变量和字符串是否不相等,不相等时if指令认为条件为true,反之为false ~ #区分大小写字符,可以通过正则表达式匹配,满足匹配条件为真,不满足匹配条件为假 !~ #区分大小写字符,判断是否匹配,不满足匹配条件为真,满足匹配条件为假 ~* #不区分大小写字符,可以通过正则表达式匹配,满足匹配条件为真,不满足匹配条件为假 !~* #不区分大小字符,判断是否匹配,满足匹配条件为假,不满足匹配条件为真 -f 和 !-f #判断请求的文件是否存在和是否不存在 -d 和 !-d #判断请求的目录是否存在和是否不存在 -x 和 !-x #判断文件是否可执行和是否不可执行 -e 和 !-e #判断请求的文件或目录是否存在和是否不存在(包括文件,目录,软链接) #注意: #如果$变量的值为空字符串或0,则if指令认为该条件为false,其他条件为true 例:
[root@nginx nginx-1.28.1]# mkdir /webdir/czg.org/czg/html -p [root@nginx nginx-1.28.1]# echo czg test > /webdir/czg.org/czg/html/index.html [root@nginx nginx-1.28.1]# vim /usr/local/nginx/conf.d/vhosts.conf server { listen 80; server_name www.czg.org; root /webdata/nginx/czg.org/czg/html/; location / { root /webdir/czg.org/czg/html; if ( $http_user_agent ~ firefox ) { return 200 "test if messages"; } } } [root@nginx nginx-1.28.1]# nginx -s reload #测试 [root@nginx nginx-1.28.1]# curl -A "firefox" www.czg.org test if messages [root@nginx nginx-1.28.1]# curl www.czg.org czg test set指令
指定key并给其定义一个变量,变量可以调用Nginx内置变量赋值给key 另外set定义格式为set $key value,value可以是text, variables和两者的组合,可以用于自定义变量。
用法如下:
[root@nginx nginx-1.28.1]# vim /usr/local/nginx/conf.d/vhosts.conf server { listen 80; server_name www.czg.org; root /webdata/nginx/czg.org/czg/html/; location / { set $testname czg; echo $testname; } } [root@nginx nginx-1.28.1]# nginx -s reload #测试 [root@nginx nginx-1.28.1]# curl www.czg.org czgbreak指令
用于中断当前相同作用域(location)中的其他Nginx配置
与该指令处于同一作用域的Nginx配置中,位于它前面的配置生效
位于后面的 ngx_http_rewrite_module 模块中指令就不再执行
注意: 如果break指令在location块中后续指令还会继续执行,只是不执行 ngx_http_rewrite_module 模块的指令,其它指令还会执行
用法如下:
[root@nginx ~]# vim /usr/local/nginx/conf.d/vhosts.conf server { listen 80; server_name www.czg.org; root /webdata/nginx/czg.org/czg/html/; location / { set $test1 1; set $test2 2; if ($http_user_agent = firefox){ break; } set $test3 3; echo $test1 $test2 $test3; } } [root@nginx ~]# nginx -s reload #测试 [root@nginx ~]# curl www.czg.org 1 2 3 [root@nginx ~]# curl -A "firefox" www.czg.org 1 2 3return指令
return用于完成对请求的处理,并直接向客户端返回响应状态码,比如:可以指定重定向URL(对于特殊重 定向状态码,301/302等) 或者是指定提示文本内容(对于特殊状态码403/500等),处于此指令后的所有配 置都将不被执行。
[root@nginx ~]# vim /usr/local/nginx/conf.d/vhosts.conf server { listen 80; server_name www.czg.org; root /webdata/nginx/czg.org/czg/html/; location / { return 200 "hello world"; } } [root@nginx ~]# nginx -s reload [root@nginx ~]# curl www.czg.org hello worl ———————————————— 全站加密https
制作key
[root@nginx ~]# mkdir /usr/local/nginx/certs/ [root@nginx ~]# openssl req -newkey rsa:2048 \ > -nodes -sha256 -keyout /usr/local/nginx/certs/czg.org.key \ > -x509 -days 365 -out /usr/local/nginx/certs/czg.org.crt编辑配置文件
[root@nginx ~]# vim /usr/local/nginx/conf.d/vhosts.conf server { listen 80; listen 443 ssl; server_name www.czg.org; root /webdata/nginx/czg.org/czg/html/; ssl_certificate /usr/local/nginx/certs/czg.org.crt; ssl_certificate_key /usr/local/nginx/certs/czg.org.key; ssl_session_cache shared:sslcache:20m; ssl_session_timeout 10m; location / { if ($scheme = http ){ rewrite /(.*) https://$host/$1 redirect; #return 301 https://$host$request_uri; #也可以直接使用return直接返回 } } } [root@nginx ~]# nginx -s reload #测试 [root@nginx ~]# curl -kIL www.czg.org HTTP/1.1 302 Moved Temporarily Server: nginx/1.28.1 Date: Sat, 07 Feb 2026 20:40:30 GMT Content-Type: text/html Content-Length: 145 Connection: keep-alive Keep-Alive: timeout=60 Location: https://www.czg.org/ HTTP/1.1 200 OK Server: nginx/1.28.1 Date: Sat, 07 Feb 2026 20:40:30 GMT Content-Type: text/html Content-Length: 12 Last-Modified: Tue, 03 Feb 2026 00:47:36 GMT Connection: keep-alive Keep-Alive: timeout=60 ETag: "698145a8-c" Accept-Ranges: bytes 判断文件是否存在
[root@nginx ~]# vim /usr/local/nginx/conf.d/vhosts.conf server { listen 80; listen 443 ssl; server_name www.czg.org; root /webdata/nginx/czg.org/czg/html/; ssl_certificate /usr/local/nginx/certs/czg.org.crt; ssl_certificate_key /usr/local/nginx/certs/czg.org.key; ssl_session_cache shared:sslcache:20m; ssl_session_timeout 10m; location / { if ($scheme = http ){ rewrite ^/(.*) https://$host/$1 redirect; } if ( !-e $request_filename ){ rewrite ^/(.*) /index.html; } } } [root@nginx ~]# nginx -s reload #测试 [root@nginx ~]# curl -Lk www.czg.org www.czg.org [root@nginx ~]# curl -Lk www.czg.org/czg www.czg.org [root@nginx ~]# curl -Lk www.czg.org/666 www.czg.org Nginx 防盗链
防盗链基于客户端携带的referer实现,referer是记录打开一个页面之前记录是从哪个页面跳转过来的标 记信息,如果别人只链接了自己网站图片或某个单独的资源,而不是打开了网站的整个页面,这就是盗 链,referer就是之前的那个网站域名,正常的referer信息有以下几种:
none: #请求报文首部没有referer首部, #比如用户直接在浏览器输入域名访问web网站,就没有referer信息。 blocked: #请求报文有referer首部,但无有效值,比如为空。 server_names: #referer首部中包含本主机名及即nginx 监听的server_name。 arbitrary_string: #自定义指定字符串,但可使用*作通配符。示例: *.timinglee.org www.timinglee.* regular expression: #被指定的正则表达式模式匹配到的字符串,要使用~开头,例如: ~.*\.timinglee\.com实现盗链
在一个web 站点盗链另一个站点的资源信息,比如:图片、视频等
#盗链者web页面: <html> <head> <meta http-equiv=Content-Type content="text/html;charset=utf-8"> <title>盗链</title> </head> <body> <img src="http://www.timinglee.org/images/lee.png" > #使用别人的图片链接 <h1>欢迎大家</h1> <p><a href=http://www.timinglee.org>狂点老李</a>出门见喜</p> #使用别人的网页链接 </body> </html>实现防盗链
基于访问安全考虑,nginx支持通过ngx_http_referer_module模块,检查访问请求的referer信息是否有效 实现防盗链功能

Nginx 反向代理功能

反向代理:reverse proxy,指的是代理外网用户的请求到内部的指定的服务器,并将数据返回给用户的 一种方式,这是用的比较多的一种方式。
Nginx 除了可以在企业提供高性能的web服务之外,另外还可以将 nginx 本身不具备的请求通过某种预 定义的协议转发至其它服务器处理,不同的协议就是Nginx服务器与其他服务器进行通信的一种规范,主要在不同的场景使用以下模块实现不同的功能。
ngx_http_proxy_module: #将客户端的请求以http协议转发至指定服务器进行处理 ngx_http_upstream_module #用于定义为proxy_pass,fastcgi_pass,uwsgi_pass #等指令引用的后端服务器分组 ngx_stream_proxy_module: #将客户端的请求以tcp协议转发至指定服务器处理 ngx_http_fastcgi_module: #将客户端对php的请求以fastcgi协议转发至指定服务器助理 ngx_http_uwsgi_module: #将客户端对Python的请求以uwsgi协议转发至指定服务器处理同构代理:用户不需要其他程序的参与,直接通过http协议或者tcp协议访问后端服务器
异构代理:用户访问的资源时需要经过处理后才能返回的,比如php,python,等等,这种访问资源需要经过处理才能被访问
七层反向代理
基于ngx_http_proxy_module模块实现
配置简单的代理
实验环境
#172.25.254.10 RS1 172.25.254.20 RS2 [root@RSX ~]# dnf install httpd -y [root@RSX ~]# systemctl enable --now httpd [root@RSX ~]# echo RS2 - 172.25.254.20 > /var/www/html/index.html #测试 在Nginx主机中 [root@nginx ~]# curl 172.25.254.10 RS1 - 172.25.254.10 [root@nginx ~]# curl 172.25.254.20 RS2 - 172.25.254.20 配置反向代理
[root@RS2 ~]# mkdir /var/www/html/web [root@RS2 ~]# echo 172.25.254.20 web > /var/www/html/web/index.html [root@nginx ~]# vim /usr/local/nginx/conf.d/vhosts.conf server { listen 80; server_name www.czg.org; location / { proxy_pass http://172.25.254.10:80; } location /web { proxy_pass http://172.25.254.20:80; } } [root@nginx ~]# nginx -s reload #测试 [root@nginx ~]# curl 172.25.254.20/web/ 172.25.254.20 web [root@nginx ~]# curl 172.25.254.10 RS1 - 172.25.254.10实现动静分离
[root@RS1 ~]# dnf install php -y [root@RS1 ~]# vim /var/www/html/index.php <?php echo RS1 - 172.25.254.10 phpinfo() ?> [root@RS1 ~]# systemctl enable --now php-fpm [root@nginx ~]# vim /usr/local/nginx/conf.d/vhosts.conf server { listen 80; server_name www.czg.org; location ~* \.(php|js)$ { proxy_pass http://172.25.254.10:80; } location / { proxy_pass http://172.25.254.20:80; } } [root@nginx ~]# nginx -s reload 静态:

动态:

配置缓存加速
[root@nginx ~]# vim /usr/local/nginx/conf/nginx.conf proxy_cache_path /usr/local/nginx/proxy_cache levels=1:2:2 keys_zone=proxycache:20m inactive=120s max_size=1g; [root@nginx ~]# vim /usr/local/nginx/conf.d/vhosts.conf server { listen 80; server_name www.czg.org; location ~* \.(php|js)$ { proxy_pass http://172.25.254.10:80; proxy_cache proxycache; proxy_cache_key $request_uri; proxy_cache_valid 200 302 301 10m; proxy_cache_valid any 1m; } location / { proxy_pass http://172.25.254.20:80; } } [root@nginx ~]# systemctl restart nginx.service #缓存之前的目录 [root@nginx ~]# tree /usr/local/nginx/proxy_cache/ /usr/local/nginx/proxy_cache/ 0 directories, 0 files #进行缓存后查看缓存目录 [root@nginx ~]# tree /usr/local/nginx/proxy_cache/ /usr/local/nginx/proxy_cache/ └── 1 └── af └── 15 └── e251273eb74a8ee3f661a7af00915af1 3 directories, 1 file 四层反向代理
基于ngx_stream_proxy_module模块实现
建立子配置文件避免主配置文件杂乱
[root@nginx ~]# vim /usr/local/nginx/conf/nginx.conf include "/usr/local/nginx/conf.d/tcp/*.conf"; #与http同级四层反向代理配置示例
[root@nginx ~]# vim /usr/local/nginx/conf.d/tcp/proxy.conf # 四层代理需放在stream块中(和http块同级) stream { # MySQL代理 server { listen 3306; # 监听本机3306端口 # 转发到后端MySQL服务器 proxy_pass 172.25.254.50:3306; # 四层超时配置 proxy_connect_timeout 5s; proxy_timeout 300s; } # Redis代理(UDP示例) server { listen 6379 udp; # 监听UDP 6379 proxy_pass 172.25.254.60:6379; } } FastCGI
Nginx基于模块ngx_http_fastcgi_module实现通过fastcgi协议将指定的客户端请求转发至php-fpm处理,其配置指令参数如下:
fastcgi_pass address:port; #转发请求到后端服务器,address为后端的fastcgi server的地址,可用位置:localhost, if in localhost fastcgi_index name; #fastcgi默认的主页资源,示例:fastcgi_index index.php; fastcgi_param value; #设置传递给FastCGI服务器的参数值,可以是文本,变量或组合,可用于将Nginx的内置变量赋值给自定义key 有以下值等; fastcgi_param REMOTE_ADDR $remote_addr; #客户端源IP fastcgi_param REMOTE_PORT $remote_port; #客户端源端口 fastcgi_param SERVER_ADDR $server_addr; #请求的服务器IP地址 fastcgi_param SERVER_PORT $server_port; #请求的服务器端口 fastcgi_param SERVER_NAME $server_name; #请求的server name #可以通过include fastcgi.conf;参数来作为环境配置参数 #fastcgi.conf此文件都包含了预设的FastCGI环境变量 
php源码编译安装
1.下载源码包
[root@nginx ~]# wget https://www.php.net/distributions/php-8.3.30.tar.gz [root@nginx ~]# wget https://mirrors.aliyun.com/rockylinux/9.7/devel/x86_64/os/Packages/o/oniguruma-devel-6.9.6-1.el9.6.x86_64.rpm #下载依赖包 2.解压并编译
[root@nginx ~]# tar zxf php-8.3.30.tar.gz #下载依赖包 [root@nginx ~]# dnf install gcc systemd-devel-252-51.el9.x86_64 libxml2-devel.x86_64 sqlite-devel.x86_64 libcurl-devel.x86_64 libpng-devel.x86_64 oniguruma-devel-6.9.6-1.el9.6.x86_64.rpm -y [root@nginx php-8.3.30]# ./configure \ --prefix=/usr/local/php \ #安装路径 --with-config-file-path=/usr/local/php/etc \ #指定配置路径 --enable-fpm \ #用cgi方式启动程序 --with-fpm-user=nginx \ #指定运行用户身份 --with-fpm-group=nginx \ --with-curl \ #打开curl浏览器支持 --with-iconv \ #启用iconv函数,转换字符编码 --with-mhash \ #mhash加密方式扩展库 --with-zlib \ #支持zlib库,用于压缩http压缩传输 --with-openssl \ #支持ssl加密 --enable-mysqlnd \ #mysql数据库 --with-mysqli \ --with-pdo-mysql \ --disable-debug \ #关闭debug功能 --enable-sockets \ #支持套接字访问 --enable-soap \ #支持soap扩展协议 --enable-xml \ #支持xml --enable-ftp \ #支持ftp --enable-gd \ #支持gd库 --enable-exif \ #支持图片元数据 --enable-mbstring \ #支持多字节字符串 --enable-bcmath \ #打开图片大小调整,用到zabbix监控的时候用到了这个模块 --with-fpm-systemd #支持systemctl 管理cgi [root@nginx php-8.3.30]# make && make instsall 3.配置优化php
[root@nginx ~]# cd /usr/local/php/etc [root@nginx etc]# cp php-fpm.conf.default php-fpm.conf #复制模板 [root@nginx etc]# vim php-fpm.conf #去掉注释 pid = run/php-fpm.pid #指定pid文件存放位置 [root@nginx etc]# cd php-fpm.d/ [root@nginx php-fpm.d]# cp www.conf.default www.conf [root@nginx php-fpm.d]# vim www.conf 41 listen = 0.0.0.0:9000 #可以修改端口 #生成主配置文件 [root@nginx php-8.3.30]# cp php.ini-production /usr/local/php/etc/php.ini [root@nginx ~]# vim /usr/local/php/etc/php.ini 989 date.timezone = Asia/Shanghai #修改时区 #生成启动文件 [root@nginx etc]# cp ~/php-8.3.30/sapi/fpm/php-fpm.service /lib/systemd/system/ [root@nginx etc]# vim /lib/systemd/system/php-fpm.service #ProtectSystem=full #注释该内容 [root@nginx etc]# systemctl daemon-reload [root@nginx etc]# systemctl enable --now php-fpm.service [root@nginx etc]# netstat -antlupe | grep php tcp 0 0 127.0.0.1:9000 0.0.0.0:* LISTEN 0 120615 147595/php-fpm: mas Nginx整合php
生成默认发布目录与默认发布文件
[root@nginx ~]# mkdir /webdir/czg.org/php/html -p [root@nginx ~]# echo php.czg.org > /webdir/czg.org/php/html/index.html [root@nginx ~]# cat > /webdir/czg.org/php/html/index.php << eof > <?php > phpinfo(); > ?> > eof 编辑配置文件
[root@nginx ~]# vim /usr/local/nginx/conf/nginx.conf server { ...... include "/usr/local/nginx/conf.d/*.conf"; } [root@nginx ~]# vim /usr/local/nginx/conf.d/php.conf server { listen 80; server_name php.czg.org; root /webdir/czg.org/php/html; location ~ \.php$ { fastcgi_pass 127.0.0.1:9000; fastcgi_index index.php; include fastcgi.conf; } } [root@nginx ~]# nginx -s reload php的动态扩展模块(php的缓存模块)
软件下载:http://pecl.php.net/package/memcache

安装memcache模块




复制测试文件到nginx发布目录中

修改状态页面的登陆密码和memcache的访问接口
配置php加载memcache模块



部署memcached



php高速缓存

实现nginx直接访问memcache需要两个模块
- srcache-nginx-module 缓存获取
- memc-nginx-module memcache读写
重新编译nginx添加模块
[root@nginx ~]# systemctl stop nginx.service [root@nginx ~]# tar zxf memc-nginx-module-0.20.tar.gz [root@nginx ~]# tar zxf srcache-nginx-module-0.33.tar.gz #切换到nginx源码包清除Makefile [root@nginx ~]# cd nginx-1.28.1/ [root@nginx nginx-1.28.1]# make clean #添加模块重新编译 [root@nginx nginx-1.28.1]# ./configure --prefix=/usr/local/nginx --user=nginx --group=nginx --with-http_ssl_module --with-http_v2_module --with-http_realip_module --with-http_stub_status_module --with-http_gzip_static_module --with-pcre --with-stream --with-stream_ssl_module --with-stream_realip_module --add-module=/root/echo-nginx-module-0.64 --add-module=/root/memc-nginx-module-0.20 --add-module=/root/srcache-nginx-module-0.33 #编译但不拷贝文件到系统路径 [root@nginx nginx-1.28.1]# make 更换二进制文件
[root@nginx nginx-1.28.1]# rm -rf /usr/local/nginx/sbin/nginx [root@nginx nginx-1.28.1]# cp -p objs/nginx /usr/local/nginx/sbin/ #查看是否添加成功

编辑nginx整合memcache
[root@nginx ~]# vim /usr/local/nginx/conf.d/php.conf upstream memcache { server 127.0.0.1:11211; keepalive 512; } server { listen 80; server_name php.czg.org; root /webdir/fjw.org/php/html; location /memc { internal; # 标记该 location 仅能被 Nginx 内部调用,不接受外部直接访问 # Memcache 连接/读写超时时间(均为 100 毫秒) memc_connect_timeout 100ms; memc_send_timeout 100ms; memc_read_timeout 100ms; # 设置 Memcache 的缓存键:值为请求的查询字符串(如 ?id=1 的部分) set $memc_key $query_string; # 设置缓存过期时间:300 秒(5 分钟) set $memc_exptime 300; # 将请求转发到上面定义的 memcache 上游服务 memc_pass memcache; } location ~ \.php$ { # 定义缓存键:URL 路径 + 查询参数(比如 /index.php?id=1) set $key $uri$args; # 读取缓存:从 /memc 接口获取 $key 对应的缓存数据 srcache_fetch GET /memc $key; # 写入缓存:将 PHP 解析后的响应结果通过 /memc 接口存入 $key srcache_store PUT /memc $key; fastcgi_pass 127.0.0.1:9000; fastcgi_index index.php; include fastcgi.conf; } } [root@nginx ~]# nginx -s reload#重启memcache并访问没有缓存的php文件查看缓存命中 [root@nginx ~]# systemctl restart memcached.service [root@nginx ~]# ab -n 1000 -c 100 php.czg.org/index.php
nginx 二次开发版本
openresty
Nginx 是俄罗斯人发明的, Lua 是巴西几个教授发明的,中国人章亦春把 LuaJIT VM 嵌入到 Nginx中, 实现了OpenResty 这个高性能服务端解决方案
OpenResty® 是一个基于 Nginx 与 Lua 的高性能 Web 平台,其内部集成了大量精良的 Lua 库、第三方模块以及大多数的依赖项。用于方便地搭建能够处理超高并发、扩展性极高的动态Web 应用、Web 服 务和动态网关。
OpenResty® 通过汇聚各种设计精良的 Nginx 模块(主要由 OpenResty 团队自主开发),从而将Nginx 有效地变成一个强大的通用 Web 应用平台。这样,Web 开发人员和系统工程师可以使用 Lua 脚本语言调动 Nginx 支持的各种 C 以及 Lua 模块,快速构造出足以胜任 10K 乃至 1000K 以上单机并发连接的高性能 Web 应用系统。
OpenResty 由于有功能强大且方便的的API,可扩展性更强,如果需要实现定制功能,OpenResty是个不错的选择
官网: http://openresty.org/cn/
编译安装 openresty:
因为openresty与nginx冲突,所以编译安装 openresty前要把nginx卸载:

下载:



解压并编译:


./configure --prefix=/usr/local/openresty --user=nginx --group=nginx --with-http_ssl_module --with-http_v2_module --with-http_realip_module --with-http_stub_status_module --with-http_gzip_static_module --with-pcre --with-stream --with-stream_ssl_module --with-stream_realip_module

启动:


IO模型
介绍
IO模型实际上描述的是操作系统(或程序)和设备(如网络、硬盘等)之间数据传输的方式和策略。
在网络编程里,常常涉及等待数据的到来,处理请求的效率是关键。不同的IO模型决定了程序在等待数据时的表现。
IO的基本流程:
内核空间接受到外部请求后,内核空间把该请求复制传递给用户空间,用户空间进行分析后知道要什么数据,将要求发给内核空间,内核空间则根据要求去硬盘中拿,然后将数据复制给用户空间,用户空间根据这个数据去构建响应报文发给内核空间,然后内核空间再将已构建好的响应发给外部。
同步/异步
同步(Synchronous): A调用B,B的处理是同步的,在处理完之前他不会通知A,只有处理完之后才会明确的通知A。B在没有处理完A的请求时不能处理其他请求;就像你去餐厅点餐,服务员得把你的餐做好了才会叫你取。
异步(Asynchrnnous): A调用B,B的处理是异步的,B在接到请求后先告诉A我已经接到请求了,然后异步去处理,处理完之后通过回调等方式再通知A。B在处理A请求的同时,也可以接着处理其他人发送过来的请求;这就好比你在网上下单,商家先告诉你订单收到了,然后慢慢备货,备好后再通知你发货了。
同步和异步最大的区别就是被调用方的**执行方式**和**返回时机**。
阻塞/非阻塞
阻塞(Blocking): A调用B,A一直等着B的返回,别的事情什么也不干。就像你排队买票,只能一直等着,啥也做不了。
非阻塞(Non-blocking): I/O操作被调用后立即返回状态值,调用者可做其他事情,即A调用B,A不用一直等着B的返回,先去忙别的事情了。比如你打电话问外卖到没到,外卖员说没到,你就先去做别的事,过会儿再问。阻塞和非阻塞最大的区别就**是在被调用方返回结果之前的这段时间内,调用方是否一直等待。
五种I/O模型
阻塞 IO(最常见的IO模型)——同步阻塞
阻塞IO就是当应用发起读取数据申请时,在内核数据没有准备好之前,应用会一直处于等待数据状态,直到内核把数据准备好了交给应用才结束。
* 优点:编程简单,逻辑直观。在阻塞期间,用户线程被挂起,挂起期间不会占用CPU资源;
* 缺点:
* 1)连接利用率不高,内核如果没有响应数据,则该连接一直处于阻塞状态,占用连接资源
* 2)一个线程维护一个IO资源,当用大量并发请求时,需要创建等价的线程来处理请求,不适合用于高并发场景;
非阻塞 IO——同步非阻塞
非阻塞IO就是当应用发起读取数据申请时,如果内核数据没有准备好会即刻告诉应用(返回错误码等),不会让在这里等待。一旦内核中的数据准备好了,并且又再次收到了应用的请求,那么它马上就将数据拷贝到了用户线程,然后返回。
优点:每次发起IO调用去内核获取数据时,在内核等待数据的过程中可以立即返回,用户线程不会被阻塞,实时性较好;缺点:1)当用户线程A没有获取到数据时,不断轮询内核,查看是否有新的数据,占用大量CPU时间,效率不高;2)和阻塞IO一样,一个线程维护一个IO资源,当用大量并发请求时,需要创建等价的线程来处理请求,不适合用于高并发场景;
多路复用I/O——同步阻塞
多路复用IO指一个线程可以同时(实际是交替实现,即并发完成)监控和处理多个文件描述符对应各自的IO,即复用同一个线程
一个线程之所以能实现同时处理多个IO,是因为这个线程调用了内核中的SELECT,POLL或EPOLL等系统调用,从而实现多路复用IO
select`:线性轮询扫描所有的fd,不管他们是否活跃,监听的IO最大连接数不能多于FD_ SIZE(32位操作系统1024,64位操作系统2048)。
poll:原理和select相似,poll底层需要分配一个pollfd结构数组,维护在内核中,它没有数量限制,但IO数量大,扫描线性性能下降。
epoll :用于代替poll和select,没有大小限制。epoll采用事件驱动代替了轮询,epoll会把哪个流发生了怎样的I/O事件通知用户线程,另外epoll模型采用mmap内存映射实现内核与用户空间的消息传递,减少用户态和内核态数据传输的开销。
select,poll,epoll都是IO多路复用的机制。I/O多路复用就通过其中某一种机制,可以监视多个描述符,一旦某个描述符准备就绪,能够通知程序进行相应的读写操作。但select,poll,epoll本质上都是同步I/O,因为他们都需要在读写事件就绪后自己负责进行读写(一个个的处理),也就是说这个读写过程是阻塞的,而异步I/O则无需自己负责进行读写,异步I/O的实现会负责把数据从内核拷贝到用户空间。
优点:系统不必创建和维护大量的线程,只使用一个或几个线程来监听select选择器的操作,而一个选择器可同时处理成千上万个连接,大大减少了系统的开销;
IO复用模型的缺点:select本质上还是同步阻塞模式;
总结:复用IO的基本思路就是通过select或poll、epoll来监控多fd ,来达到不必为每个fd创建一个对应的监控线程,从而减少线程资源创建的目的。**复用IO模型的优势并不是对于单个连接能处理得更快,而是在于能处理更多的连接。
信号驱动 IO——同步非阻塞
当进程发起一个IO操作,系统调用sigaction执行一个信号处理函数,该函数向内核注册一个信号处理函数(回调函数),然后进程返回,并且不阻塞当前进程;当内核数据准备好时,内核使用信号通知应用线程调用recvfrom来读取数据(运行回调函数)。但是,等到内核空间读取到数据之后,应用线程需要将数据从内核空间拷贝到用户空间,此时是用户线程是阻塞的,即应用程序将数据从内核态拷贝到用户态的过程是阻塞等待的。
优点:
避免轮询,减少 CPU 占用。
缺点:
信号处理复杂,可靠性较低(信号可能丢失)。
异步 IO——异步非阻塞
应用只需要向内核发送一个请求,告诉内核它要读取数据后即刻返回;内核收到请求后会建立一个信号联系,当数据准备就绪,内核会主动把数据从内核复制到用户空间(而信号驱动是告诉应用程序何时可以开始拷贝数据),异步IO模型真正的做到了完完全全的非阻塞
优点:
完全非阻塞,性能最佳。
缺点:要实现真正的异步 I/O,操作系统需要做大量的工作。目前 Windows 下通过 IOCP 实现了真正的异步 I/O,在 Linux 系统下,Linux 2.6才引入,目前 AIO 并不完善,
