文章目录
nginx
简介
nginx(发音同engine x)是一款轻量级的Web服务器/反向代理服务器及电子邮件代理服务器,并在一个BSD-like协议下发行。支持热部署,几乎可以做到 7 * 24 小时不间断运行,即使运行几个月也不需要重新启动,还能在不间断服务的情况下对软件版本进行热更新。性能是 Nginx 最重要的考量,其占用内存少、并发能力强、能支持高达 5w 个并发连接数,最重要的是,Nginx 是免费的并可以商业化,配置使用也比较简单。
特性与优点
特性
nginx是一个很牛的高性能Web和反向代理服务器,它具有很多非常优越的特性:
- 在高连接并发的情况下,nginx是Apache服务器不错的替代品,能够支持高达50000个并发连接数的响应
- 使用epoll and kqueue作为开发模型
- nginx作为负载均衡服务器:nginx既可在内部直接支持和PHP程序对外进行服务,也可支持作为HTTP代理服务器对外进行服务
- nginx采用C进行编写,不论系统资源开销还是CPU使用效率都比Perlbal要好很多
优点
- 高并发连接:官方测试能够支撑5万并发连接,在实际生产环境中跑到2-3万并发连接数
- 内存消耗少:在3万并发连接下,开启的10个nginx进程才消耗150M内存(15M*10=150M)
- 配置文件非常简单:风格跟程序一样通俗易懂
- 成本低廉:nginx为开源软件,可以免费使用。而购买F5 BIG-IP、NetScaler等硬件负载均衡交换机则需要十多万至几十万人民币
- 支持Rewrite重写规则:能够根据域名、URL的不同,将HTTP请求分到不同的后端服务器群组
- 内置的健康检查功能:如果Nginx Proxy后端的某台Web服务器宕机了,不会影响前端访问
- 节省带宽:支持GZIP压缩,可以添加浏览器本地缓存的Header头
- 稳定性高:用于反向代理,宕机的概率微乎其微
- 模块化设计:模块可以动态编译
- 外围支持好:文档全,二次开发和模块较多
- 支持热部署:可以不停机重载配置文件
- 支持事件驱动、AIO(AsyncIO,异步IO)、mmap(Memory Map,内存映射)等性能优化
功能及应用类别
基本功能
- 静态资源的web服务器,能缓存打开的文件描述符
- http、smtp、pop3协议的反向代理服务器
- 缓存加速、负载均衡
- 支持FastCGI(fpm,LNMP),uWSGI(Python)等
- 模块化(非DSO机制),过滤器zip、SSI及图像的大小调整
- 支持SSL
扩展功能
- 基于名称和IP的虚拟主机
- 支持keepalive
- 支持平滑升级
- 定制访问日志、支持使用日志缓冲区提高日志存储性能
- 支持URL重写
- 支持路径别名
- 支持基于IP及用户的访问控制
- 支持速率限制,支持并发数限制
应用类别
- 使用nginx结合FastCGI运行PHP、JSP、Perl等程序
- 使用nginx作反向代理、负载均衡、规则过滤
- 使用nginx运行静态HTML网页、图片
- nginx与其他新技术的结合应用
模块与工作原理
nginx由内核和模块组成。其中,内核的设计非常微小和简洁,完成的工作也非常简单,仅仅通过查找配置文件将客户端请求映射到一个location block(location是nginx配置中的一个指令,用于URL匹配),而在这个location中所配置的每个指令将会启动不同的模块去完成相应的工作。
模块分类
nginx的模块从结构上分为核心模块、基础模块和第三方模块
- HTTP模块、EVENT模块和MAIL模块等属于核心模块
- HTTP Access模块、HTTP FastCGI模块、HTTP Proxy模块和HTTP Rewrite模块属于基本模块
- HTTP Upstream模块、Request Hash模块、Notice模块和HTTP Access Key模块属于第三方模块
用户根据自己的需要开发的模块都属于第三方模块。正是有了如此多模块的支撑,nginx的功能才会如此强大
nginx模块从功能上分为三类,分别是:
- Handlers(处理器模块)。此类模块直接处理请求,并进行输出内容和修改headers信息等操作。handlers处理器模块一般只能有一个
- Filters(过滤器模块)。此类模块主要对其他处理器模块输出的内容进行修改操作,最后由nginx输出
- Proxies(代理器模块)。就是nginx的HTTP Upstream之类的模块,这些模块主要与后端一些服务比如fastcgi等操作交互,实现服务代理和负载均衡等功能
工作原理
nginx的模块直接被编译进nginx,因此属于静态编译方式。
启动nginx后,nginx的模块被自动加载,与Apache不一样,首先将模块编译为一个so文件,然后在配置文件中指定是否进行加载。
在解析配置文件时,nginx的每个模块都有可能去处理某个请求,但是同一个处理请求只能由一个模块来完成。
nginx的进程架构:
启动nginx时,会启动一个Master进程,这个进程不处理任何客户端的请求,主要用来产生worker线程,一个worker线程用来处理n个request。
下图展示了nginx模块一次常规的HTTP请求和响应的过程
下图展示了基本的WEB服务请求步骤
用户通过客户端对服务端建立链接,在建立连接时需经过三次握手进行TCP连接,然后通过TCP连接来连接到80端口号,服务端便接收请求,接收请求后对数据进行拆封装,了解到所需要取的资源,服务器便通过master选择一个worker进行处理,取到资源后需构建响应报文,通过网卡返回到客户端,最后会记录事务的过程到日志中去,这便是整个过程。
安装与配置
安装
创建系统用户nginx
[root@localhost ~]# useradd -r -M -s /sbin/nologin nginx
安装依赖环境
[root@localhost ~]# yum -y install pcre-devel openssl openssl-devel gd-devel gcc gcc-c++
[root@localhost ~]# yum -y groups mark install 'Development Tools'
创建日志存放目录
[root@localhost ~]# mkdir -p /var/log/nginx
[root@localhost ~]# chown -R nginx.nginx /var/log/nginx
下载nginx
[root@localhost ~]# cd /usr/src/
[root@localhost src]# wget http://nginx.org/download/nginx-1.12.0.tar.gz
编译安装
[root@localhost src]# ls
debug kernels nginx-1.12.0.tar.gz
[root@localhost src]# tar xf nginx-1.12.0.tar.gz
[root@localhost src]# cd nginx-1.12.0
[root@localhost nginx-1.12.0]# ./configure \
--prefix=/usr/local/nginx \
--user=nginx \
--group=nginx \
--with-debug \
--with-http_ssl_module \
--with-http_realip_module \
--with-http_image_filter_module \
--with-http_gunzip_module \
--with-http_gzip_static_module \
--with-http_stub_status_module \
--http-log-path=/var/log/nginx/access.log \
--error-log-path=/var/log/nginx/error.log
[root@localhost nginx-1.12.0]# make -j $(grep 'processor' /proc/cpuinfo | wc -l) && make install
配置
服务控制方式,使用nginx命令
配置环境变量
[root@localhost ~]# echo 'export PATH=/usr/local/nginx/sbin:$PATH' > /etc/profile.d/nginx.sh
[root@localhost ~]# . /etc/profile.d/nginx.sh
服务控制方式,使用nginx命令
-t 检查配置文件语法
[root@localhost ~]# 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
-v 输出nginx的版本
[root@localhost ~]# nginx -v
nginx version: nginx/1.20.1
-c 指定配置文件的路径
[root@localhost ~]# nginx -s stop ; nginx -c /opt/nginx.conf ##直接停掉然后启动
[root@localhost ~]# ps -ef|grep nginx
root 99290 1 0 03:32 ? 00:00:00 nginx: master process nginx -c /opt/nginx.conf
nginx 99291 99290 0 03:32 ? 00:00:00 nginx: worker process
nginx 99292 99290 0 03:32 ? 00:00:00 nginx: worker process
root 101138 1653 0 03:33 pts/0 00:00:00 grep --color=auto nginx
-s 发送服务控制信号,可选值有{stop|quit|reopen|reload}
[root@localhost ~]# nginx -s quit
[root@localhost ~]# ss -antl
State Recv-Q Send-Q Local Address:Port Peer Address:Port Process
LISTEN 0 128 0.0.0.0:22 0.0.0.0:*
LISTEN 0 128 [::]:22 [::]:*
nginx的配置文件详解
主配置文件:/usr/local/nginx/conf
- 默认启动nginx时,使用的配置文件是:安装路径/conf/nginx.conf文件
- 可以在启动nginx时通过-c选项来指定要读取的配置文件
- nginx常见的配置文件及其作用
配置文件 | 作用 |
---|---|
nginx.conf | nginx的基本配置文件 |
mime.types | MIME类型关联的扩展文件 |
fastcgi.conf | 与fastcgi相关的配置 |
proxy.conf | 与proxy相关的配置 |
sites.conf | 配置nginx提供的网站,包括虚拟主机 |
nginx.conf配置详解
nginx.conf的内容分为以下几段:
- main配置段:全局配置段。其中main配置段中可能包含event配置段
- event {}:定义event模型工作特性
- http {}:定义http协议相关的配置
Nginx配置文件示例
[root@localhost ~]# vim /usr/local/nginx/conf
# 全局块
user www-data; ##用户
worker_processes 2; ## 默认1,一般建议设成CPU核数1-2倍
error_log logs/error.log; ## 错误日志路径
pid logs/nginx.pid; ## 进程id
# Events块
events {
# 使用epoll的I/O 模型处理轮询事件。
# 可以不设置,nginx会根据操作系统选择合适的模型
use epoll;
# 工作进程的最大连接数量, 默认1024个
worker_connections 2048;
# http层面的keep-alive超时时间
keepalive_timeout 60;
# 客户端请求头部的缓冲区大小
client_header_buffer_size 2k;
}
# http块
http {
include mime.types; # 导入文件扩展名与文件类型映射表
default_type application/octet-stream; # 默认文件类型
# 日志格式及access日志路径
log_format main '$remote_addr - $remote_user [$time_local] $status '
'"$request" $body_bytes_sent "$http_referer" '
'"$http_user_agent" "$http_x_forwarded_for"';
access_log logs/access.log main;
# 允许sendfile方式传输文件,默认为off。
sendfile on;
tcp_nopush on; # sendfile开启时才开启。
# http server块
# 简单反向代理
server {
listen 80;
server_name domain2.com www.domain2.com;
access_log logs/domain2.access.log main;
# 转发动态请求到web应用服务器
location / {
proxy_pass http://127.0.0.1:8000;
deny 192.24.40.8; # 拒绝的ip
allow 192.24.40.6; # 允许的ip
}
# 错误页面
error_page 500 502 503 504 /50x.html;
location = /50x.html {
root html;
}
}
# 负载均衡
upstream backend_server {
server 192.168.0.1:8000 weight=5; # weight越高,权重越大
server 192.168.0.2:8000 weight=1;
server 192.168.0.3:8000;
server 192.168.0.4:8001 backup; # 热备
}
server {
listen 80;
server_name big.server.com;
access_log logs/big.server.access.log main;
charset utf-8;
client_max_body_size 10M; # 限制用户上传文件大小,默认1M
location / {
# 使用proxy_pass转发请求到通过upstream定义的一组应用服务器
proxy_pass http://backend_server;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header Host $http_host;
proxy_redirect off;
proxy_set_header X-Real-IP $remote_addr;
}
}
}
配置指令:要以分号结尾,语法格式如下:
derective value1 [value2 ...];
支持使用变量:
- 内置变量:模块会提供内建变量定义
- 自定义变量:set var_name value
用于调试、定位问题的配置参数
daemon {on|off}; //是否以守护进程方式运行nginx,调试时应设置为off
master_process {on|off}; //是否以master/worker模型来运行nginx,调试时可以设置为off
error_log 位置 级别; //配置错误日志
正常运行必备的配置参数
使用的时候直接在配置文件中指明使用的用户是nginx
user USERNAME [GROUPNAME]; # 指定运行worker进程的用户和组
[root@localhost ~]# cd /usr/local/nginx/conf/
[root@localhost conf]# vim nginx.conf
1
2 user nginx nginx; # 取消注释,然后修改为nginx用户,nginx组
3 worker_processes 1;
.......
[root@localhost conf]# nginx -s reload # 发送信号重新加载配置文件立即生效
pid文件位置也取消注释直接使用,因为默认注释掉也是使用的这个位置,当然也可以修改为其他位置
pid /path/to/pid_file; # 指定nginx守护进程的pid文件
........
7 #error_log logs/error.log info;
8
9 pid logs/nginx.pid; # 取消注释
..........
[root@localhost conf]# nginx -s reload # 发送信号重新加载配置文件立即生效
设置worker线程最大可以打开的文件数
worker_rlimit_nofile number; # 更改worker线程中最大开放文件数量的限制。用于在不重新启动主过程的情况下增加限制。默认为1024,但是1024太小了,所以我们可以设置为10240
[root@localhost ~]# cd /usr/local/nginx/conf/
[root@localhost conf]# vim nginx.conf
1
2 user nginx nginx;
3 worker_processes 1;
4 worker_rlimit_nofile 10240; # 添加此行,并设置为10240,默认是1024
...........
[root@localhost conf]# nginx -s reload # 发送信号重新加载配置文件立即生效
指明所有worker进程所能够使用的总体的最大核心文件大小,保持默认即可
worker_rlimit_core size;
性能优化的配置参数
启动worker线程个数,把进程进行切换就是上下文切换,(寄存器)记录运行的位置,上下文切换的信息会一直被保存在CPU的内存中,直到被再次使用。
worker_processes n;
[root@localhost ~]# cd /usr/local/nginx/conf/
[root@localhost conf]# vim nginx.conf
1
2 user nginx nginx;
3 worker_processes 3; # 默认是1,更改就可以产生多个worker线程去处理
4 worker_rlimit_nofile 10240;
[root@localhost conf]# nginx -s reload # 发送信号重新加载配置文件立即生效
将进程绑定到某cpu核心中,避免频繁刷新缓存。绑定规则是核心数-1,比如总核心数为4,那么就绑定三个,另一个给其他使用
worker_cpu_affinity cpumask ...;
# cpumask:使用8位二进制表示cpu核心,如:
0000 0001 //第一颗cpu核心
0000 0010 //第二颗cpu核心
0000 0100 //第三颗cpu核心
0000 1000 //第四颗cpu核心
0001 0000 //第五颗cpu核心
0010 0000 //第六颗cpu核心
0100 0000 //第七颗cpu核心
1000 0000 //第八颗cpu核心
[root@localhost ~]# cd /usr/local/nginx/conf/
[root@localhost conf]# vim nginx.conf
1
2 user nginx nginx;
3 worker_processes 3;
4 worker_rlimit_nofile 10240;
5 worker_cpu_affinity 0001 0010 0100; # 添加此行,为前面增加的三个worker线程绑定三个核心
....................
[root@localhost ~]# /usr/local/nginx/sbin/nginx -s stop;nginx # 重启nginx
# 查看是否生效: top命令,大写L搜索nginx,然后按小写f,移动到大写P,然后空格选中,最后按q退出就可以看见是否生效
计时器解析度。降低此值,可减少gettimeofday()系统调用的次数。减少worker线程中的定时器分辨率,从而减少系统呼叫的数量。默认情况下,每次收到内核事件时都会被调用。随着分辨率的降低,每个指定呼叫一次。
timer_resolution interval;
# 例如可以设置为 timer_resolution 100ms;
指明worker进程的nice值,优先级是-20到19,指定的数字越小,优先级越高,相对优先级(可以调整) ,绝对优先级,100到139(无法调整) ,提高优先级可以先进行处理
worker_priority number;
[root@localhost ~]# ps -elf|grep nginx # 查看发现worker线程的nice值是80,我们可以修改提高它的优先级,这样就可以优先进行处理
1 S root 34284 1 0 80 0 - 20408 - 01:35 ? 00:00:00 nginx: master process nginx
5 S nginx 34285 34284 0 80 0 - 28560 do_epo 01:35 ? 00:00:00 nginx: worker process
5 S nginx 34286 34284 0 80 0 - 28560 do_epo 01:35 ? 00:00:00 nginx: worker process
5 S nginx 34287 34284 0 80 0 - 28560 do_epo 01:35 ? 00:00:00 nginx: worker process
0 S root 99205 33695 0 80 0 - 2302 - 01:53 pts/0 00:00:00 grep --color=auto nginx
[root@localhost ~]# cd /usr/local/nginx/conf/
[root@localhost conf]# vim nginx.conf
1
2 user nginx nginx;
3 worker_processes 3;
4 worker_rlimit_nofile 10240;
5 worker_cpu_affinity 0001 0010 0100;
6 worker_priority -20 # 添加此行来提高worker线程的优先级
[root@localhost conf]# nginx -s reload # 发送信号重新加载配置文件立即生效
[root@localhost conf]# ps -elf|grep nginx # 查看发现worker线程的nice值提高为60
1 S root 34284 1 0 80 0 - 20441 - 01:35 ? 00:00:00 nginx: master process nginx
5 S nginx 112949 34284 0 60 -20 - 28597 do_epo 01:56 ? 00:00:00 nginx: worker process
5 S nginx 112950 34284 0 60 -20 - 28597 do_epo 01:56 ? 00:00:00 nginx: worker process
5 S nginx 112951 34284 0 60 -20 - 28597 do_epo 01:56 ? 00:00:00 nginx: worker process
0 S root 113823 33695 0 80 0 - 2302 - 01:56 pts/0 00:00:00 grep --color=auto nginx
事件相关的配置:event{}段中的参数配置
accept_mutex {off|on}; 互斥锁,互相排斥,mster调度用户请求至各worker进程时使用的负载均衡锁;on表示能让多个worker轮流地、序列化地去响应新请求 ,保持默认关闭的。
accept_mutex {off|on};
lock_file logs/nginx.lock; # accept_mutex用到的互斥锁锁文件路径(main段)
指明使用的事件模型,建议让nginx自行选择。指定要使用的连接处理。通常不需要明确说明,因为 nginx 默认情况下会使用最有效的方法
use [epoll | rtsig | select | poll];
每个进程能够接受的最大连接数
worker_connections 1024;
[root@localhost ~]# cd /usr/local/nginx/conf/
[root@localhost conf]# vim nginx.conf
.......
14
15 events {
16 worker_connections 20480; # 默认值是1024
17 }
........
# worker_connections 20480; 并发连接数 = 20480 * worker线程数量(3个)/2
# 使用ab命令测试并发,安装工具 **yum -y install httpd-tools**
[root@localhost conf]# ab -n 30000(三万并发测试) http://192.168.220.9/(本机IP) # 测试
This is ApacheBench, Version 2.3 <$Revision: 1843412 $>
Copyright 1996 Adam Twiss, Zeus Technology Ltd, http://www.zeustech.net/
Licensed to The Apache Software Foundation, http://www.apache.org/
Benchmarking 192.168.220.9 (be patient)
Completed 3000 requests
Completed 6000 requests
Completed 9000 requests
Completed 12000 requests
Completed 15000 requests
Completed 18000 requests
Completed 21000 requests
Completed 24000 requests
Completed 27000 requests
Completed 30000 requests
Finished 30000 requests
Server Software: nginx/1.20.1
Server Hostname: 192.168.220.9
Server Port: 80
Document Path: /
Document Length: 612 bytes
Concurrency Level: 1
Time taken for tests: 3.518 seconds
Complete requests: 30000
Failed requests: 0
Total transferred: 25350000 bytes
HTML transferred: 18360000 bytes
Requests per second: 8528.53 [#/sec] (mean)
Time per request: 0.117 [ms] (mean)
Time per request: 0.117 [ms] (mean, across all concurrent requests)
Transfer rate: 7037.70 [Kbytes/sec] received
Connection Times (ms)
min mean[+/-sd] median max
Connect: 0 0 0.0 0 1
Processing: 0 0 0.0 0 2
Waiting: 0 0 0.0 0 1
Total: 0 0 0.0 0 2
Percentage of the requests served within a certain time (ms)
50% 0
66% 0
75% 0
80% 0
90% 0
95% 0
98% 0
99% 0
100% 2 (longest request)
网络连接相关的配置参数
长连接的超时时长,默认为65s
[root@localhost]# cd /usr/local/nginx/conf
[root@localhost conf]# vim nginx.conf
........
32
33 #keepalive_timeout 0;
34 keepalive_timeout 65; # 默认值
35
36 #gzip on;
.......
设置可以通过一个保持活力连接服务的最大请求数量。请求的最大数目后,连接将关闭。
定期关闭连接是每个连接内存分配的必要条件。因此,使用过高的最大请求量可能导致内存使用过量,不推荐
keepalive_requests number; # 可以添加在http段,server段,location段
[root@localhost]# cd /usr/local/nginx/conf
[root@localhost conf]# vim nginx.conf
........
38 server {
39 listen 80;
40 server_name localhost;
41 keepalived_requests 10000 # 可以添加在server段
42
43 #charset koi8-r;
.......
为指定类型的UserAgent(用户代理)禁用长连接
eepalive_disable [msie6(关闭Microsoft浏览器IE6的长连接)|safari(类mac的系统)|none(全部)];
是否对长连接使用TCP_NODELAY选项,为了提升用户体验,通常设为on
cp_nodelay on|off;
client_header_timeout number; //读取http请求报文首部的超时时长
client_body_timeout number; //读取http请求报文body部分的超时时长
send_timeout number; //发送响应报文的超时时长
FastCGI的相关配置参数
LNMP:php要启用fpm模型
配置示例如下:
location ~ \.php$ {
root html;
fastcgi_pass 127.0.0.1:9000; //定义反向代理
fastcgi_index index.php;
fastcgi_param SCRIPT_FILENAME /scripts$fastcgi_script_name;
include fastcgi_params;
}
常需要进行调整的参数
- worker_processes # worker线程数量
- worker_connections # 并发连接数
- worker_cpu_affinity # cpu核心数绑定
- worker_priority # worker线程的优先级
nginx作为web服务器时使用的配置:http{}段的配置参数
http{…}:配置http相关,由ngx_http_core_module模块引入。nginx的HTTP配置主要包括四个区块,结构如下:
http {//协议级别
include mime.types;
default_type application/octet-stream;
keepalive_timeout 65;
gzip on;
upstream {//负载均衡配置
...
}
server {//服务器级别,每个server类似于httpd中的一个<VirtualHost>
listen 80;
server_name localhost;
location / {//请求级别,类似于httpd中的<Location>,用于定义URL与本地文件系统的映射关系
root html;
index index.html index.htm;
}
}
http{}段配置指令:
server {}:定义一个虚拟主机,示例如下:
server{
listen 81;(端口)
server_name www.lp.com;(域名可以给多个)
location / {
root html/test; (网站位置) or alias /var/www/html/;(别名,但是别名一定要写绝对路径,就是把资源放到另外一个位置,当有人访问时,看见的路径是/根下面,其实我们已经放在了另一个位置,防止被攻击)
index index.html;
listen:指定监听的地址和端口
listen address[:port];
listen port;
server_name NAME […]; 后面可跟多个主机,名称可使用正则表达式或通配符
当有多个server时,匹配顺序如下:
1.先做精确匹配检查
2.左侧通配符匹配检查,如*.idfsoft.com
3.右侧通配符匹配检查,如mail.*
4.正则表达式匹配检查,如~ ^.*.idfsoft.com$
5.default_server
root path; 设置资源路径映射,用于指明请求的URL所对应的资源所在的文件系统上的起始路径
alias path; 用于location配置段,定义路径别名
index file; 默认主页面
index index.php index.html;
error_page code […] [=code] URI | @name 根据http响应状态码来指明特用的错误页面,例如 error_page 404 /404_customed.html
[=code]:以指定的响应码进行响应,而不是默认的原来的响应,默认表示以新资源的响应码为其响应码,例如 error_page 404 =200 /404_customed.html
log_format定义日志格式
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;
//注意:此处可用变量为nginx各模块内建变量
location区段,通过指定模式来与客户端请求的URI相匹配
//功能:允许根据用户请求的URI来匹配定义的各location,匹配到时,此请求将被相应的location配置块中的配置所处理,例如做访问控制等功能
//语法:location [ 修饰符 ] pattern {......}
error_page code […] [=code] URI | @name 根据http响应状态码来指明特用的错误页面,例如
error_page 404 /404.html;
[root@localhost nginx]# vim /usr/local/nginx/conf/nginx.conf
error_page 404 /404.html;
[root@localhost nginx]# vim html/404.html
[root@localhost nginx]# cat html/404.html
<html>
<head>
<title>test page</title>
</head>
<body>
<a href="http://www.baidu.com">baidu</a>
<html>
[root@localhost nginx]# systemctl restart nginx.service
访问ip不会再报错404,而是会出现一个链接
进去后便是百度官网
[=code]:以指定的响应码进行响应,而不是默认的原来的响应,默认表示以新资源的响应码为其响应码,例如 error_page 404 =200 /404.html
[root@localhost nginx]# vim /usr/local/nginx/conf/nginx.conf
error_page 404 =200 /404.html;
[root@localhost nginx]# systemctl restart nginx.service
状态会显示为200
log_format 定义日志格式
log_format main '$remote_addr - $remote_user [$time_local] "$request" '
'$status $body_bytes_sent "$http_referer" '
'"$http_user_agent" "$http_x_forwarded_for"';
[root@localhost nginx]# tail -f logs/access.log
192.168.101.1 - - [27/Oct/2021:15:26:04 +0800] "GET / HTTP/1.1" 304 0 "-" "Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/84.0.4147.89 Safari/537.36 SLBrowser/7.0.0.8031 SLBChan/25" "-"
$remote_addr :远程主机地址
$remote_user:远程用户
$time_local:本地时间
$request:请求资源
$status:状态码
$body_bytes_sent:发送主题的字节数
$http_referer:是否是跳转过来的
$http_user_agent:用户代理
$http_x_forwarded_for:从哪跳转过来的
location区段,通过指定模式来与客户端请求的URI相匹配
//功能:允许根据用户请求的URI来匹配定义的各location,匹配到时,此请求将被相应的location配置块中的配置所处理,例如做访问控制等功能
//语法:location [ 修饰符 ] pattern {…}
常用修饰符说明:
修饰符 | 功能 |
---|---|
= | 精确匹配 |
~ | 正则表达式模式匹配,区分大小写 |
~* | 正则表达式模式匹配,不区分大小写 |
^~ | 前缀匹配,类似于无修饰符的行为,也是以指定模块开始,不同的是,如果模式匹配,那么就停止搜索其他模式了,不支持正则表达式 |
@ | 定义命名location区段,这些区段客户端不能访问,只可以由内部产生的请求来访问,如try_files或error_page等 |
没有修饰符
[root@localhost local]# vim nginx/conf/nginx.conf
location / {
root html;
index index.html index.htm;
}
location /test {
echo "test";
}
[root@localhost ~]# nginx -s reload
[root@localhost ~]# curl http://192.168.101.210/test
test
[root@localhost ~]# curl http://192.168.101.210/testhpo
test
[root@localhost ~]# curl http://192.168.101.210/testhposadasf
test
精确匹配
[root@localhost ~]# vim /usr/local/nginx/conf/nginx.conf
location =/test {
echo "test";
}
[root@localhost ~]# nginx -s reload
##如下内容就可正确匹配
[root@localhost ~]# curl http://192.168.101.210/test
test
##如下内容则无法匹配
[root@localhost ~]# curl http://192.168.101.210/testdasdasd
<html>
<head><title>404 Not Found</title></head>
<body>
<center><h1>404 Not Found</h1></center>
<hr><center>nginx/1.20.1</center>
</body>
</html>
正则表达式模式匹配(区分大小写)
[root@localhost ~]# vim /usr/local/nginx/conf/nginx.conf
location ^~ /test {
echo "test";
}
[root@localhost ~]# curl http://192.168.101.210/test
test
[root@localhost ~]# curl http://192.168.101.210/Test
<html>
<head><title>404 Not Found</title></head>
<body>
<center><h1>404 Not Found</h1></center>
<hr><center>nginx/1.20.1</center>
</body>
</html>
正则表达式模式匹配(不区分大小写)
[root@localhost ~]# vim /usr/local/nginx/conf/nginx.conf
location ~* /test {
echo "test";
}
[root@localhost ~]# curl http://192.168.101.210/test
test
[root@localhost ~]# curl http://192.168.101.210/Test
test
~:类似于无修饰符的行为,也是以指定模式开始,不同的是,如果模式匹配,则停止搜索其他模式
优先级次序
( location = 路径 ) --> ( location ^~ 路径 ) --> ( location ~ 正则 ) --> ( location ~* 正则 ) --> ( location 路径 )
查找顺序和优先级:由高到底依次为
1.带有=的精确匹配优先
2.正则表达式按照他们在配置文件中定义的顺序
3.带有^~修饰符的,开头匹配
4.带有或*修饰符的,如果正则表达式与URI匹配
5.没有修饰符的精确匹配
示例:
[root@localhost ~]# vim /usr/local/nginx/conf/nginx.conf
location / {
root html;
index index.html index.html;
}
location /test {
echo "test1";
}
location ~ ^ /test {
echo "test2";
}
location ~* /test {
echo "test3";
}
[root@localhost ~]# nginx -s reload
优先级测试
[root@localhost ~]# curl http://192.168.168.210/test
test2
[root@localhost ~]# curl http://192.168.168.210/testid
test1
[root@localhost ~]# curl http://192.168.168.210/TEST
test3
访问控制
注:用于location段,可以用主机地址表示,也可用网段表示,必须一起用
allow:设定允许那台或那些主机访问,多个参数间用空格隔开
deny:设定禁止那台或那些主机访问,多个参数间用空格隔开
在matser主机上修改nginx配置文件,将192.168.50.0网段禁止访问
[root@localhost ~]# vim /usr/local/nginx/conf/nginx.conf
location / {
root html;
index index.html index.htm;
allow 192.168.101.210/32;
deny 192.168.101.110/32;
}
[root@localhost ~]# nginx -s reload
主机为192.168.101.210访问
[root@localhost ~]# curl http://192.168.101.210
<!DOCTYPE html>
<html>
<head>
<title>Welcome to nginx!</title>
<style>
body {
width: 35em;
margin: 0 auto;
font-family: Tahoma, Verdana, Arial, sans-serif;
}
</style>
</head>
<body>
<h1>Welcome to nginx!</h1>
<p>If you see this page, the nginx web server is successfully installed and
working. Further configuration is required.</p>
<p>For online documentation and support please refer to
<a href="http://nginx.org/">nginx.org</a>.<br/>
Commercial support is available at
<a href="http://nginx.com/">nginx.com</a>.</p>
<p><em>Thank you for using nginx.</em></p>
</body>
</html>
主机为192.168.101.110访问
[root@localhost ~]# curl http://192.168.101.210
<html>
<head><title>403 Forbidden</title></head>
<body>
<center><h1>403 Forbidden</h1></center>
<hr><center>nginx/1.20.1</center>
</body>
</html>
将deny字段改为all,表示在拒绝所有主机访问
[root@localhost ~]# vim /usr/local/nginx/conf/nginx.conf
location / {
root html;
index index.html index.htm;
allow 192.168.101.210/32;
deny 192.168.101.110/32;
deny allow;
}
[root@localhost ~]# nginx -s reload
再次访问
https配置
server {
listen 443 ssl;
server_name luojk.com;
ssl_certificate ssl/nginx.crt;
ssl_certificate_key ssl/nginx.key;
ssl_session_cache shared:SSL:1m;
ssl_session_timeout 5m;
ssl_ciphers HIGH:!aNULL:!MD5;
ssl_prefer_server_ciphers on;
location / {
root html;
index index.html index.htm;
}
}
开启状态界面
开启status:
[root@localhost ~]# vim /usr/local/nginx/conf/nginx.conf
location / {
root html;
index index.html index.htm;
}
location /status {
stub_status;
}
[root@localhost ~]# nginx -s reload
状态页面信息详解:
状态码 | 表示的意义 |
---|---|
Active connections 2 | 当前所有处于打开状态的连接数 |
accepts | 总共处理了多少个连接 |
handled | 成功创建多少握手 |
requests | 总共处理了多少个请求 |
Reading | nginx读取到客户端的Header信息数,表示正处于接收请求状态的连接数 |
Writing | nginx返回给客户端的Header信息数,表示请求已经接收完成, 且正处于处理请求或发送响应的过程中的连接数 |
Waiting | 开启keep-alive的情况下,这个值等于active - (reading + writing), 意思就是Nginx已处理完正在等候下一次请求指令的驻留连接 |
rewrite
语法:rewrite regex replacement flag;,如:
[root@localhost ~]# ls /usr/local/nginx/html/sanctuary
sanctuary.jpg
[root@localhost ~]# vim /usr/local/nginx/conf/nginx.conf
location /luo {
rewrite ^/luo/(.*\.jpg)$ /sanctuary/$1 break;
}
[root@localhost ~]# nginx -s reload
常见的flag
flag | 作用 |
---|---|
last | 基本上都用这个flag,表示当前的匹配结束,继续下一个匹配,最多匹配10个到20个 一旦此rewrite规则重写完成后,就不再被后面其它的rewrite规则进行处理 而是由UserAgent重新对重写后的URL再一次发起请求,并从头开始执行类似的过程 |
break | 中止Rewrite,不再继续匹配 一旦此rewrite规则重写完成后,由UserAgent对新的URL重新发起请求, 且不再会被当前location内的任何rewrite规则所检查 |
redirect | 以临时重定向的HTTP状态302返回新的URL |
permanent | 以永久重定向的HTTP状态301返回新的URL |
last
[root@localhost ~]# vim /usr/local/nginx/conf/nginx.conf
location /luo {
rewrite ^/luo/(.*\.html)$ /tian/$1 last;
}
location /tian {
rewrite ^/tian/(.*\.html)$ http://www.baidu.com last;
}
[root@localhost ~]# nginx -s reload
浏览器访问IP/luo/tian.html时结果为百度页面
rewrite模块的作用是用来执行URL重定向。这个机制有利于去掉恶意访问的url,也有利于搜索引擎优化(SEO)
nginx使用的语法源于Perl兼容正则表达式(PCRE)库,基本语法如下:
标识符 | 意义 |
---|---|
^ | 必须以^后的实体开头 |
$ | 必须以$前的实体结尾 |
. | 匹配任意字符 |
[] | 匹配指定字符集内的任意字符 |
[^] | 匹配任何不包括在指定字符集内的任意字符串 |
| | 匹配 之前或之后的实体 |
() | 分组,组成一组用于匹配的实体,通常会有 |
if
语法:if (condition) {…}
应用场景:
-
server段
-
location段
常见的condition -
变量名(变量值为空串,或者以“0”开始,则为false,其它的均为true)
-
以变量为操作数构成的比较表达式(可使用=,!=类似的比较操作符进行测试)
-
正则表达式的模式匹配操作
- ~:区分大小写的模式匹配检查
- ~*:不区分大小写的模式匹配检查
- !和!*:对上面两种测试取反
-
测试指定路径为文件的可能性(-f,!-f)
-
测试指定路径为目录的可能性(-d,!-d)
-
测试文件的存在性(-e,!-e)
-
检查文件是否有执行权限(-x,!-x)
基于浏览器实现分离案例
if ($http_user_agent ~ Firefox) {
rewrite ^(.*)$ /firefox/$1 break;
}
if ($http_user_agent ~ MSIE) {
rewrite ^(.*)$ /msie/$1 break;
}
if ($http_user_agent ~ Chrome) {
rewrite ^(.*)$ /chrome/$1 break;
}
防盗链案例
location ~* \.(jpg|gif|jpeg|png)$ {
valid_referers none blocked www.idfsoft.com;
if ($invalid_referer) {
rewrite ^/ http://www.idfsoft.com/403.html;
}
}