本文将深入探讨 Nginx 配置的几个关键方面,包括 URL 重写、代理转发以及如何根据 URL 模式修改代理行为。为了更好地理解,我们将提供测试代码及其详细注释。
基础配置:HTTP 重定向
强制 HTTP 跳转到 HTTPS
对于安全性要求较高的网站,通常需要将 HTTP 流量重定向到 HTTPS。以下是实现此目的的 Nginx 配置:
server {
listen 80;
server_name example.com;
# HTTP 强制跳转到 HTTPS
rewrite ^(.*)$ https://$server_name$1 permanent;
}
-
listen 80;
表示 Nginx 监听 80 端口,即 HTTP 默认端口。 -
server_name example.com;
定义服务器名称。 -
rewrite ^(.*)$ https://$server_name$1 permanent;
用于重写 URL。其中^(.*)$
是一个正则表达式,匹配任意请求。$1
表示重写规则中捕获的第一个分组。permanent
指明这是一个永久重定向。
请求重定向到指定地址
server {
listen 80;
server_name example.com;
location /api/ {
# HTTP 强制跳转到 百度
# 将所有访问 `http://127.0.0.1:8000/api/` 的请求重定向到 `https://www.baidu.com`,并且忽略原始请求中 `/api/` 之后的任何路径和查询参数
rewrite ^/api/(.*)$ https://www.baidu.com/ permanent;
# 保留原始请求的路径和查询参数并附加到百度的 URL 上
# rewrite ^/api/(.*)$ https://www.baidu.com/$1$is_args$args permanent;
}
}
-
listen 8000;
:表示 Nginx 监听 8000 端口。 -
server_name 127.0.0.1;
:定义服务器的名称或 IP 地址。 -
location /api/ { ... }
:指定当请求的 URL 路径以/api/
开头时,应用这个location
块的配置。 -
rewrite ^/api/(.*)$ https://www.baidu.com permanent;
:使用rewrite
指令进行 URL 重写。 -
^/api/(.*)$
是一个正则表达式,用于匹配以/api/
开头的任意路径。这里的(.*)
捕获/api/
后面的任意字符(如果有的话)。 -
https://www.baidu.com
是重定向的目标地址。 -
permanent
表示这是一个永久重定向,会向客户端返回 HTTP 状态码 301。 -
$is_args
:这是一个 Nginx 变量,如果原始请求中有查询参数,则返回一个?
;否则返回空字符串。 -
$args
或$query_string
:表示原始请求的查询参数部分。
高级配置:代理转发
基本的代理转发
在 Nginx 中,可以将请求代理到另一个服务器。以下是一个基本的代理转发配置:
# 请求地址: http://example.com/api/users
# 实际地址: http://127.0.0.1:8000/users
location /api/ {
proxy_pass http://127.0.0.1:8000/;
proxy_set_header Host $http_host;
proxy_set_header X-Real-IP $remote_addr;
}
# 请求地址: http://example.com/api/users
# 实际地址: http://127.0.0.1:8000/api/users
location /api/ {
proxy_pass http://127.0.0.1:8000;
proxy_set_header Host $http_host;
proxy_set_header X-Real-IP $remote_addr;
}
-
location /api/
指定只有当请求路径符合/api/
时,才应用该配置。 -
proxy_pass http://127.0.0.1:8000/;
将请求转发到另一个服务器。这里,它将请求转发到运行在本机的 8000 端口上的服务。 -
proxy_set_header
设置传递给代理服务器的 HTTP 头部。
处理 URL 模式
Nginx 允许根据不同的 URL 模式来修改代理行为。以下是一个处理不同 URL 模式的配置示例:
# 第一种情况 匹配地址有/ 代理地址无斜杠
# 请求地址:http://example.com/api/users
# 实际访问地址:http://127.0.0.1:8000/api/users
# 在这种配置中,请求的 URI /api/users 会被直接附加到代理地址 http://127.0.0.1:8000 后面。
location ^~/api/ {
proxy_pass http://127.0.0.1:8000;
}
# 第二种情况:匹配地址有/ 代理地址有斜杠
# 请求地址:http://example.com/api/users
# 实际访问地址:http://127.0.0.1:8000/users
# 在这种配置中,/api/ 部分被从请求的 URI 中移除,并将剩余部分 /users 附加到 http://127.0.0.1:8000/。
location ^~/api/ {
proxy_pass http://127.0.0.1:8000/;
}
# 第三种情况:匹配地址无/ 代理地址无斜杠
# 请求地址:http://example.com/apiusers
# 实际访问地址:http://127.0.0.1:8000/apiusers
# 在这种配置中,由于没有结尾斜杠,请求的 URI /apiusers 会被直接附加到 http://127.0.0.1:8000 后面。
location ^~/api {
proxy_pass http://127.0.0.1:8000;
}
# 第四种情况:匹配地址无/ 代理地址有斜杠
# 请求地址:http://example.com/apiusers
# 实际访问地址:http://127.0.0.1:8000/users
# 在这种配置中,由于存在代理地址的结尾斜杠,Nginx 将从请求的 URI /apiusers 中移除 /api 部分,并将剩余部分 users 附加到代理地址 http://127.0.0.1:8000/。
location ^~/api {
proxy_pass http://127.0.0.1:8000/;
}
-
^~/api/
匹配以/api/
开头的请求。proxy_pass
无斜杠,意味着 Nginx 会保留原始请求路径的/api/
部分。 -
^~/api
匹配以/api
开头的请求。这里,proxy_pass
有斜杠,意味着 Nginx 在转发请求时,会去除/api
部分。