Nginx 的安装和配置
0 安装
略,到官网下载即可。注意 Nginx 是 C 语言编写的,不跨平台,不同操作系统需要下载不同的 Nginx。
1 Windows 下的 Nginx 基本命令
启动
start nginx
关闭
./nginx -s quit
./nginx -s stop
查看信息
./nginx -V
重启
./nginx -s reload
2 Linxu 下的 Nginx 基本命令
启动
./sbin/nginx
关闭
./sbin/nginx -s quit
./sbin/nginx -s stop
查看信息
./sbin/nginx -V
./sbin/nginx -v
重启
./sbin/nginx -s reload
3 Nginx 在 CentOS 7 下的安装
Nginx 的 Linux 版本和 Windows 版本有一些不同,即在于其只提供源码,编译的步骤需要使用者自己去做。
step 1 - 使用 CentOS 的 yum 功能下载编译环境
yum -y install make zlib zlib-devel gcc-c++ libtool openssl openssl-devel
step 2 - 进入到 Nginx 的目录下,输入 ./configure 进行配置
No 1 - 如果出现权限问题,就改用 bash ./configure
No 2 - 想要安装到特定目录,就使用 ./configure --prefix=[路径]
step 3 - 输入 make
step 4 - 输入 make install
step 5 - 默认情况下,此时默认在 /usr/local 目录下会出现一个 nginx 目录(如果 configure 的时候修改过路径那就不会在这里了)
step 6 - 进入此目录下的 sbin 目录,使用相关命令操作 Nginx
step 7 - 注意对于 Nginx 要用到的端口,需要放开防火墙
No 1 - 如果是阿里云的服务器,可以配置端口规则
No 2 - 如果是自己的虚拟机或者实体服务器,需要自己开放防火墙端口
[1] firewall-cmd --zone=public --add-port=80/tcp --permanent
[2] firewall-cmd --reload
跨域的后端配套代码
如果是使用 Nginx 做静态资源服务器去做前后端分离,那么就涉及到前端页面的跨域问题。java 基于 Spring 设置跨域允许:
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.servlet.config.annotation.CorsRegistry;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurerAdapter;
/**
* 解决跨域问题的配置类
* 让 Spring 扫描到该类即可
*/
@Configuration
public class CorsConfig{
//允许的 Http 连接类型
static final String ORIGINS[] = new String[] { "GET", "POST", "PUT", "DELETE" };
@Bean
public WebMvcConfigurer corsConfigurer() {
return new WebMvcConfigurer() {
@Override
public void addCorsMappings(CorsRegistry registry) {
//设置所有的路径均允许跨域请求
registry.addMapping("/**").allowedOrigins("*").allowCredentials(true).allowedMethods(ORIGINS)
.maxAge(3600).allowCredentials(true);
}
};
}
}
Nginx 的一些概念思考
Nginx 是什么
Nginx 是一个主要用于作为 Http、Https 的事件驱动的 Web 服务器。
Nginx 有两大功能 —— 反向代理和负载均衡。
另外它的扩展性良好,支持很多第三方库。
与 Apache 相比更加轻巧,且支持热更新。
Nginx 如何实现高性能
Nginx 在工作时有一条主线程和多条 Worker 线程;主线程用于维持进程存在和读取配置, Worker 线程用于处理 Request。
当有 Request 进来的时候,会有一条 Worker 线程去进行处理,而如果 Request 进入了阻塞状态,Worker 线程会被暂时调用去处理其它 Request。
也就是说,可以认为 Nginx 是异步处理请求的,一个线程对应了多个 Requst,这使得 Nginx 对 io 密集型工作非常擅长。
Nginx 阻止请求
server {
listen 80;
server_name "";
return 444;
}
Nginx 解决惊群现象
惊群现象意为多个子线程去争抢同一个资源,导致了资源的浪费。在 Nginx 中则是多个线程共同监听一个端口引起的。
Nginx 在端口处加了锁,每次只有一个 Worker 线程会监控该端口。
Nginx 大文件上传
在实际的网站开发过程中,可能会遇到要上传较大文件的需求。在这种情况下,如果使用 Nginx 作为静态资源服务器,则会遇到一系列问题需要调整配置。
Nginx 的运作流程:
(服务端阶段) (反向代理阶段)
浏览器 --> Nginx --> java project
当有浏览器访问 Nginx 的时候,Nginx 作为服务器存在,此时在 Nginx 的配置文件中,对于这一阶段的配置均使用 client_xxxx 进行配置。
而当 Nginx 去访问后端的 java 项目的时候,Nginx 是作为客户端存在,此时在配置文件中均为 proxy_xxxx 去作为配置。
对应到 Nginx 中的 nginx.conf 文件中,则是在 http 模块中进行相关调控:
# 主要用于传输附件的时候,前端往后端传输的最大数额
client_max_body_size 500m;
# 浏览器端传过来的 body 的缓冲区大小,会直接影响文件传输的速度
client_body_buffer_size 100m;
# 请求头的缓冲区大小,如果在这个数字以内,就会使用该配置项去读取请求头
client_header_buffer_size 16k;
# 如果请求头超过 client_header_buffer_size 的配置数,就会使用 large_client_header_buffers 去读取
large_client_header_buffers 4 32k;
# 与 Nginx 建立连接的超时时间,单位是秒
proxy_connect_timeout 60s;
# Nginx 连接 upstream 服务器的超时时间,单位是秒
proxy_send_timeout 60s;
# Http请求被后端项目处理后,返回给 Nginx 的响应时间,单位是秒
proxy_read_timeout 60s;
# 在 proxy_buffering 开启的时候,proxy_buffers 和 proxy_busy_buffers_size 才会起作用
proxy_buffering on;
# Nginx 往后端项目发送的 Request 的数量和值
proxy_buffers 4 8k;
如果后端使用的是 SpringBoot 2.0,还需要在 application.properties 中添加如下配置:
spring.servlet.multipart.max-file-size=500MB
spring.servlet.multipart.max-request-size=500MB
Nginx 的配置文件整合
在 Nginx 目录下的 conf 文件夹下有一个 nginx.conf。内容如下:
# 设置登录用户
# 在 Linux 下如果不设置登录用户,可能会没有权限去访问静态资源
# user root;
# Nginx 进程,一般设置为和 cpu 核数一样
worker_processes 8;
# 单个进程打开的最多文件描述符数目
# 最好与 Linux 的文件描述符数量相同
# Linux 上查看文件描述符数量 (ulimit -n)
worker_rlimit_nofile 65535;
#错误日志存放目录
error_log logs/error.log;
# pid 的存储文件
# 如果不设置的话默认在 /log 下
pid nginx.pid;
# 用来指定 Nginx 的工作模式和最大连接数
events {
# 工作模式有 select、poll、epoll、kqueue 等,其中前两者是标准模式,后两者是高效模式
# 在 Linux 上,工作模式一般选择使用 epoll
# 在 Windows 上,可以选择 poll
use epoll;
# 单个进程的最大连接数,在 Linux 上受到最大句柄数的限制
# 注意,Nginx 是多进程的
worker_connections 1024;
# 设置网路连接序列化,防止惊群现象发生
# on 为开启,off 为关闭,默认 on
accept_mutex on;
# 设置一个进程是否同时接受多个网络连接
# on 为开启,off 为关闭,默认 off
multi_accept on;
}
# 核心的配置模块
http {
# 文件扩展名与文件类型映射表
include mime.types;
# 默认文件类型,默认为 text/plain
default_type application/octet-stream;
# 日志的自定义格式
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;
# 编码格式
charset utf-8;
# 开启 tcp_nopush 可以把 HttpResponse Header 和文件的开始放在一个文件里发布,减少网络报文段的数量
tcp_nopush on;
# 开启 tcp_nodelay,内核会等待将更多的字节组成一个数据包,从而提高 IO 性能
tcp_nodelay on;
# 是否使用 sendfile 系统调用来传输文件
# sendfile 是 Linux 2.0 中新增的 IO 系统(零拷贝 IO 系统)
sendfile on;
# Nginx 工作进程每次调用 sendfile() 传输数据的大小上限
# 默认值为 0 (表示无限制),可以设置在 http/server/location 模块中
sendfile_max_chunk 1024k;
# 连接超时时间,单位是秒
keepalive_timeout 65s;
# 单个长连接的最大请求数,默认 100
keepalive_requests 100;
# 开启 gzip 压缩功能
gzip on;
# 主要用于传输附件的时候,前端往后端传输的最大数额
client_max_body_size 500m;
# 浏览器端传过来的 body 的缓冲区大小,会直接影响文件传输的速度
client_body_buffer_size 100m;
# 请求头的缓冲区大小,如果在这个数字以内,就会使用该配置项去读取请求头
client_header_buffer_size 16k;
# 如果请求头超过 client_header_buffer_size 的配置数,就会使用 large_client_header_buffers 去读取
large_client_header_buffers 4 32k;
# 后端服务器与 Nginx 建立连接的超时时间,单位是秒
proxy_connect_timeout 60s;
# Nginx 连接 upstream 服务器的超时时间,单位是秒
proxy_send_timeout 60s;
# Http 请求被后端服务器处理后,返回给 Nginx 的响应时间,单位是秒
proxy_read_timeout 60s;
# 在 proxy_buffering 开启的时候,proxy_buffers 和 proxy_busy_buffers_size 才会起作用
proxy_buffering on;
# Nginx 往后端项目发送的 Request 的数量和值
proxy_buffers 4 8k;
# Nginx 主要功能之一 —— 作为网关进行服务分发
# 首先需要在 server 模块中配置监听的端口和 url
server {
# 监听端口
listen 8090;
# 服务的名称
server_name hello_world;
# 编码格式
#charset gkb;
charset utf-8;
# 设置单个连接上能够使用的带宽,单位:k - kb,m - mb
limit_rate 500k;
# 对不同的错误编码设置错误的页面
# error_page 404 /404.html;
error_page 500 502 503 504 /50x.html;
# 此处如果有客户端访问 http://ip:8090/,就等同于访问 http://ip:8091/
location / {
proxy_pass http://localhost:8091/;
}
# 此处如果有客户端访问 http://ip:8090/api,就等同于访问 http://ip:8092/
location /api {
proxy_pass http://localhost:8092/;
}
# 需要负载均衡的情况
location /api2 {
# 如果客户端在指定时间内没有发送一个完整的 request header,Nginx 返回 HTTP 408(Request Timed Out)
client_header_timeout 60s;
# 如果客户端在指定时间内没有发送任何 request body 内容,Nginx 返回 HTTP 408(Request Timed Out)
client_body_timeout 60s;
# 服务端向客户端传输数据的超时时间
send_timeout 60s;
# 重试次数
proxy_next_upstream_tries 3;
# Nginx 与 后端业务服务器连接的超时时间
proxy_connect_timeout 60s;
# Nginx 与 后端业务服务器连接的读取超时时间
proxy_read_timeout 60s;
# Nginx 与 后端业务服务器连接的存入超时时间
proxy_send_timeout 60s;
# 如果负载的后端服务中的一台存在 502、504 等问题,则重试到下一台
proxy_next_upstream http_500 http_501 http_502 http_503 http_504 error timeout invalid_header;
# 是否开启 aio,默认关闭
aio on;
# 在转发的时候把原 http 请求的 Header 中的 Host、X-Real-IP、X-Forwarded-For 等字段放到转发的请求里
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
# 设置转发地址
proxy_pass http://hello_word_service/;
}
}
# 配置多个服务达到负载均衡的目的
upstream hello_word_service {
# 负载均衡方案一 按照权重分配
server localhost:8091 weight=5;
server localhost:8092 weight=5;
# 负载均衡方案二 按照响应时间分配
# server localhost:8091;
# server localhost:8092;
# fair;
# 负载均衡方案三 按照 ip 的 hash 值来分配
# 注意,同一 ip 的 Hash 值是一定的,所以此处必然分配到同一台服务器上
# server localhost:8091;
# server localhost:8092;
# ip_hash;
# 其它方案不一一列举
}
# Nginx 主要功能之二 —— 作为静态资源服务器去调用后端接口
# 首先需要在 server 模块中配置静态的资源
server {
# 监听端口
listen 8100;
# 服务的名称
server_name demo_web;
# 编码格式
charset utf-8;
# 首页配置,注意读取路径必须要有配置的 index.html 或者 index.htm
# 如果首页是其它的,就要在这里配置
# 如果客户端访问 http://ip:8100,就会显示首页
index index.html index.htm;
# 静态资源的读取路径,首先会去读取路径下的首页
root D:\\demo_web;
# 如果客户端或者页面资源需要访问到 http://ip:8100/api,就等同于访问 http://ip:8080/
location /api {
proxy_pass http://localhost:8080/;
}
# 需要负载均衡的情况
location /api2 {
proxy_next_upstream http_500 http_501 http_502 http_503 http_504 error timeout invalid_header;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
# 设置转发地址
proxy_pass http://demo_web_service/;
}
}
# 配置服务地址
upstream demo_web_service {
server localhost:8080;
}
# Nginx 主要功能之三 —— 正向代理
# 正向代理的 Nginx 直接作为转发到外网 url 的转发器使用
server {
# 监听端口
listen 80;
# 服务的名称
server_name base_proxy;
# 编码格式
charset utf-8;
location / {
proxy_pass http://baidu.com;
}
}
# 如果觉得配置文件太长了,可以用 include 去引入其它的配置文件
# include servers.conf;
}