一、域名重定向 Redirect¶
自定义 NGINX 的方式有以下三种:
-
ConfigMap:使用 Configmap 在 NGINX 中设置全局配置。
-
Annotations: 如果您想要特定 Ingress 规则的特定配置,请使用此选项。
- Custom template: 当需要更具体的设置时,例如open_file_cache, 调整listen 选项为
rcvbuf或无法通过 ConfigMap 更改配置
注意:ConfigMap和Annotations同时配置时,Annotations优先级更高
当一个服务需要更换域名时,并不能对其直接更改,需要一个过渡的过程。在这个过程中,需要将旧域名的访问跳转到新域名,此时可以使用Redirect功能。待旧域名无访问时,再停止旧域名。
在Nginx作为代理服务器时,Redirect可用于域名的重定向,比如访问old.com被重定向到new.com。Ingress可以更简单地实现Redirect功能。接下来用nginx.redirect.com作为旧域名,baidu.com作为新域名进行演示:
1.编写yaml文件
[root@k8s-master01 ~]# vim ingress-redirect.yaml
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
annotations:
nginx.ingress.kubernetes.io/permanent-redirect: https://www.baidu.com
nginx.ingress.kubernetes.io/permanent-redirect-code: '308'
name: nginx-redirect
namespace: study-ingress
spec:
ingressClassName: nginx
rules:
- host: test.zhang-qing.com
http:
paths:
- backend:
service:
name: nginx
port:
number: 80
path: /
pathType: ImplementationSpecific
上面参数说明:
(1)apiVersion: networking.k8s.io/v1: 指定使用的Kubernetes API版本,这里是Networking API的版本
(2)kind: Ingress: 表示这是一个Ingress资源对象
(3)metadata: 包含Ingress资源的元数据信息,包括名称和所属的命名空间。
annotations: 为Ingress资源添加注解,用于配置Ingress控制器的行为nginx.ingress.kubernetes.io/permanent-redirect: https://www.baidu.com: 这个注解指示nginx-ingress控制器对所有请求进行永久重定向(308重定向)到https://www.baidu.com。所有到nginx.redirect.com的请求都会被永久重定向到https://www.baidu.com网站。nginx.ingress.kubernetes.io/permanent-redirect-code: '308': 这个注解设置重定向的HTTP状态码为308。HTTP状态码308表示永久重定向,告诉客户端以后应该直接使用重定向的URI。这与常见的301和302重定向不同,301和302是临时重定向name: nginx-redirect: Ingress资源的名称,这里命名为nginx-redirect。namespace: study-ingress: Ingress资源所属的命名空间,这里是study-ingress。
(4)spec: 指定了Ingress资源的规则和配置
(5)rules: 定义了Ingress资源的规则列表。每个规则指定了如何将请求路由到后端服务
- host: nginx.test.com: 这个规则适用于主机名为nginx.test.com的请求。http:: 表示这个规则适用于HTTP流量。paths:: 定义了路径规则列表,允许将特定路径的请求转发到后端Servicebackend: 路径规则的后端定义。指定了后端Service的信息。service:: 后端Service的名称为nginx。port:: Service的端口号为80。path: /: 定义了将匹配的请求转发到后端Service的路径。这里设置为根路径/,表示所有请求都会匹配。pathType: ImplementationSpecific: 定义了路径类型,表示Kubernetes根据实现来选择路径类型。在这里设置为ImplementationSpecific,由Ingress控制器特定的实现来决定路径类型
2.创建新的Ingress
[root@k8s-master01 ~]# kubectl create -f ingress-redirect.yaml
3.测试访问,观察到状态码为308
root@k8s-master01 day012]# curl -I test.zhang-qing.com
HTTP/1.1 308 Permanent Redirect
Date: Wed, 19 Mar 2025 05:13:31 GMT
Content-Type: text/html
Content-Length: 164
Connection: keep-alive
Location: https://www.baidu.com
上面curl参数说明:
-H选项用于添加自定义HTTP头部-I选项表示仅请求HTTP头部信息而不返回主体内容。这是一个常用的用法,用于仅获取服务器的响应头部,而不下载完整的响应内容。
4.打开浏览器,输入nginx.redirect.com即可跳转到百度页面

5.环境复原
[root@k8s-master01 ~]# kubectl delete -f ingress-redirect.yaml
二、前后端分离 Rewrite¶
现在大部分应用都是前后端分离的架构,也就是前端用某个域名的根路径进行访问,后端接口采用/api进行访问,用来区分前端和后端。或者同时具有很多个后端,需要使用/api-a到A服务,/api-b到B服务,但是由于A和B服务可能并没有/api-a和/api-b的路径,会出现404的报错。

