目录
1、工作层次
2、七层负载的应用场景
二、Ingress概念和应用场景
使用Nginx的Ingress内部工作原理图
基于Ingress API的七层实现
三、Ingress安装部署
1、各节点安装2个镜像
ingress>nginx-ingress-controller%E7%9A%84chart%E4%BB%A5%E5%8F%8A%E4%BF%AE%E6%94%B9values.yaml%E6%96%87%E4%BB%B6-toc" name="tableOfContents" style="margin-left:40px">2、下载ingress>nginx-ingress-controller的chart以及修改values.yaml文件
ingress>nginx-ingress-controller-toc" name="tableOfContents" style="margin-left:40px">3、部署ingress>nginx-ingress-controller
ingress-toc" name="tableOfContents" style="margin-left:0px">四、应用ingress
1、实验1—Ingress-nginx http代理
(1)创建单一服务
(2)创建第2个服务
2、实验2—Ingress-nginx https代理
3、实验3—Ingress-nginx BasicAuth
4、实验4—Ingress-nginx 域名重定向
5、实验5—Ingress-nginx 重写rewrite
6、实验6—Ingress-nginx 错误代码重定向 - 默认错误后端
ingress-nginx%20%E5%8C%B9%E9%85%8D%E8%AF%B7%E6%B1%82%E5%A4%B4-toc" name="tableOfContents" style="margin-left:40px">7、实验7—ingress-nginx 匹配请求头
ingress-nginx%C2%A0%20%E9%85%8D%E7%BD%AE%E9%BB%91%E7%99%BD%E5%90%8D%E5%8D%95-toc" name="tableOfContents" style="margin-left:40px">8、实验8—ingress-nginx 配置黑白名单
1、黑名单
(1)configmap添加黑名单
(2)annotations配置黑名单
2、白名单
(1)configmap添加白名单
(2)annotations配置黑名单
ingress-nginx%C2%A0%20%E9%80%9F%E7%8E%87%E9%99%90%E5%88%B6-toc" name="tableOfContents" style="margin-left:40px">9、实验9—ingress-nginx 速率限制
ingress-nginx%C2%A0%20%E7%81%B0%E5%BA%A6%E6%88%96%E8%80%85%E9%87%91%E4%B8%9D%E9%9B%80%E5%8F%91%E5%B8%83-toc" name="tableOfContents" style="margin-left:40px">10、实验10—ingress-nginx 灰度或者金丝雀发布
ingress-nginx%C2%A0%20%E4%BB%A3%E7%90%86%E5%90%8E%E7%AB%AFhttps%E5%8D%8F%E8%AE%AE-toc" name="tableOfContents" style="margin-left:40px">11、实验11—ingress-nginx 代理后端https协议
ingress-nginx%C2%A0%20%E5%9B%9B%E5%B1%82%E4%BB%A3%E7%90%86-toc" name="tableOfContents" style="margin-left:40px">12、实验12—ingress-nginx 四层代理
ingress-nginx%C2%A0%20%E5%9F%BA%E4%BA%8EUDP%E5%9B%9B%E5%B1%82%E4%BB%A3%E7%90%86-toc" name="tableOfContents" style="margin-left:40px">13、实验13—ingress-nginx 基于UDP四层代理
ingress-nginx%C2%A0%20%E9%93%BE%E8%B7%AF%E8%BF%BD%E8%B8%AA-toc" name="tableOfContents" style="margin-left:40px">14、实验14—ingress-nginx 链路追踪
一、四层负载与七层负载
四层负载均衡和七层负载均衡的主要区别在于它们工作的网络层次和功能特点。
1、工作层次
- 四层负载均衡:工作在OSI模型的第四层,即传输层,主要基于IP地址和端口号进行负载均衡。它通过修改数据包的IP地址和端口号来转发流量,不涉及应用层的内容。客户端和后端服务器是一次完整的TCP连接,负载均衡器只是起到转发作用。
- 它在接收到客户端的流量以后通过修改数据包的地址信息(目标地址和端口,以及源地址)将流量转发到应用服务器。其中目的地址即需要转发的目的服务器,源地址原本是客户端地址,但是转发中会把源地址修改为负载均衡服务器的地址。
- LVS是典型的四层负载均衡调度器,如下是基本架构。
- 七层负载均衡:工作在OSI模型的第七层,即应用层,可以根据应用层的内容(如HTTP头、URL路径、Cookie等)进行负载均衡。它能够解析应用层的数据,根据具体的请求信息进行更加精细的负载均衡。
- 它首先会与客户端建立一条完整的连接并将应用层的请求流量解析出来,再按照调度算法选择一个应用服务器,并与应用服务器建立另外一条连接将请求发送过去。所以七层负载均衡是需要建立两次连接。
- Nginx是典型的7层负载均衡调度器,如下是基本架构。
2、七层负载的应用场景
四层和七层负载均衡在实际应用中有什么区别呢?
比如,如果客户端想发起HTTPS的请求访问(安全性),假如你使用的是四层负载均衡器,因为四层负载均衡器只是转发,所以后端服务器要都是HTTPS服务才行。但如果是使用的七层负载均衡器的话, 因为是两次连接,客户端可以和Nginx走https服务,确保安全,第二次连接Nginx和后端服务器之间可以走http服务。
如下是通过Nginx七层负载均衡完成客户端和后端微服务的两次连接。
整体访问链接的过程如下:客户端首先访问的是nginx的ip+端口,以及页面地址。比如如果访问的是stu/xxx.phh页面,Nginx接收到请求后,因为Nginx是可以工作在七层负载,它可以解析数据包获取域名,得到域名后会在server区中找到访问stu的路径,反向代理指向http://stu:80地址,该地址在upstream区中是upstream stu,然后会有两台服务器,分别是14和15服务器,通过负载均衡算法,选中一台服务器进行访问建立连接。
在K8S集群中通过Nginx做七层负载均衡,整体框架可以如下。
通过创建nodeport-nginx的pod,可以让外网通过nodeport绑定的端口(10080和10443两个端口,这两个端口分别映射到nginx pod的80和443端口上),这两个端口的访问路由到由deployment控制器创建的nginx的pod,nginx因为工作在7层负载均衡,它会解析数据包,得到域名,根据配置内容,反向代理信息等,www1.xinxianghf.com的域名访问会代理到http://www1的地址,这个地址在upstream区域中,会找到server为www1svcIP:port的服务器地址,即途中名为www1的service的clusterIp地址及端口号,四层负载均衡服务器地址,这个www1的service会帮忙负载到对应下边的2台tomcat app=www1的服务器中的一台中。www2的访问路径同www1。
deployment中启动的nginx,其配置文件可以通过configmap文件进行版本管理,可以进行修改形成新的版本,不过configmap修改重新使得nginx生效需要手动重启。
以上是可以利用k8s已有的组件可以完成七层负载均衡的搭建。那为什么还需要Ingress呢,发现上面的框架中,我们还是需要手动配置Nginx的文件,设定好对应的service集群的ip和端口使之和实际的要匹配,也就是这部分需要人工手动进行配置,如果配置错了就会出现问题。
另外,每当有新服务加入,都需要对nginx相关的配置进行修改、升级,在服务数量逐渐变多后,该配置项目会变得越来越大,手工修改的风险也会逐渐增高。
那么需要一个工具来简化这一过程,希望可以通过简单的配置动态生成代理中复杂的配置,最好还可以顺手重新加载配置文件。
想想怎么实现配置的自动化生成和修改?
二、Ingress概念和应用场景
Ingress是API Server中的一个组件,Ingress 包含两大组件:Ingress Controller 和 Ingress。
Ingress并不直接处理或转发流量,它需要与Ingress Controller一起使用。Ingress Controller是一个实际处理流量的组件,它根据Ingress资源中定义的规则,将请求路由到正确的服务。这种组合使得在Kubernetes环境中能够方便地管理多个服务的访问入口。
- Ingress 资源对象:这是通过 YAML 文件配置的,它定义了请求如何转发到服务的规则。Ingress 对象可以包含多个规则,每个规则可以指定不同的域名、路径和后端服务。
- Ingress 控制器(Ingress Controller):这是一个运行在 Kubernetes 集群中的组件,它负责实现 Ingress 资源对象中定义的规则。Ingress 控制器通常是一个反向代理服务器,如 Nginx 或 Traefik,它根据 Ingress 规则来处理进入集群的流量。
一般,ingress-controller的形式都是一个pod,里面跑着daemon程序和反向代理程序。daemon负责不断监控集群的变化,根据 ingress对象生成配置并应用新配置到反向代理,比如ingress-nginx就是动态生成nginx配置,动态更新upstream,并在需要的时候reload程序应用新配置。为了方便,后面的例子都以k8s官方维护的ingress-nginx为例。
Ingress-Nginx github 地址:https://github.com/kubernetes/ingress-nginx
Ingress-Nginx 官方网站:https://kubernetes.github.io/ingress-nginx/
总结来说:ingress-controller才是负责具体转发的组件,通过各种方式将它暴露在集群入口,外部对集群的请求流量会先到 ingress-controller, 而ingress对象是用来告诉ingress-controller该如何转发请求,比如哪些域名、哪些URL要转发到哪些service等等。
Ingress 简单的理解就是你原来需要改 Nginx 配置,然后配置各种域名对应哪个 Service,现在把这个动作抽象出来,变成一个 Ingress 对象,你可以用 yaml 创建,每次不要去改 Nginx 了,直接改 yaml 然后创建/更新就行了;
Ingress Controller 通过与 Kubernetes API 交互,动态的去感知集群中 Ingress 规则变化,并按照规则模板生成一段 Nginx 配置,再写到 Nginx Pod 里,最后 reload 一下。
使用Nginx的Ingress内部工作原理图
store协程主要是监听变化事件,并根据事件情况分两条路径分发,如果是配置Nginx服务必要的信息则会直接给到Sync协程处理,如果不是,则写入缓存处理系统当中。分两条处理的思路是对于必要紧急的事件是需要实时性的处理的,而对于非实时性处理事件可以延后一段时间进行处理,因为处理结果是需要reload nginx服务的,这会有代价的。所以需要分开区别对待。
基于Ingress API的七层实现
三、Ingress安装部署
1、各节点安装2个镜像
docker pull registry.aliyuncs.com/google_containers/kube-webhook-certgen:v1.4.3
docker pull registry.aliyuncs.com/google_containers/ingress>nginx-ingress-controller:v1.10.0
在各个节点上都运行上面两条命令,拉取2个镜像到本地。
ingress>nginx-ingress-controller%E7%9A%84chart%E4%BB%A5%E5%8F%8A%E4%BF%AE%E6%94%B9values.yaml%E6%96%87%E4%BB%B6" name="2%E3%80%81%E4%B8%8B%E8%BD%BDingress>nginx-ingress-controller%E7%9A%84chart%E4%BB%A5%E5%8F%8A%E4%BF%AE%E6%94%B9values.yaml%E6%96%87%E4%BB%B6">2、下载ingress>nginx-ingress-controller的chart以及修改values.yaml文件
#chart包的下载地址
wget https://github.com/kubernetes/ingress-nginx/releases/download/helm-chart-4.8.3/ingress-nginx-4.8.3.tgz
tar -xf ingress-nginx-4.8.3.tgz
cd ingress-nginx/
vim values.yaml
修改values.yaml文件内容如下:
1)hostNetwork: false =》 hostNetwork: true
#开启与宿主机共享网络,就像docker的host网络模式,不用单独建立网络命名空间了
2)dnsPolicy: ClusterFirst =》 dnsPolicy: ClusterFirstWithHostNet
3)kind: Deployment =》 kind: DaemonSet
#修改默认控制器类型,DaemonSet让ingress>nginx-ingress有高可用的这么个机制,保证每个节点都有一个pod
4)ingressClassResource.default: false => ingressClassResource.default: true
#设置默认Ingress控制器类名,Ingress控制器有很多的,这里设置为nginx的意思是只要明确指定别的控制器,默认被nginx代理
5)注释掉digest值。如果你的digest值与官方不一致就会重新下载。
6)将2个镜像的registry和image都修改为上面pull到本地的名称。如下:
ingress>nginx-ingress-controller" name="3%E3%80%81%E9%83%A8%E7%BD%B2ingress>nginx-ingress-controller">3、部署ingress>nginx-ingress-controller
kubectl create ns ingress #单独建立命名空间是为了方便隔离,管理。
执行安装命令:
helm install ingress-nginx -n ingress ./ingress-nginx -f ./ingress-nginx/values.yaml
查看部署结果如下:
ingress" name="%E5%9B%9B%E3%80%81%E5%BA%94%E7%94%A8ingress">四、应用ingress
1、实验1—Ingress-nginx http代理
(1)创建单一服务
vim 5.ingress.yaml
####10章节,ingress-http代理
apiVersion: apps/v1
kind: Deployment
metadata:name: ngress-httpproxy-www1
spec:replicas: 2selector:matchLabels:hostname: www1template:metadata:labels:hostname: www1spec:containers:- name: nginximage: nginx: v1imagePullPolicy: IfNotPresentports:- containerPort: 80
---
apiVersion: v1
kind: Service
metadata:name: ingress-httpproxy-www1
spec:selector:hostname: www1 #标签选择器,匹配标签为hostname=www1的pod,也就是能够匹配到上面deployment控制器的pod。ports:- port: 80 #SVC暴露的端口targetPort: 80 #讲流量转发给容器的端口,必须要和containerPort一致protocol: TCP
---
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:name: ingress-httpproxy-www1
spec:# 指定使用的 Ingress 控制器类,这里使用 nginx。这就是安装部分修改的默认控制器类型,如果刚才设置了可以不写,反之则必须写。推荐写上ingressClassName: nginxrules: # 定义路由规则- host: www1.test.com # 第一条规则,基于域名 www1.test.comhttp: # 定义 HTTP 路由规则paths: # 定义路径规则- path: / # 匹配根路径 /pathType: Prefix # 路径匹配类型为前缀匹配(Prefix)backend: # 定义后端服务service: # 后端服务的定义name: ingress-httpproxy-www1 # 后端服务的名称port: # 后端服务的端口number: 80 # 端口号为 80
执行创建命令:kubectl create -f 5.ingress.yaml
检查对应的deployment、service、pod以及ingress创建成功。
在master01节点上访问服务:
在虚拟机外的物理主机上访问IP服务:
当访问物理ip地址的时候,返回404,原因是传统的nginx里面,有一个默认的服务,一般是第一个server区域,没有指定域名访问的话,就匹配第一个server区域,默认就是根目录下的index.html主页地址。但是在ingress里面,nginx做了修改,它没有默认的服务,如果没有指定域名,那就直接报404.
我们在mac os系统的/etc/hosts文件中添加:
192.168.21.12 www1.test.com
保存退出后,在浏览器中访问域名,成功。
(2)创建第2个服务
我们创建基于nginx:v2镜像之上提供www2域名访问的服务。
cp 5.ingress.yaml 6.ingress.yaml
修改6.ingress.yaml中所有www1为www2,以及把deployment的pod镜像nginx版本改为v2。
我们在mac os系统的/etc/hosts文件中添加:
192.168.21.12 www2.test.com
保存退出后,在浏览器中访问域名,成功。
查看ingress资源情况:
如上,我们创建了两个域名的服务,分别是www1.test.com以及www2.test.com,他们在hosts中都是使用了相同ip地址,访问都会流入到该IP的服务器节点上。最终通过ingress配置的访问路由规则,访问流入到service后端服务上。
最终实现了不同的域名访问不同的服务。
疑问:访问到了物理IP地址后,ingress>nginx-ingress-controller是如何将外部对集群的请求流量会先到其自己的?
我们查看下之前我们部署的ingress>nginx-ingress-controller服务,它是loadbalance类型的service。
利用ipvsadm -Ln命令查看负载均衡情况:
2、实验2—Ingress-nginx https代理
nginx https代理访问需要证书,实际环境中肯定是买的,但是学习自己可以做个测试的。
openssl req -x509 -sha256 -nodes -days 365 -newkey rsa:2048 -keyout tls.key -out tls.crt -subj "/CN=nginxsvc/O=nginxsvc"
创建secret资源对象,将私钥和证书加密,后面在ingress中引用
kubectl create secret tls ingress-nginx-tls --key tls.key --cert tls.crt
创建deployment控制器和service
####10章节,ingress-https代理
apiVersion: apps/v1
kind: Deployment
metadata:name: ingress-httpproxy-ssl
spec:replicas: 2selector:matchLabels:hostname: ssltemplate:metadata:labels:hostname: sslspec:containers:- name: nginximage: nginx:v3imagePullPolicy: IfNotPresentports:- containerPort: 80
---
apiVersion: v1
kind: Service
metadata:name: ingress-httpproxy-ssl
spec:selector:hostname: sslports:- port: 80targetPort: 80protocol: TCP
---
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:name: ingress-httpproxy-sslannotations:nginx.ingress.kubernetes.io/ssl-redirect: "true" # 强制将所有 HTTP 请求重定向到 HTTPS
spec:ingressClassName: nginx # 指定使用的 Ingress 控制器为 Nginxrules: # 定义 Ingress 的路由规则- host: ssl.test.com # 指定域名,匹配该域名的请求会被路由http:paths: # 定义路径规则- path: / # 匹配根路径pathType: Prefix # 路径匹配类型为前缀匹配backend: # 定义后端服务service:name: ingress-httpproxy-ssl # 后端服务的名称port:number: 80 # 后端服务的端口号tls: # 定义 TLS 配置- hosts: # 指定支持 TLS 的域名- ssl.test.com # 域名必须与 rules 中的 host 匹配secretName: ingress-nginx-tls # 引用包含 TLS 证书和私钥的 Secret
其中tls:会话卸载层,主要目的就是外部通过https访问到ingress后,会通过包括tls和私钥的secret进行认证以及解密操作等,这样利用这个层,使得后端服务不需要关注或耦合认证和解密等事项了。
我们在mac os系统的/etc/hosts文件中添加:
192.168.21.12 ssl.test.com
保存。
在虚拟机外的物理主机上访问essl.test.com域名:
3、实验3—Ingress-nginx BasicAuth
nginx可以实现用户的访问控制有很多种方法,但用的最多的就两种。
- 基于ip访问控制
location /admin {allow 192.168.1.0/24; # 允许 192.168.1.0/24 网段访问deny all; # 拒绝其他所有 IP 访问
}allow:允许指定的 IP 或网段访问。
deny:拒绝指定的 IP 或网段访问
- 基于用户认证的访问控制
Nginx 支持通过 HTTP 基本认证来限制访问。你需要创建一个密码文件,并在配置中启用认证#使用 htpasswd 工具创建密码文件
htpasswd -c /etc/nginx/.htpasswd username#在 Nginx 配置中启用基本认证
location /secure {auth_basic "Restricted Area"; # 认证提示信息auth_basic_user_file /etc/nginx/.htpasswd; # 密码文件路径
}
扩展介绍结束。接下来的实验就是基于用户认证的访问控制,毕竟ingress接口是基于nginx实现的,功能基本相同.
1)首先要安装httpd-tools程序,通过htpasswd命令创建http认证文件
yum -y install httpd-tools
htpasswd -c auth test
2-1)将生成的文件封装为secret,留给后续调用
kubectl create secret generic ingress-basic-auth --from-file=auth
将之前生成的auth文件封装到secret generic类型的对象里面(ingress-basic-auth),等待后续被调用。
2-2)也可以openssl passwd -crypt your_password将密码加密,然后手动创建用户,然后使用加密密码。然后创建一个文本文件,并按照以下格式添加用户名和加密密码
username:encrypted_password
二者选其一,看喜好。
Nginx 的 auth_basic 认证机制要求密码文件中的密码必须是加密的,而不是明文的。如果尝试在密码文件中使用明文密码,Nginx 将无法正确验证用户,从而导致认证失败。
3)创建资源文件以及部署
####10章节,ingress-BasicAuth代理
apiVersion: apps/v1
kind: Deployment
metadata:name: ingress-httpproxy-auth
spec:replicas: 2selector:matchLabels:hostname: authtemplate:metadata:labels:hostname: authspec:containers:- name: nginximage: nginx:v1imagePullPolicy: IfNotPresentports:- containerPort: 80
---
apiVersion: v1
kind: Service
metadata:name: ingress-httpproxy-auth
spec:selector:hostname: authports:- port: 80targetPort: 80protocol: TCP
---
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:name: ingress-with-authannotations:nginx.ingress.kubernetes.io/auth-type: basic # 启用 Basic Auth 基础认证nginx.ingress.kubernetes.io/auth-secret: ingress-basic-auth # 指定包含用户名和密码的 Secret对象名称。上一步我们已经创建了。nginx.ingress.kubernetes.io/auth-realm: 'Authentication Required - test' # 设置认证提示信息,显示在浏览器的认证对话框中
spec:ingressClassName: nginx # 指定使用的 Ingress Controller 类型为 nginxrules: # 定义路由规则- host: auth.flyinlinux.com # 配置域名规则,只有访问 auth.flyinlinux.com 时才会匹配此规则http: # 定义 HTTP 路由规则paths: # 定义路径规则- path: / # 匹配根路径(即所有路径)pathType: ImplementationSpecific # 路径匹配类型,由 Ingress Controller 本身实现决定backend: # 定义后端服务service: # 指定后端服务的名称和端口name: ingress-httpproxy-auth # 后端服务的名称port: # 后端服务的端口配置number: 80 # 后端服务的端口号
部署成功。
我们在mac os系统的/etc/hosts文件中添加:
192.168.21.12 auth.flyinlinux.com
在虚拟机外的物理主机上访问auto.flyinlinux.com域名:
没有出现清单中设置的提示信息,是因为在当下很多新版浏览器中它觉得这个提示多此一举,就不给提示了,老版本ie浏览器可以看到提示。
4、实验4—Ingress-nginx 域名重定向
####10章节,ingress-域名重定向
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:name: ingress-with-redirectannotations:kubernetes.io/ingress.class: "nginx" # 这个是k8s老版本写法,新版本写法是在spec.ingressClassName: nginx里面,见下。nginx.ingress.kubernetes.io/permanent-redirect: https://www.baidu.com # 配置永久重定向,将所有请求重定向到 https://www.baidu.comnginx.ingress.kubernetes.io/permanent-redirect-code: '301' # 指定重定向的 HTTP 状态码为 301(永久重定向)
spec: # 定义 Ingress 的具体规则ingressClassName: nginx # 指定使用的 Ingress Controller 类型为 nginx。 新版本写法。rules: # 定义路由规则- host: redirect.test.com # 配置域名规则,只有访问 redirect.test.com 时才会匹配此规则http: # 定义 HTTP 路由规则
创建及部署成功。
同上,增加域名。我们在mac os系统的/etc/hosts文件中添加:
192.168.21.12 redirect.test.com
在虚拟机外的物理主机上访问edirect.test.com域名:
5、实验5—Ingress-nginx 重写rewrite
原文链接:https://blog.csdn.net/qq_49148518/article/details/145048732
重写和重定向
Redirect(重定向)
作用:重定向是指服务器向客户端发出一个新的URL。让客户端进行新的请求。客户端会收到一个HTTP 3xx状态码,然后根据其中的重定向地址进行新的请求。这意味着客户端会知道发生了重定向。它会发起新的请求。
示例:假设现在有个网站旧地址是http://old.com,但现在想将所有的请求都转发https://new.com。这时就可以使用重定向将所有的HTTP请求重定向到HTTPS。
Rewrite(重写)
作用:重写是指修改请求的路径,但是客户端不会察觉到这个变化,它仅在服务器中发生。在k8s中,可以通过ingress的注解来配置重写规则。
示例:假设有个服务部署在/v1路径下,但是希望用户访问是不需要输入/v1,那就可以用重写将请求从根路径/重写到/v1。
Redirect和Rewrite的区别
影响范围:Rewrite只在服务器内部修改路径,不会影响到客户端,而Redirect则会向客户端发送一个新的URL,让客户端发起新的请求。
状态码:Rewrit不涉及状态码的改变,而Redirect会向客户端发送一个重定向的HTTP状态码如301、302等。
可见性:Rewrite对客户端来说是透明的,而Redirect则会告知客户端发生了重定向。
在选择使用 Rewrite 还是 Redirect 时,需要根据具体的需求来决定。如果你希望在不修改客户端请求的情况下修改路径,那么使用 Rewrite;如果你希望客户端知道发生了重定向,并且根据新的 URL 进行新的请求,那么使用 Redirect。
####10章节,ingress-域名重写
apiVersion: apps/v1
kind: Deployment
metadata:name: ingress-httpproxy-rewrite
spec:replicas: 2selector:matchLabels:hostname: rewritetemplate:metadata:labels:hostname: rewritespec:containers:- name: nginximage: nginx:v1imagePullPolicy: IfNotPresentports:- containerPort: 80
---
apiVersion: v1
kind: Service
metadata:name: ingress-httpproxy-rewrite
spec:selector:hostname: rewriteports:- port: 80targetPort: 80protocol: TCP
---
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:name: ingress-with-rewriteannotations:nginx.ingress.kubernetes.io/rewrite-target: /$2 # 配置 URL 重写规则,将匹配的路径重写为 /$2, 表示正则表达式中第二个捕获组的内容
spec:ingressClassName: nginx rules: # 定义路由规则- host: rewrite.test.com # 配置域名规则,只有访问 redirect.test.com 时才会匹配此规则http: # 定义 HTTP 路由规则paths: # 定义路径规则- path: /api(/|$)(.*) # 匹配路径规则,使用正则表达式匹配 /api 开头的路径pathType: ImplementationSpecific # 路径匹配类型,由 Ingress Controller 实现决定backend:service:name: ingress-httpproxy-rewriteport:number: 80
path: /api(/|$)(.*)这是一个 路径匹配规则,使用正则表达式定义哪些请求路径会被匹配。
正则表达式解析:
/api:匹配路径的开头必须是 /api。
(/|$):
(/|) 表示 /api 后面可以跟一个 /。
$ 表示 /api 可以直接结束(即路径就是 /api)。
(.*):这是一个捕获组,匹配 /api 或 /api/ 之后的所有内容。.* 表示匹配任意字符(除换行符外)零次或多次。
示例
如果请求路径是 /api/v1/resource:
正则表达式匹配后,$2 的值为 v1/resource。
重写后的路径为 /v1/resource。
如果请求路径是 /api/:
正则表达式匹配后,$2 的值为空。
重写后的路径为 /
创建及部署资源对象。
同上,增加域名。我们在mac os系统的/etc/hosts文件中添加:
192.168.21.12 rewrite.test.com
在虚拟机外的物理主机上访问rewrite.test.com域名:
在虚拟机外的物理主机上访问rewrite.test.com/api,结果如下:
在虚拟机外的物理主机上访问rewrite.test.com/api/index.html,结果如下:
为什么最后的两次访问能够正常访问呢,原因就是最后两次都符合重写路径截取之后获取的访问路径是正确的。如上的分析:
rewrite.test.com/api最后访问的就是rewrite.test.com根目录,因为默认访问根目录就是访问主页即index.html。
rewrite.test.com/api/index.html最后访问的就是rewrite.test.com/index.html,即指明访问主页即index.html。
6、实验6—Ingress-nginx 错误代码重定向 - 默认错误后端
如果ingress代理的服务都出现了问题或错误,我们不可能在每个服务的开发里面都嵌入问题处理的代码吗?其实没必要或者不是聪明的做法。我们可以在ingress nginx里面统一进行配置。但凡是通过ingress nginx访问的,出现的错误页,就可以给他一个默认页面用于展示错误或者出现一个小游戏等等。
因为这个错误页面无关乎具体服务页面,所以它的配置应该是在ingress nginx安装的时候就应该达到的这么一种配置要求。
安装的时候最好是想清楚配置一起安装,避免后续陆续的进行更新安装。
由于涉及到错误页面镜像打包,我的是苹果A1芯片的arm架构,需要自己动手封装,如果是amd64的,可以跟老师做下去。
目前暂时就没有做实验了。
最终效果如下,当访问一个不存在的页面时,就会重写到我们事先准备好的页面中。
ingress-nginx%20%E5%8C%B9%E9%85%8D%E8%AF%B7%E6%B1%82%E5%A4%B4" name="%E5%AE%9E%E9%AA%8C7-ingress-nginx%20%E5%8C%B9%E9%85%8D%E8%AF%B7%E6%B1%82%E5%A4%B4">7、实验7—ingress-nginx 匹配请求头
Ingress-Nginx中的
data.allow-snippet-annotations
是一个配置项,用于控制是否允许在Nginx配置中使用自定义的注解(annotations)。
功能描述
data.allow-snippet-annotations
配置项用于控制是否允许在Nginx配置中使用自定义的注解。当设置为true
时,允许在Nginx配置中使用自定义注解;否则,禁止使用自定义注解。
默认值和修改方法
默认情况下,data.allow-snippet-annotations
的值为false
,即默认情况下不允许使用自定义注解。如果需要启用自定义注解,需要在Nginx配置中显式设置该值为true
。
安全性影响
启用自定义注解可能会带来安全风险,因为这可能会让权限有限的用户获得访问集群中所有秘密的权限。因此,在使用自定义注解时需要谨慎处理,确保不会引入安全漏洞。
这个功能需要单独开启一下,修改ingress-nginx-controller控制器的配置文件:
1)kubectl edit cm -n ingress ingress-nginx-controller
2)将其中data.allow-snippet-annotations: "false" =》 data.allow-snippet-annotations: "true"
3)kubectl delete pod -n ingress --all #重新加载配置
创建资源文件
####第10章节,ingress-nginx snippet注解
apiVersion: apps/v1
kind: Deployment
metadata:name: snippetlabels:app: snippet
spec:selector:matchLabels:app: snippettemplate:metadata:labels:app: snippetspec:containers:- name: nginximage: nginx:v1
---
apiVersion: v1
kind: Service
metadata:name: snippetlabels:app: snippet
spec:ports:- name: 80-80port: 80targetPort: 80protocol: TCPselector:app: snippettype: ClusterIP
---
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:name: snippet.flyinlinux.comlabels:app: snippetannotations:# 使用 server-snippet 注解向 Nginx 配置中添加自定义指令 # 判断语句部分是nginx的配置语法nginx.ingress.kubernetes.io/server-snippet: |set $agentflag 0; # 定义一个变量 agentflag,初始值为 0if ($http_user_agent ~* "(Android|Iphone)") { # 检查 User-Agent 是否包含 Android 或 Iphoneset $agentflag 1; # 如果是移动设备,设置 agentflag 为 1}if ($agentflag = 1) { # 如果 agentflag 为 1return 302 http://www.baidu.com; # 返回 302 重定向到百度}
spec:rules:- host: snippet.test.com # 定义 Ingress 的域名http:paths:- path: / # 匹配所有路径pathType: Prefix # 路径匹配类型为前缀匹配backend:service:name: snippet # 后端服务名称port:number: 80 # 后端服务端口
部署资源对象
同上,增加域名。我们在mac os系统的/etc/hosts文件中添加:
192.168.21.12 snippet.test.com
在虚拟机外的物理主机上访问snippet.test.com域名:
假如我们将请求头里面的User-Agent标识为Android的话,看下结果:
curl snippet.test.com -H 'User-Agent: Android' -I
302重定向到了www.baidu.com网址上了。
所以结论是,我们可以通过在Ingress资源清单中使用 server-snippet 注解向 Nginx 配置中添加自定义指令,可以解析请求头中的内容,从而实现不同请求头可以重定向到目的网址。
ingress-nginx%C2%A0%20%E9%85%8D%E7%BD%AE%E9%BB%91%E7%99%BD%E5%90%8D%E5%8D%95" name="8%E3%80%81%E5%AE%9E%E9%AA%8C8%E2%80%94ingress-nginx%C2%A0%20%E9%85%8D%E7%BD%AE%E9%BB%91%E7%99%BD%E5%90%8D%E5%8D%95">8、实验8—ingress-nginx 配置黑白名单
1、黑名单
在Ingress资源清单的规则配置中,设置哪些IP不可被访问,除此外都可被访问。
(1)configmap添加黑名单
ingress%20nginx%20controller%E6%8E%A7%E5%88%B6%E5%99%A8%E7%9A%84configmap%E5%AF%B9%E8%B1%A1%EF%BC%8C%E4%BF%AE%E6%94%B9%E9%87%8C%E9%9D%A2%E7%9A%84%E9%85%8D%E7%BD%AE%E5%8F%82%E6%95%B0%EF%BC%9A" name="%E6%89%93%E5%BC%80ingress%20nginx%20controller%E6%8E%A7%E5%88%B6%E5%99%A8%E7%9A%84configmap%E5%AF%B9%E8%B1%A1%EF%BC%8C%E4%BF%AE%E6%94%B9%E9%87%8C%E9%9D%A2%E7%9A%84%E9%85%8D%E7%BD%AE%E5%8F%82%E6%95%B0%EF%BC%9A">打开ingress nginx controller控制器的configmap对象,修改里面的配置参数:
执行命令:kubectl edit cm -n ingress ingress-nginx-controller
修改为:
data
allow-snippet-annotations: "true"
block-cidrs:block-cidrs: 192.168.21.12 #新增,如有多个ip用逗号隔开即可
修改完成后,重新加载配置:kubectl delete pod -n ingress --all
如上我们对node01节点的ip设置了黑名单。
block-cidrs是由ingress-nginx官方提供的:https://kubernetes.github.io/ingress-nginx/user-guide/nginx-configuration/configmap/
在每个节点上都添加域名和ip映射。
echo "192.168.21.12 snippet.test.com" >>/etc/hosts
访问三个节点情况:
但是为什么node01节点上访问snippet.test.com竟然可以?按说应该访问受限才对。因为node01节点的IP是192.168.21.12。
后续找下这个bug。
(2)annotations配置黑名单
我们先去掉上面在configmap里面设置的黑名单。
####第10章节,ingress-nginx annotation配置黑名单
apiVersion: apps/v1
kind: Deployment
metadata:name: black-deploylabels:app: black
spec:selector:matchLabels:app: blacktemplate:metadata:labels:app: blackspec:containers:- name: nginximage: nginx:v1imagePullPolicy: IfNotPresent # 镜像拉取策略:如果本地不存在则拉取
---
apiVersion: v1
kind: Service
metadata:name: black-svclabels:app: black
spec:selector:app: black # 选择器,匹配具有 app=black 标签的 Podports:- name: 80-80port: 80 # 服务暴露的端口targetPort: 80 # 容器监听的端口type: ClusterIP # 服务类型为 ClusterIP,仅集群内部访问
---
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:name: black.test.com # Ingress 资源名称annotations:# 使用 server-snippet 注解向 Nginx 配置中添加自定义指令nginx.ingress.kubernetes.io/server-snippet: |-deny 192.168.21.12; # 拒绝来自 192.168.21.12 的请求allow all; # 允许所有其他请求
spec:rules:- host: black.test.com # 定义 Ingress 的域名http:paths:- path: / # 匹配所有路径pathType: Prefix # 路径匹配类型为前缀匹配backend:service:name: black-svc # 后端服务名称port:number: 80 # 后端服务端口
完成创建和部署。
同上,增加域名。我们在mac os系统的/etc/hosts文件中添加:
192.168.21.12 black.test.com
在虚拟机外的物理主机上访问black.test.com域名:
在集群节点访问,结果都能访问,理论上node01节点是192.168.21.12的地址是黑名单,不能访问的,后续找下这个bug。
2、白名单
在Ingress资源清单的规则配置中,设置哪些IP可以被访问,除此外都不可被访问。
(1)configmap添加白名单
打开ingress nginx controller控制器的configmap对象,修改里面的配置参数:
执行命令:kubectl edit cm -n ingress ingress-nginx-controller
修改为:
data
allow-snippet-annotations: "true"
whitelist-source-range: 192.168.21.11 #新增,只让该IP的节点能访问。
修改完成后,重新加载配置:kubectl delete pod -n ingress --all
资源清单文件:
####第10章节,ingress-nginx configmap配置白名单
apiVersion: apps/v1
kind: Deployment
metadata:labels:app: testname: test-deploy
spec:replicas: 1selector:matchLabels:app: testtemplate:metadata:labels:app: testspec:containers:- image: nginx:v2name: myapp
---
apiVersion: v1
kind: Service
metadata:labels:app: testname: test-svc
spec:ports:- name: 80-80port: 80protocol: TCPtargetPort: 80selector:app: testtype: ClusterIP
---
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:name: test.flyinlinux.com
spec:rules:- host: test.flyinlinux.comhttp:paths:- path: /pathType: Prefixbackend:service:name: test-svc port:number: 80
创建及部署后,每个节点添加ip域名映射:echo "192.168.21.12 test.flyinlinux.com" >> /etc/hosts
访问192.168.21.11 master01节点,可以访问成功。因为之前我们添加了该节点到白名单里面。
访问其他节点都不成功。验证正确。
(2)annotations配置黑名单
我们先把上面在ingress nginx controller控制器的configmap对象里面的白名单删掉,保存退出后重启pod节点。
####第10章节,ingress-nginx annotation配置白名单
apiVersion: apps/v1
kind: Deployment
metadata:name: white-deploylabels:app: white
spec:selector:matchLabels:app: whitetemplate:metadata:labels:app: whitespec:containers:- name: nginximage: nginximagePullPolicy: IfNotPresent # 镜像拉取策略:如果本地不存在则拉取
---
apiVersion: v1
kind: Service
metadata:name: white-svclabels:app: white
spec:selector:app: white # 选择器,匹配具有 app=white 标签的 Podports:- name: 80-80port: 80 # 服务暴露的端口targetPort: 80 # 容器监听的端口type: ClusterIP # 服务类型为 ClusterIP,仅集群内部访问
---
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:name: white.flyinlinux.com # Ingress 资源名称annotations:# 使用 whitelist-source-range 注解配置 IP 白名单nginx.ingress.kubernetes.io/whitelist-source-range: 192.168.21.11 # 只允许 192.168.21.11 访问
spec:rules:- host: white.flyinlinux.com # 定义 Ingress 的域名http:paths:- path: / # 匹配所有路径pathType: Prefix # 路径匹配类型为前缀匹配backend:service:name: white-svc # 后端服务名称port:number: 80 # 后端服务端口
创建及部署后,每个节点添加ip域名映射:echo "192.168.21.12 white.flyinlinux.com" >> /etc/hosts.
访问master01节点(192.168.21.11)成功。
访问其他节点不成功。验证正确。
ingress-nginx%C2%A0%20%E9%80%9F%E7%8E%87%E9%99%90%E5%88%B6" name="9%E3%80%81%E5%AE%9E%E9%AA%8C9%E2%80%94ingress-nginx%C2%A0%20%E9%80%9F%E7%8E%87%E9%99%90%E5%88%B6">9、实验9—ingress-nginx 速率限制
其中nginx.ingress.kubernetes.io/limit-whitelist: 速率限制白名单,含义是在白名单里面的不受速率限制,其余都受速率限制。
####第10章节,ingress-nginx 速率限制
apiVersion: apps/v1
kind: Deployment
metadata:name: speedlabels:app: speed
spec:selector:matchLabels:app: speedtemplate:metadata:labels:app: speedspec:containers:- name: speedimage: nginx:v3imagePullPolicy: IfNotPresent # 镜像拉取策略:如果本地不存在则拉取ports:- containerPort: 80 # 容器监听的端口
---
apiVersion: v1
kind: Service
metadata:name: speedlabels:app: speed
spec:selector:app: speed # 选择器,匹配具有 app=speed 标签的 Podports:- name: 80-80port: 80 # 服务暴露的端口targetPort: 80 # 容器监听的端口protocol: TCP # 协议类型为 TCPtype: ClusterIP # 服务类型为 ClusterIP,仅集群内部访问
---
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:name: speed.test.com # Ingress 资源名称
spec:rules:- host: speed.test.com # 定义 Ingress 的域名http:paths:- path: / # 匹配所有路径pathType: Prefix # 路径匹配类型为前缀匹配backend:service:name: speed # 后端服务名称port:number: 80
创建及部署后,每个节点添加ip域名映射:echo "192.168.21.12 speed.test.com" >> /etc/hosts.
访问master01节点(192.168.21.11)以及node01、node02节点都是成功的。
接下来我们通过压测工具ab,如果没安装,通过yum install httpd-tools进行安装。
其中:-c指定并发数量10,-n请求数量100。
执行结果,成功请求了100个,失败为0个。每个请求的耗时0.555ms。
接下来我们进行限速测试:
#在上面的ingress资源清单的配置部分加上一条注解
metadata.annotations: nginx.ingress.kubernetes.io/limit-connections: "1"
这个含义是限制并发数量为1个。
#应用更新配置
kubectl apply -f 16.speed_ingress.yaml
通过压测工具测试限制并发为1的结果:
ingress-nginx%C2%A0%20%E7%81%B0%E5%BA%A6%E6%88%96%E8%80%85%E9%87%91%E4%B8%9D%E9%9B%80%E5%8F%91%E5%B8%83" name="10%E3%80%81%E5%AE%9E%E9%AA%8C10%E2%80%94ingress-nginx%C2%A0%20%E7%81%B0%E5%BA%A6%E6%88%96%E8%80%85%E9%87%91%E4%B8%9D%E9%9B%80%E5%8F%91%E5%B8%83">10、实验10—ingress-nginx 灰度或者金丝雀发布
我们实验Ingress在不宕机的情节下完成公司代码的灰度发布。
首先我们发布v1版本的软件,当前我们通过nginx模拟我们的开发软件。
####第10章节,ingress-nginx 灰度或金丝雀发布
apiVersion: apps/v1
kind: Deployment
metadata:name: v1-deploylabels:app: v1
spec:replicas: 10selector:matchLabels:app: v1template:metadata:labels:app: v1spec:containers:- name: app-v1image: nginx:v1imagePullPolicy: IfNotPresent
---
apiVersion: v1
kind: Service
metadata:name: v1-svclabels:app: v1
spec:selector:app: v1type: ClusterIPports:- name: 80-80port: 80targetPort: 80
---
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:name: v1.test.com
spec:rules:- host: svc.test.comhttp:paths:- path: /pathType: Prefixbackend:service:name: v1-svcport:number: 80
创建及部署后,每个节点添加ip域名映射:echo "192.168.21.12 svc.test.com" >> /etc/hosts.
访问master01节点(192.168.21.11)以及node01、node02节点都是成功的。
发布成功了,然后等一段时间后我们出了v2版本软件了,需要替换之前的v1版本软件,采用灰度或金丝雀部署方式。
我们同样按照v1发布的方式创建资源清单文件。
####第10章节,ingress-nginx 灰度或金丝雀发布
###v2版本软件
apiVersion: apps/v1
kind: Deployment
metadata:name: v2-deploylabels:app: v2
spec:replicas: 10selector:matchLabels:app: v2template:metadata:labels:app: v2spec:containers:- name: app-v2image: nginx:v2imagePullPolicy: IfNotPresent
---
apiVersion: v1
kind: Service
metadata:name: v2-svclabels:app: v2
spec:selector:app: v2type: ClusterIPports:- name: 80-80port: 80targetPort: 80
---
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:name: v2.test.comannotations:nginx.ingress.kubernetes.io/canary: "true" # 启用金丝雀nginx.ingress.kubernetes.io/canary-weight: "10" #百分比,金丝雀部署权重10%
spec:rules:- host: svc.test.com # 定义 Ingress 的域名。注意:这个名称跟V1版本的Ingress主机名是一样的,因为只有一样才能完成金丝雀部署。http:paths:- path: / # 匹配所有路径pathType: Prefix # 路径匹配类型为前缀匹配backend:service:name: v2-svc # 后端服务名称port:number: 80 # 后端服务端口
注意:这个名称跟V1版本的Ingress主机名是一样的,因为只有一样才能完成金丝雀部署。
创建部署完成:
我们接下来写一个访问100次的脚本,得到访问结果做一个统计。
#两个控制器一共20个pod,但是使用的是同个域名,访问100次看看结果
for i in {1..100} ;do curl svc.test.com >> sum ;done
感觉比例不是很准,总是差几个,不过无所谓了,要是觉得10%不够,可以改成50%
#统计访问
cat sum |sort |uniq -c
比例不会是刚好10%的比例,会有些浮动。
我们将浓度改为50%之后看下效果。
rm -fr sum 删掉sum文件,重新访问100次,以及统计下sum的结果。结果接近50%的比例了。
所以,通过调整浓度比例,可以逐步扩大范围,达到最终替换原来版本。
ingress-nginx%C2%A0%20%E4%BB%A3%E7%90%86%E5%90%8E%E7%AB%AFhttps%E5%8D%8F%E8%AE%AE" name="11%E3%80%81%E5%AE%9E%E9%AA%8C11%E2%80%94ingress-nginx%C2%A0%20%E4%BB%A3%E7%90%86%E5%90%8E%E7%AB%AFhttps%E5%8D%8F%E8%AE%AE">11、实验11—ingress-nginx 代理后端https协议
nginx跟后端进行代理动作的时候,提供非加密或者加密类型的链接给用户使用。
前面的实验nginx代理后端都是用的http协议,之所以不用https是因为后端都是在内网环境,存在的安全问题相对很小。代理使用https协议较少使用,但是我们还是需要掌握其知识。
####第10章节,ingress-nginx 代理https协议
apiVersion: apps/v1
kind: Deployment
metadata:labels:app: proxyhttps # 标签,用于标识资源name: proxyhttps-deploy # Deployment 名称
spec:replicas: 1 # 副本数selector:matchLabels:app: proxyhttps # 选择器,匹配具有 app=proxyhttps 标签的 Podtemplate:metadata:labels:app: proxyhttps # Pod 的标签spec:containers:- image: wangyanglinux/tools:httpsv1 # 使用的镜像,里面包括了一个Go语言写的基于https的应用name: myapp # 容器名称
---
apiVersion: v1
kind: Service
metadata:labels:app: proxyhttps # 标签,用于标识资源name: proxyhttps-svc # Service 名称
spec:ports:- name: 443-443 # 端口名称port: 443 # 服务暴露的端口protocol: TCP # 协议类型为 TCPtargetPort: 443 # 容器监听的端口selector:app: proxyhttps # 选择器,匹配具有 app=proxyhttps 标签的 Podtype: ClusterIP # 服务类型为 ClusterIP,仅集群内部访问
---
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:annotations:nginx.ingress.kubernetes.io/backend-protocol: HTTPS # 指定后端协议为 HTTPSname: proxyhttps.test.com # Ingress 资源名称namespace: default # 命名空间
spec:rules:- host: proxyhttps.test.com # 定义 Ingress 的域名http: #这是一个默认标记,目前版本就只有http没有httpspaths:- path: / # 匹配所有路径pathType: Prefix # 路径匹配类型为前缀匹配backend:service:name: proxyhttps-svc # 后端服务名称port:number: 443 # 后端服务端口
同样在我们在mac os系统的/etc/hosts文件中添加:
192.168.21.12 proxyhttps.xinxianghf.com
在浏览器中访问。走http协议访问成功:
走https协议访问成功:
ingress-nginx%C2%A0%20%E5%9B%9B%E5%B1%82%E4%BB%A3%E7%90%86" name="12%E3%80%81%E5%AE%9E%E9%AA%8C12%E2%80%94ingress-nginx%C2%A0%20%E5%9B%9B%E5%B1%82%E4%BB%A3%E7%90%86">12、实验12—ingress-nginx 四层代理
实际生产中,四层负载肯定首先使用service(ipvs),而Nginx 1.9.0版本起支持四层负载均衡,从而使得nginx变得更加强大。
因为是做实验,所以将ingress-nginx 的这个四层代理都试了一下。并不代表这个功能就一定需要去使用。
实验目标:将部署的httpsproxy的pod,通过四层负载的方式,将其暴露出来。
#实现四层代理需要修改ingress-nginx控制器,因为是用ds方式安装的,所以修改ds中的参数
kubectl edit ds -n ingress ingress-nginx-controller
ds.sepc.template.spec.containers
- args: # 定义容器的启动参数- /ingress>nginx-ingress-controller # 容器启动时执行的命令,即 ingress>nginx-ingress-controller 二进制文件- --tcp-services-configmap=$(POD_NAMESPACE)/ingress>nginx-ingress-tcp-configmap # 修改为四层负载的配置文件。指定 TCP 服务的 ConfigMap,$(POD_NAMESPACE) 是环境变量,表示 Pod 所在的命名空间,将 Pod 所在的命名空间下的ingress>nginx-ingress-tcp-configmap里面的信息变成四层负载的配置文件加载到当前的nginx文件中,并生效。#创建ConfigMap进行应用
apiVersion: v1
kind: ConfigMap
metadata:name: ingress>nginx-ingress-tcp-configmapnamespace: ingress # ConfigMap 所在的命名空间为 ingress
data:"9000": "default/proxyhttps-svc:443" # 将 TCP 端口 9000 映射到 default 命名空间中的 proxyhttps-svc 服务的 443 端口#用来测试功能的代码
apiVersion: apps/v1 # 指定 Kubernetes API 版本为 apps/v1
kind: Deployment # 定义资源类型为 Deployment
metadata: # 定义 Deployment 的元数据labels: # 定义 Deployment 的标签app: proxyhttps # 标签键值对,标识该 Deployment 属于 proxyhttps 应用name: proxyhttps-deploy # Deployment 的名称为 proxyhttps-deploy
spec: # 定义 Deployment 的规格replicas: 1 # 指定 Pod 的副本数为 1selector: # 定义 Deployment 如何选择管理的 PodmatchLabels: # 使用标签选择器app: proxyhttps # 选择标签为 app: proxyhttps 的 Podtemplate: # 定义 Pod 的模板metadata: # 定义 Pod 的元数据labels: # 定义 Pod 的标签app: proxyhttps # 标签键值对,标识该 Pod 属于 proxyhttps 应用spec: # 定义 Pod 的规格containers: # 定义 Pod 中的容器- image: wangyanglinux/tools:httpsv1 # 使用的容器镜像为 wangyanglinux/tools:httpsv1name: myapp # 容器的名称为 myapp---
# Service 部分
apiVersion: v1 # 指定 Kubernetes API 版本为 v1
kind: Service # 定义资源类型为 Service
metadata: # 定义 Service 的元数据labels: # 定义 Service 的标签app: proxyhttps # 标签键值对,标识该 Service 属于 proxyhttps 应用name: proxyhttps-svc # Service 的名称为 proxyhttps-svc
spec: # 定义 Service 的规格ports: # 定义 Service 暴露的端口- name: 443-443 # 端口的名称为 443-443port: 443 # Service 暴露的端口为 443protocol: TCP # 使用的协议为 TCPtargetPort: 443 # 将流量转发到 Pod 的 443 端口selector: # 定义 Service 如何选择后端 Podapp: proxyhttps # 选择标签为 app: proxyhttps 的 Podtype: ClusterIP # Service 的类型为 ClusterIP,仅集群内部可访问
验证下nginx服务器的9000端口, 因为是四层负载,不需要访问域名,直接访问ip地址即可
我们打开浏览器输入IP地址和端口:
ingress-nginx%C2%A0%20%E5%9F%BA%E4%BA%8EUDP%E5%9B%9B%E5%B1%82%E4%BB%A3%E7%90%86" name="13%E3%80%81%E5%AE%9E%E9%AA%8C13%E2%80%94ingress-nginx%C2%A0%20%E5%9F%BA%E4%BA%8EUDP%E5%9B%9B%E5%B1%82%E4%BB%A3%E7%90%86">13、实验13—ingress-nginx 基于UDP四层代理
kubectl edit ds -n ingress ingress-nginx-controllerspec:containers:- args:- /ingress>nginx-ingress-controller- --udp-services-configmap=$(POD_NAMESPACE)/ingress>nginx-ingress-udp-configmapapiVersion: v1
kind: ConfigMap
metadata:name: ingress>nginx-ingress-udp-configmapnamespace: ingress
data:"53": "kube-system/kube-dns:53"
ingress-nginx%C2%A0%20%E9%93%BE%E8%B7%AF%E8%BF%BD%E8%B8%AA" name="14%E3%80%81%E5%AE%9E%E9%AA%8C14%E2%80%94ingress-nginx%C2%A0%20%E9%93%BE%E8%B7%AF%E8%BF%BD%E8%B8%AA">14、实验14—ingress-nginx 链路追踪
链路追踪需要用插件,官方给了推荐:Zipkin和Jaeger。实验用的是Jaeger。
(1)下载Jaeger官方部署文件,并部署Jaeger。
wget https://raw.githubusercontent.com/jaegertracing/jaeger-kubernetes/master/all-in-one/jaeger-all-in-one-template.yml
部署过程中遇到错误,就按照错误进行修改。
(2)修改ingress-nginx-controller控制器的configmap文件内容
开启链路追踪,配置追踪的Jaeger的svc名称。
重启ingress-nginx-controller控制器,使配置生效。