此时需要将/api-x重写为“/”,才可以正常到A或者B服务

下面通过Rewrite功能达到上述效果
1.创建一个应用模拟后端服务:
[root@k8s-master01 ~]# kubectl create deploy backend-api --image=registry.cn-hangzhou.aliyuncs.com/abroad_images/nginx:backend-api -n study-ingress
2.查看后端服务是否启动
[root@k8s-master01 ~]# kubectl get po -n study-ingress
NAME READY STATUS RESTARTS AGE
backend-api-cc76d4b77-bmzx2 1/1 Running 0 102s
3.创建Service暴露该应用:
[root@k8s-master01 ~]# kubectl expose deploy backend-api --port 80 -n study-ingress
4.查看该 Service 的地址,并且通过/api-a 访问测试,发现访问失败
[root@k8s-master01 ~]# kubectl get svc -n study-ingress
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
backend-api ClusterIP 10.107.131.177 <none> 80/TCP 7s
nginx ClusterIP 10.111.129.142 <none> 80/TCP 6h8m
[root@k8s-master01 ~]# curl 10.107.131.177/api-a
<html>
<head><title>404 Not Found</title></head>
<body>
<center><h1>404 Not Found</h1></center>
<hr><center>nginx/1.15.12</center>
</body>
</html>
5.测试直接访问根路径,发现是可以的
[root@k8s-master01 ~]# curl 10.107.131.177
<h1> backend for ingress rewrite </h1>
<h2> Path: /api-a </h2>
<a href="http://gaoxin.kubeasy.com"> Kubeasy </a>
6.通过 Ingress Nginx 的 Rewrite 功能,将/api-a 重写为"/"
[root@k8s-master01 ~]# vim rewrite.yaml
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
annotations:
nginx.ingress.kubernetes.io/rewrite-target: /$2
name: backend-api
namespace: study-ingress
spec:
ingressClassName: nginx
rules:
- host: test.zhang-qing.com
http:
paths:
- backend:
service:
name: backend-api
port:
number: 80
path: /api-a(/|$)(.*)
pathType: ImplementationSpecific
上面参数说明:
(1)apiVersion: networking.k8s.io/v1: 指定使用的Kubernetes API版本,这里是Networking API的版本
(2)kind: Ingress: 表示这是一个Ingress资源对象
(3)metadata: 包含Ingress资源的元数据信息,包括名称和所属的命名空间。
-
annotations: 为Ingress资源添加注解,用于配置Ingress控制器的行为 -
nginx.ingress.kubernetes.io/rewrite-target: /$2: 这个注解指示nginx-ingress控制器对请求进行重写。具体来说,它将会重写请求路径为/$2。这里的$2是一个正则表达式中的反向引用,表示匹配到的第二个括号中的内容。 name: backend-api: Ingress资源的名称,这里命名为backend-api。namespace: study-ingress: Ingress资源所属的命名空间,这里是study-ingress。
(4)spec: 指定了Ingress资源的规则和配置
(5)rules: 定义了Ingress资源的规则列表。每个规则指定了如何将请求路由到后端服务
- host: nginx.test.com: 这个规则适用于主机名为nginx.test.com的请求。http:: 表示这个规则适用于HTTP流量。paths:: 定义了路径规则列表,允许将特定路径的请求转发到后端Servicebackend: 路径规则的后端定义。指定了后端Service的信息。service:: 后端Service的名称为backend-api。port:: Service的端口号为80。path: /api-a(/|$)(.*): 定义了将匹配的请求转发到后端Service的路径规则。这里的路径规则使用了正则表达式。/api-a: 匹配请求路径以/api-a开头;(/|$): 这是一个正则表达式,它匹配路径中的/或者空字符串(即路径结尾)。这样,请求可以匹配/api-a后直接以/结尾,也可以匹配/api-a/,甚至是/api-a/<任意路径>。(.*): 这也是一个正则表达式,它匹配路径中的任意字符,这样可以捕获请求路径中/api-a之后的内容。pathType: ImplementationSpecific: 定义了路径类型,表示Kubernetes根据实现来选择路径类型。在这里设置为ImplementationSpecific,由Ingress控制器特定的实现来决定路径类型
需要添加一个key为nginx.ingress.kubernetes.io/rewrite-target的annotation,并且value是$2,此时访问/api-a就会被重写为“/”,访问/api-a/xxx会被重写为/xxx。
7.创建该Ingress
[root@k8s-master01 ~]# kaf rewrite.yaml
8.打开浏览器,输入test.zhang-qing.com/api-a查看页面正常跳转,不会报404

9.环境复原
k delete -f rewrite.yaml