【云原生】Kubernetes----Ingress对外服务

news2025/3/18 10:14:45

目录

引言

一、K8S对外方式

(一)NodePort

1.作用

2.弊端

3.示例

(二)externalIPs

1.作用

2.弊端

3.示例

(三)LoadBalancer

1.作用

2.弊端

(四)Ingress

二、Ingress的基本概念

(一)基本概念

(二)Ingress组成

1.ingress

2.ingress-controller

3.关系归纳

(三)Ingress的工作原理

(四)访问流程

三、配置Ingress规则

(一)ingress暴露服务方式

(二)方式二搭建

1.获取资源

1.1 获取配置文件

1.2 获取镜像资源

2.修改ClusterRole资源配置

3.修改nginx-ingress-controller配置

4.创建资源

4.1 创建ingress-controller

4.2 创建pod与service

5.创建ingress规则

6.客户端访问

(三)方式三搭建

1.清空环境

2.获取文件

3.创建代理资源

3.1 创建nginx-ingress-controller资源

3.2 创建service资源

4.创建访问资源

4.1 创建Deployment

4.2 创建service

4.3 创建Ingress规则

5.使用客户端进行访问

四、虚拟主机

(一)创建pod资源

(二)创建service资源

(三)创建ingress规则

(四)客户端访问

五、HTPPS代理

(一)获取SSL证书

(二)创建Kubernetes Secret

(三)创建pod资源

(四)创建service

(五)创建ingress规则

(六)客户端访问

六、实现BasicAuth

(一)创建认证文件

1.下载htpasswd工具

2.创建认证文件

(二)创建Secret

(三)创建pod资源

(四)创建service

(五)创建ingress资源

七、Nginx重写


引言

随着Kubernetes在云原生应用领域的广泛应用,如何高效地管理集群的外部流量成为了许多开发者和管理员面临的挑战。在Kubernetes中,Ingress提供了一个标准化的方式来管理外部流量到集群内部服务的路由,从而简化了流量管理的复杂性。本文将介绍Ingress的基本概念、工作原理以及如何使用Ingress来优化你的Kubernetes集群的流量路由

一、K8S对外方式

在Kubernetes(k8s)中,使外部应用能够访问集群内的服务主要有四种方式

(一)NodePort

1.作用

NodePort服务类型将服务暴露在每个Kubernetes节点的相同端口上。外部用户可以通过访问任何节点的IP地址和该端口来访问服务。

2.弊端

NodePort背后就是Kube-Proxy,Kube-Proxy是沟通service网络、Pod网络和节点网络的桥梁。
测试环境使用还行,当有几十上百的服务在集群中运行时,NodePort的端口管理就是个灾难。因为每个端口只能是一种服务,端口范围只能是 30000-32767

3.示例

[root@master01 pod]#vim deployment.yaml 
[root@master01 pod]#cat deployment.yaml 
apiVersion: apps/v1
kind: Pod
metadata:
  name: nginx-pod
  labels:
    app: nginx  
spec:
  containers:
  - name: nginx
    image: nginx:1.18.0
    ports:
    - containerPort: 80
---
apiVersion: v1
kind: Service             #创建service
metadata:
  name: nginx-svc
  labels:
    app: nginx
spec:
  type: NodePort          #type类型为NodePort,用于对外提供服务
  ports:
  - port: 80
    targetPort: 80 
  selector:
    app: nginx

执行完yaml文件之后,查看地址与映射端口

[root@master01 pod]#kubectl apply -f pod.yaml 
pod/nginx-pod created
service/nginx-svc created
[root@master01 pod]#
[root@master01 pod]#kubectl get pod -owide
NAME        READY   STATUS    RESTARTS   AGE   IP           NODE     NOMINATED NODE   READINESS GATES
nginx-pod   1/1     Running   0          14s   10.244.2.3   node02   <none>           <none>
[root@master01 pod]#kubectl get svc
NAME         TYPE        CLUSTER-IP      EXTERNAL-IP   PORT(S)        AGE
kubernetes   ClusterIP   10.96.0.1       <none>        443/TCP        17d
nginx-svc    NodePort    10.96.131.227   <none>        80:30425/TCP   31s
#使用客户端访问任意节点的30425端口


使用客户端进行访问

[root@nfs ~]#curl 192.168.83.30:30425  -I
HTTP/1.1 200 OK
Server: nginx/1.18.0
Date: Mon, 03 Jun 2024 06:55:53 GMT
Content-Type: text/html
Content-Length: 612
Last-Modified: Tue, 21 Apr 2020 14:09:01 GMT
Connection: keep-alive
ETag: "5e9efe7d-264"
Accept-Ranges: bytes

(二)externalIPs

1.作用

Kubernetes中的externalIPs允许将一个或多个外部IP地址直接绑定到一个Kubernetes服务上,从而可以通过这些外部IP地址直接访问该服务

2.弊端

当使用externalIPs时,外部流量将直接通过指定的IP地址进入集群,这可能增加了集群的安全风险。攻击者可能会利用这些外部IP地址对集群进行攻击,如拒绝服务攻击(DoS)、中间人攻击(MITM)等。不支持负载均衡和故障转移

3.示例

[root@master01 pod]#cat pod02.yaml 
apiVersion: v1
kind: Pod
metadata:
  name: nginx-pod02
  labels:
    app: nginx  
spec:
  nodeName: node02        
#pod需要使用节点亲和,指定pod建立在externalIPs指定nodeIP地址之外
#同样IP可能导致网络数据包的路由变得混乱,使得Kubernetes集群内外的网络无法正确区分和处理流量
#如果使用deployment建立的pod,则externalIPs只会非本节点的pod实例
  containers:
  - name: nginx
    image: nginx:1.18.0
    ports:
    - containerPort: 80
---
apiVersion: v1
kind: Service
metadata:
  name: nginx-svc02
  labels:
    app: nginx
spec: 
  externalIPs:          #指定pod绑定地址
  - 192.168.83.40       #绑定到node01节点的IP上
  ports:
  - port: 80
    targetPort: 80 
  selector:
    app: nginx

创建后,查看服务

[root@master01 pod]#kubectl apply -f pod02.yaml 
pod/nginx-pod02 created
service/nginx-svc02 created
[root@master01 pod]#kubectl get pod nginx-pod02
[root@master01 pod]#kubectl get pod nginx-pod02 -owide
NAME          READY   STATUS    RESTARTS   AGE     IP          NODE     NOMINATED NODE   READINESS GATES
nginx-pod02   1/1     Running   0          5s   10.244.2.4     node02   <none>           <none>
[root@master01 pod]#kubectl get svc nginx-svc02 
NAME          TYPE        CLUSTER-IP     EXTERNAL-IP     PORT(S)   AGE
nginx-svc02   ClusterIP   10.96.42.161   192.168.83.40   80/TCP    14s

客户端直接访问节点即可

[root@nfs ~]#curl 192.168.83.40  -I
HTTP/1.1 200 OK
Server: nginx/1.18.0
Date: Mon, 03 Jun 2024 07:08:42 GMT
Content-Type: text/html
Content-Length: 612
Last-Modified: Tue, 21 Apr 2020 14:09:01 GMT
Connection: keep-alive
ETag: "5e9efe7d-264"
Accept-Ranges: bytes

(三)LoadBalancer

1.作用

LoadBalancer服务类型允许外部负载均衡器将流量路由到Kubernetes集群中的服务。

这种方式通常用于云服务提供商(如AWS、Azure、GCP等),它们可以自动创建一个负载均衡器并为其分配一个外部IP地址。

2.弊端

这种用法仅用于在公有云服务提供商的云平台上设置 Service 的场景。受限于云平台,且通常在云平台部署LoadBalancer还需要额外的费用

(四)Ingress

  • Ingress是Kubernetes中的一个API对象,它管理外部访问到集群内服务的HTTP和HTTPS路由规则。
  • 通常与Ingress Controller一起使用,Ingress Controller是一个反向代理服务器,负责实现Ingress定义的路由规则。
  • Ingress可以基于域名、路径或其他HTTP请求属性进行流量路由。
  • 配置Ingress需要创建Ingress对象并定义路由规则,同时还需要部署Ingress Controller。
  • Ingress提供了比LoadBalancer更高级的路由和流量管理功能。

二、Ingress的基本概念

(一)基本概念

在Kubernetes中,Ingress是一个API对象,它用于定义集群外部访问内部服务的规则。通过Ingress,可以配置基于主机名、路径等条件的路由规则,将外部流量转发到集群内的一个或者多个service。Ingress提供了一种统一的、声明式的方式来管理外部流量,使得流量路由更加灵活和可配置。

Ingress资源本身不会进行任何网络流量的路由,它依赖于Ingress控制器(如Nginx Ingress Controller、HAProxy Ingress Controller、Traefik等)来根据Ingress资源中定义的规则进行实际的路由

(二)Ingress组成

1.ingress

  • 定义:Ingress是一个Kubernetes API对象,通常使用YAML文件进行配置。它主要的作用是定义请求如何转发到集群内部服务的规则。
  • 功能:Ingress提供了负载均衡、SSL和基于名称的虚拟托管。通过Ingress,可以定义服务外部可访问的URL、负载均衡流量、SSL/TLS配置,以及基于名称的虚拟主机。
  • 特点:Ingress可以被视为一种配置模板,用于描述外部访问集群内部服务的方式。它定义了集群外部流量如何进入集群内各个服务的路由规则,但它本身无法直接实现这些路由。

2.ingress-controller

  • 定义:Ingress Controller是具体实现Ingress规则的程序。它与Kubernetes API交互,动态地感知集群中Ingress规则的变化,并按照这些规则生成相应的配置文件(例如Nginx的配置文件)。
  • 功能:Ingress Controller负责处理实际的流量转发工作,确保外部请求能够正确地路由到集群内部的Service。它实现了反向代理及负载均衡的功能,确保外部请求能够高效地路由到集群内部的服务。
  • 特点:Ingress Controller监听Ingress资源对象的变更,并根据Ingress规则进行配置。通常,Ingress Controller通过负载均衡器(如Nginx、Traefik等)来实现其功能。

ingress-controller并不是k8s自带的组件,实际上ingress-controller只是一个统称,用户可以选择不同的ingress-controller实现

目前,由k8s维护的ingress-controller只有google云的GCE与ingress-nginx两个,其他还有很多第三方维护的ingress-controller,具体可以参考官方文档。

但是不管哪一种ingress-controller,实现的机制都大同小异,只是在具体配置上有差异。

一般来说,ingress-controller的形式都是一个pod,里面跑着daemon程序和反向代理程序。daemon负责不断监控集群的变化,根据 ingress对象生成配置并应用新配置到反向代理

比如ingress-nginx就是动态生成nginx配置,动态更新upstream,并在需要的时候reload程序应用新配置。为了方便,后面的例子都以k8s官方维护的ingress-nginx为例。

3.关系归纳

  • Ingress定义了请求转发的规则,这些规则描述了外部流量如何进入集群内的各个服务。
  • Ingress Controller负责实现这些规则,并与Kubernetes API交互,动态地感知并应用Ingress规则的变化。
  • 要使Ingress资源生效,集群中必须有一个正在运行的Ingress Controller来读取这些规则并相应地进行流量转发。

总结:ingress-controller才是负责具体转发的组件,通过各种方式将它暴露在集群入口,外部对集群的请求流量会先到 ingress-controller, 而ingress对象是用来告诉ingress-controller该如何转发请求,比如哪些域名、哪些URL要转发到哪些service等等

(三)Ingress的工作原理

Ingress的工作原理可以简单概括为以下几个步骤

监听Ingress对象:Ingress Controller通过Kubernetes API服务器监听Ingress对象的变化。当新的Ingress对象被创建、更新或删除时,Ingress Controller能够感知到这些变化。

解析Ingress规则:Ingress Controller解析Ingress对象中定义的规则。这些规则包括主机名、路径、后端服务等信息,用于确定如何将流量路由到集群内的不同服务。

生成配置:Ingress Controller将解析后的规则转化为特定负载均衡器(如Nginx、HAProxy等)可以理解的配置。这些配置通常包括反向代理设置、负载均衡策略、SSL/TLS配置等。再写到nginx-ingress-controller的pod里,这个ingress-controller的pod里运行着一个Nginx服务,控制器会把生成的 nginx配置写入 /etc/nginx.conf文件中

动态更新:Ingress Controller能够实时响应Ingress对象的变化,并动态更新其配置。这意味着当Ingress规则发生变化时,无需重启Ingress Controller或整个集群,流量路由将自动更新以适应新的规则。

(四)访问流程

1.客户端访问域名,通过DNS解析到Ingress-confoller所在的节点

2.同时客户端向Ingress-confoller所在的节点发送HTTP/HTTPS请求

3.Ingress-confoller通过Ingress的配置信息(URL、域名等),确定将请求转发到哪一个service,而后根据service关联的pod地址,决定Ingress-confoller将请求转发到pod当中。

三、配置Ingress规则

(一)ingress暴露服务方式

ingress 暴露服务的方式有以下三种

方式一:Deployment+LoadBalancer 模式的 Service

这是公有云环境中非常常见的方式。在Kubernetes集群中,可以使用Deployment来部署Ingress Controller的Pod,并创建一个类型为LoadBalancer的Service来将Pod暴露到外部。在公有云环境中,当创建LoadBalancer类型的Service时,云提供商通常会为你自动创建一个负载均衡器(例如AWS的ELB,Azure的LB等),并且通常还会为你分配一个公网IP地址。你只需要将你的域名解析到这个公网IP地址,就可以通过Ingress来访问你的服务了

优点

  1. 自动化与便捷性:在公有云环境中,创建LoadBalancer类型的Service会自动为你创建负载均衡器,并分配公网IP,简化了配置过程。
  2. 高可用性:负载均衡器通常具有容错和故障转移的能力,保证服务的稳定性。
  3. 易于扩展:可以根据需求动态调整LoadBalancer的配置,如增加后端节点等。

缺点

  1. 成本:在公有云环境中,使用LoadBalancer通常需要支付额外的费用。
  2. 环境限制:这种方式主要适用于公有云环境,对于自建Kubernetes集群或者私有云环境可能不适用

方式二:DaemonSet+HostNetwork+nodeSelector

这种方式下,Ingress Controller以DaemonSet的方式部署,通过nodeSelector选择特定的节点运行。同时,使用HostNetwork将Ingress Controller的Pod与宿主机的网络打通,直接使用宿主机的80/443端口来提供服务。这样,Ingress Controller所在的节点就起到了边缘节点的作用,可以直接接受外部请求,并将请求转发到集群内的服务。这种方式的优点是请求链路简单,性能较好。但是,由于Ingress Controller直接占用了宿主机的端口,所以一个节点上通常只能运行一个Ingress Controller的Pod。

优点

  1. 性能优越:由于直接使用宿主机的网络和端口,请求链路简单,性能较好。
  2. 配置简单:通过DaemonSet和nodeSelector可以很方便地将Ingress Controller部署到指定的节点上。
  3. 适合大并发环境:对于需要处理大量并发请求的生产环境,这种方式具有更好的性能表现。

缺点

  1. 资源限制:由于Ingress Controller直接占用了宿主机的端口,因此一个节点上通常只能运行一个Ingress Controller的Pod。
  2. 安全性:由于Ingress Controller直接暴露在公网上,需要特别注意安全性问题,如防止DDoS攻击等。
  3. 可移植性差:使用HostNetwork和特定节点的方式使得Ingress Controller的部署与特定环境紧密相关,不利于跨环境部署和迁移。

方式三:Deployment+NodePort模式的Service

在这种方式下,Ingress Controller仍然以Deployment的方式部署,但是关联的Service的类型是NodePort。NodePort类型的Service会将Pod的端口映射到集群中每个节点的特定端口上。然后,你可以通过任意节点的IP地址和该节点上的映射端口来访问Ingress Controller。由于NodePort映射的端口是随机选择的,因此通常还需要在集群外部再部署一个负载均衡器来将流量分发到各个节点上。这种方式适用于节点IP地址相对固定的环境,但需要注意的是,由于NodePort类型的Service在节点之间进行了NAT转发,因此在请求量很大时可能会对性能产生一定的影响。

优点

  1. 灵活性:NodePort类型的Service可以灵活地将Pod的端口映射到集群中每个节点的特定端口上,便于外部访问。
  2. 适用于固定IP环境:在节点IP地址相对固定的环境中,这种方式可以很方便地暴露服务。

缺点

  1. 性能损耗:由于NodePort类型的Service在节点之间进行了NAT转发,因此在请求量很大时可能会对性能产生一定的影响。
  2. 需要额外配置:通常需要在集群外部再部署一个负载均衡器来将流量分发到各个节点上,增加了配置的复杂性。
  3. 端口管理:由于NodePort映射的端口是随机选择的,可能会与现有应用或服务产生冲突,需要进行端口管理。

(二)方式二搭建

DaemonSet+HostNetwork+nodeSelector

1.获取资源

1.1 获取配置文件

官方下载地址
https://raw.githubusercontent.com/kubernetes/ingress-nginx/nginx-0.30.0/deploy/static/mandatory.yaml

官方无法下载的话,可用国内的 gitee

https://gitee.com/mirrors/ingress-nginx/raw/nginx-0.30.0/deploy/static/mandatory.yaml

[root@master01 ingress]#wget https://gitee.com/mirrors/ingress-nginx/raw/nginx-0.30.0/deploy/static/mandatory.yaml
--2024-06-03 16:40:40--  https://gitee.com/mirrors/ingress-nginx/raw/nginx-0.30.0/deploy/static/mandatory.yaml
正在解析主机 gitee.com (gitee.com)... 180.76.198.77
正在连接 gitee.com (gitee.com)|180.76.198.77|:443... 已连接。
已发出 HTTP 请求,正在等待回应... 200 OK
长度:6635 (6.5K) [text/plain]
正在保存至: “mandatory.yaml”

100%[============================================================================>] 6,635       --.-K/s 用时 0s      

2024-06-03 16:40:41 (735 MB/s) - 已保存 “mandatory.yaml” [6635/6635])
[root@master01 ingress]#ls
mandatory.yaml
[root@master01 ingress]#wc -l mandatory.yaml 
293 mandatory.yaml
1.2 获取镜像资源

事先准备好镜像,防止执行yaml文件过程中下载镜像失败,导致无法进入工作状态

//在node01节点上下载
[root@node01 ~]#docker pull quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.30.0
0.30.0: Pulling from kubernetes-ingress-controller/nginx-ingress-controller
......


//在node02节点上下载
[root@node02 ~]#docker pull quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.30.0
0.30.0: Pulling from kubernetes-ingress-controller/nginx-ingress-controller
......

2.修改ClusterRole资源配置

[root@master01 ingress]#vim mandatory.yaml
......
 91   - apiGroups:
 92       - "extensions"
 93       - "networking.k8s.io"    #0.25版本以前,需要添加此段
 94     resources:
 95       - ingresses
 96     verbs:
 97       - get
 98       - list
 99       - watch
100   - apiGroups:
101       - "extensions"
102       - "networking.k8s.io"     #0.25版本以前,需要添加此段
103     resources:
104       - ingresses/status
105     verbs:
106       - update
......
---------------------------------------------------------------   
ClusterRole的规则部分,用于定义哪些API资源可以被特定的用户或用户组访问,以及可以进行哪些操作
91-99行:定义第一个规则组:
apiGroups: 定义了资源所属的API组。这里指定了两个API组:"extensions" 和 "networking.k8s.io"
resources: 定义具体的资源类型,允许对Ingress资源(用于HTTP/HTTPS路由)进行操作
verbs:定义了可以对资源进行的操作。get(获取资源信息)、list(列出所有资源)和watch(监视资源变化)

100-106行:定义第二个规则组
ingresses/status:允许对Ingress资源的状态进行操作
verbs: update,允许更新

在Kubernetes1.18及以后的版本中,extensions/v1beta1 Ingress已经被废弃,并在Kubernetes 1.22版本中完全移除。
Kubernetes集群版本是1.18或更高,使用networking.k8s.io/v1 API组,并且通常不需要在Role或ClusterRole中包含extensions API组

3.修改nginx-ingress-controller配置

指定 nginx-ingress-controller 运行在 node02 节点

①添加node02节点标签

[root@master01 ingress]#kubectl label nodes node02 china=zg
node/node02 labeled
#添加标签
[root@master01 ingress]#kubectl get nodes node02 --show-labels   #查看标签
NAME     STATUS   ROLES    AGE   VERSION    LABELS
node02   Ready    <none>   18d   v1.20.11   beta.kubernetes.io/arch=amd64,beta.kubernetes.io/os=linux,china=zg,kubernetes.io/arch=amd64,kubernetes.io/hostname=node02,kubernetes.io/os=linux

②修改 Deployment 为 DaemonSet ,指定节点运行,并开启 hostNetwork 网络

[root@master01 ingress]#vim mandatory.yaml
......
190 apiVersion: apps/v1
191 kind: DaemonSet                                
#修改资源类型为DaemonSet,需要在每个指定的节点上运行ingress-controller,标签选择时可以选择多个节点
192 metadata:
193   name: nginx-ingress-controller
194   namespace: ingress-nginx
195   labels:
196     app.kubernetes.io/name: ingress-nginx
197     app.kubernetes.io/part-of: ingress-nginx
198 spec:
199 #  replicas: 1      #注释或删除replicas
200   selector:
201     matchLabels:
.......
204   template:
......
212     spec:
213       # wait up to five minutes for the drain of connections
214       #terminationGracePeriodSeconds: 300    
#定义pod被强制杀死之前应该等待多长时间来优雅地关闭。此处不需要,注释掉
215       hostNetwork: true   #开启HostNetwork,使Pod与宿主机之前的网络建立隧道
216       serviceAccountName: nginx-ingress-serviceaccount
217       nodeSelector:
218         china: zg           #更换指定节点标签
219       containers:
220         - name: nginx-ingress-controller
221           image: quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.30.0
......

4.创建资源

4.1 创建ingress-controller
[root@master01 ingress]#kubectl apply -f mandatory.yaml 
namespace/ingress-nginx created
configmap/nginx-configuration created
configmap/tcp-services created
configmap/udp-services created
........
[root@master01 ingress]#kubectl get pod -n ingress-nginx -owide
NAME                             READY   STATUS    RESTARTS   AGE    IP              NODE     NOMINATED NODE   READINESS GATES
nginx-ingress-controller-2n7f6   1/1     Running   0          144m   192.168.83.50   node02   <none>           <none>

在node02节点过滤80端口

[root@node02 ~]#netstat -antulp |grep :80
tcp      0    0 0.0.0.0:80      0.0.0.0:*      LISTEN     62842/nginx: master 
tcp6     0    0 :::80           :::*           LISTEN     62842/nginx: master
-------------------------------------------------------------------------------
虽然80端口已经开启,但是使用客户端进行访问会出现404报错,因为它只是ingress-nginx在监听宿主机的80端口,本身不提供web服务


[root@node02 ~]#netstat -lntp | grep nginx
tcp    0    0 0.0.0.0:80            0.0.0.0:*       LISTEN    62842/nginx: master 
tcp    0    0 0.0.0.0:8181          0.0.0.0:*       LISTEN    62842/nginx: master 
tcp    0    0 0.0.0.0:443           0.0.0.0:*       LISTEN    62842/nginx: master 
tcp    0    0 127.0.0.1:10245       0.0.0.0:*       LISTEN    62787/nginx-ingress 
tcp    0    0 127.0.0.1:10246       0.0.0.0:*       LISTEN    62842/nginx: master 
tcp    0    0 127.0.0.1:10247       0.0.0.0:*       LISTEN    62842/nginx: master 
tcp6   0    0 :::10254              :::*            LISTEN    62787/nginx-ingress 
tcp6   0    0 :::80                 :::*            LISTEN    62842/nginx: master 
tcp6   0    0 :::8181               :::*            LISTEN    62842/nginx: master 
tcp6   0    0 :::443                :::*            LISTEN    62842/nginx: master
-----------------------------------------------------------------------------------
由于配置了hostnetwork,nginx已经在node主机本地监听80/443/8181端口。
其中8181是nginx-controller 默认配置的一个default backend(Ingress 资源没有匹配的 rule 对象时,流量就会被导向这个 default backend)。
这样,只要访问node主机有公网IP,就可以直接映射域名来对外网暴露服务了。
如果要nginx高可用的话,可以在多个node上部署,并在前面再搭建一套LVS+keepalived做负载均衡
4.2 创建pod与service

此时需要在node02节点上创建一个pod

[root@master01 ingress]#vim pod.yaml 
[root@master01 ingress]#cat pod.yaml 
apiVersion: v1
kind: Pod
metadata:
  name: nginx01-ingress
  labels:
    run: nginx-run
spec:
  nodeName: node02
  containers:
  - name: nginx
    image: nginx:1.20.2
    ports:
    - containerPort: 80
---
apiVersion: v1
kind: Service
metadata:
  name: in-ng-svc
spec:
  type: NodePort
  ports:
  - port: 80
    targetPort: 80
  selector:
    run: nginx-run

创建完毕后,此时四层的服务已经设置完毕

[root@master01 ingress]#kubectl apply -f pod.yaml 
pod/nginx01-ingress created
service/in-ng-svc created
[root@master01 ingress]#kubectl get pod,svc -owide
NAME                  READY   STATUS    RESTARTS   AGE   IP           NODE     NOMINATED NODE   READINESS GATES
pod/nginx01-ingress   1/1     Running   0          12s   10.244.2.6   node02   <none>           <none>

NAME                 TYPE        CLUSTER-IP   EXTERNAL-IP   PORT(S)        AGE   SELECTOR
service/in-ng-svc    NodePort    10.96.9.79   <none>        80:32169/TCP   12s   run=nginx-run
service/kubernetes   ClusterIP   10.96.0.1    <none>        443/TCP        18d   <none>
[root@master01 ingress]#curl 10.96.9.79 -I
HTTP/1.1 200 OK
Server: nginx/1.20.2
Date: Mon, 03 Jun 2024 12:54:15 GMT
Content-Type: text/html
Content-Length: 612
Last-Modified: Tue, 16 Nov 2021 14:44:02 GMT
Connection: keep-alive
ETag: "6193c3b2-264"
Accept-Ranges: bytes
[root@master01 ingress]#kubectl exec -it nginx01-ingress bash
root@nginx01-ingress:/# echo "this is ingress-nginx" >/usr/share/nginx/html/index.html 
#自定义访问界面
root@nginx01-ingress:/# exit
exit
[root@master01 ingress]#curl 10.96.9.79
this is ingress-nginx
#自定义一个访问界面 

5.创建ingress规则

[root@master01 ingress]#vim ingress.yaml
[root@master01 ingress]#cat ingress.yaml
apiVersion: networking.k8s.io/v1     #Kubernetes网络扩展API的版本1,它定义了Ingress资源。
kind: Ingress                        #定义了资源的类型
metadata:
  name: nginx-ingress
spec:
  rules:                             #定义Ingress规则,将HTTP/HTTPS请求路由到集群内的服务
  - host: www.ingress.com            #指定规则适用的主机名
    http:                            #定义了 HTTP 相关的配置。
      paths:                         #定义了 HTTP 请求的路径和它们应该被路由到的后端服务
      - path: /                      #指定了匹配的路径,这里使用了/,表示匹配所有路径
        pathType: Prefix             #定义了路径匹配的类型。Prefix表示路径是基于前缀的匹配
        backend:                     #定义了当请求匹配上述路径时应该被路由到的后端服务
          service:                   #定义了后端服务的配置,即指定转发带哪一个service
            name: in-ng-svc          #后端服务的名称,即service的名称
            port:                    #定义了后端服务的端口配置
              number: 80             #指定后端服务的端口号
---------------------------------------------------------------------------------
'host: www.ingress.com'
#当请求的Host头部为www.ingress.com时,这个规则会被应用。

'pathType类型'
#Exact
精确匹配。只有当请求的路径与定义的路径完全相同时才进行路由。
如果path定义为/exact-path,并且pathType设置为 Exact
那么只有当请求的URL路径也是/exact-path 时,该请求才会被路由到对应的后端服务。
类似于nginx配置文件中的location = /path

#Prefix
前缀匹配。如果请求的路径以定义的路径为前缀,则进行路由。
类似于nginx配置文件中的location ^~ /path

#ImplementationSpecific
实现特定匹配。此选项告诉Ingress控制器使用其实现特定的方式进行路径选择,这通常是默认值。
由于这是依赖于Ingress 控制器的实现方式,所以并没有统一的匹配规则。
不同的Ingress控制器可能会有不同的行为。
如果没有在Ingress资源中明确指定pathType,那么可能会默认使用ImplementationSpecific
使用ImplementationSpecific路径类型时,需要确保了解所使用Ingress控制器的具体实现和配置要求
由于ImplementationSpecific的行为可能因控制器而异,因此在切换控制器或更新控制器版本时,
需要仔细测试和验证路径匹配的行为是否仍然符合预期

创建规则

[root@master01 ingress]#kubectl apply -f ingress.yaml 
ingress.networking.k8s.io/nginx-ingress created
[root@master01 ingress]#kubectl get ingress
NAME            CLASS    HOSTS             ADDRESS   PORTS   AGE
nginx-ingress   <none>   www.ingress.com             80      27s

进入ingress规则进行查看

[root@master01 ingress]#kubectl exec -it nginx-ingress-controller-2n7f6 -n ingress-nginx bash
bash-5.0$ egrep -e 'server_name' -e 'start server' -e 'end server' /etc/nginx/nginx.conf 
	server_names_hash_max_size      1024;
	server_names_hash_bucket_size   64;
	# Reverse proxies can detect if a client provides a X-Request-ID header, and pass it on to the backend server.
	server_name_in_redirect off;
	## start server _
		server_name _ ;
	## end server _
	## start server www.ingress.com
		server_name www.ingress.com;
	## end server www.ingress.com;
#自动添加域名信息
#从start server www.ingress.com到end server www.ingress.com之间包含此域名用于反向代理的配置

6.客户端访问

[root@nfs ~]#vim /etc/hosts
[root@nfs ~]#grep '192.168.83.50' /etc/hosts
192.168.83.50 node02 www.ingress.com
#添加客户端域名解析信息,使用域名进行访问,触发ingress规则
[root@nfs ~]#curl www.ingress.com
this is ingress-nginx
#自定义的web访问界面

(三)方式三搭建

Deployment+NodePort模式的Service

1.清空环境

清空之前的操作信息防止pod运行冲突

[root@master01 ingress]#kubectl delete -f pod.yaml 
pod "nginx01-ingress" deleted
service "in-ng-svc" deleted
[root@master01 ingress]#kubectl delete -f ingress.yaml 
ingress.networking.k8s.io "nginx-ingress" deleted
[root@master01 ingress]#kubectl delete -f mandatory.yaml 

2.获取文件

下载 nginx-ingress-controller 和 ingress-nginx 暴露端口配置文件,

官方下载地址

https://raw.githubusercontent.com/kubernetes/ingress-nginx/nginx-0.30.0/deploy/static/provider/baremetal/service-nodeport.yaml

国内 gitee 资源地址 

https://gitee.com/mirrors/ingress-nginx/raw/nginx-0.30.0/deploy/static/mandatory.yaml

https://gitee.com/mirrors/ingress-nginx/raw/nginx-0.30.0/deploy/static/provider/baremetal/service-nodeport.yaml

[root@master01 data]#mkdir in-nodeport
[root@master01 data]#cd in-nodeport/
[root@master01 in-nodeport]#wget https://gitee.com/mirrors/ingress-nginx/raw/nginx-0.30.0/deploy/static/provider/baremetal/service-nodeport.yaml
[root@master01 in-nodeport]#wget https://gitee.com/mirrors/ingress-nginx/raw/nginx-0.30.0/deploy/static/mandatory.yaml
[root@master01 in-nodeport]#ls
mandatory.yaml  service-nodeport.yaml

3.创建代理资源

3.1 创建nginx-ingress-controller资源
[root@master01 in-nodeport]#vim mandatory.yaml

[root@master01 in-nodeport]#kubectl apply -f mandatory.yaml 
#创建nginx-ingress-controller资源
#以pod的形式在ingress-nginx命名空间运行
[root@master01 in-nodeport]#kubectl get pod -owide -n ingress-nginx 
NAME                                        READY   STATUS    RESTARTS   AGE    IP             NODE     NOMINATED NODE   READINESS GATES
nginx-ingress-controller-54b86f8f7b-vj8rl   1/1     Running   0          153m   10.244.1.214   node01   <none>           <none>
3.2 创建service资源

查看service-nodeport.yaml 文件,都是默认内容,直接创建即可

[root@master01 in-nodeport]#cat service-nodeport.yaml 
apiVersion: v1
kind: Service
metadata:
  name: ingress-nginx
  namespace: ingress-nginx      #所在命名空间,需要先执行mandatory.yaml文件创建
  labels:
    app.kubernetes.io/name: ingress-nginx
    app.kubernetes.io/part-of: ingress-nginx
spec:
  type: NodePort
  ports:
    - name: http
      port: 80
      targetPort: 80
      protocol: TCP
    - name: https
      port: 443
      targetPort: 443
      protocol: TCP
  selector:
    app.kubernetes.io/name: ingress-nginx         
    app.kubernetes.io/part-of: ingress-nginx
#此标签是nginx-ingress-controller的标签,该service绑定该标签,
#将nginx-ingress-controller以NodePort的形式暴露出去
---

创建service资源

[root@master01 in-nodeport]#kubectl apply -f service-nodeport.yaml
[root@master01 in-nodeport]#kubectl get svc -n ingress-nginx 
NAME                    TYPE       CLUSTER-IP    EXTERNAL-IP   PORT(S)                      AGE
service/ingress-nginx   NodePort   10.96.43.71   <none>        80:31705/TCP,443:32391/TCP   31s
[root@master01 in-nodeport]#kubectl describe svc -n ingress-nginx 
Name:                     ingress-nginx
Namespace:                ingress-nginx
Labels:                   app.kubernetes.io/name=ingress-nginx
                          app.kubernetes.io/part-of=ingress-nginx
Annotations:              <none>
Selector:                 app.kubernetes.io/name=ingress-nginx,app.kubernetes.io/part-of=ingress-nginx
Type:                     NodePort
IP Families:              <none>
IP:                       10.96.43.71
IPs:                      10.96.43.71
Port:                     http  80/TCP
TargetPort:               80/TCP
NodePort:                 http  31705/TCP
Endpoints:                10.244.1.214:80
Port:                     https  443/TCP
TargetPort:               443/TCP
NodePort:                 https  32391/TCP
Endpoints:                10.244.1.214:443   #后端关联地址为nginx-ingress-controller地址
Session Affinity:         None
External Traffic Policy:  Cluster
Events:                   <none>

4.创建访问资源

4.1 创建Deployment
[root@master01 in-nodeport]#vim deployment.yaml 
[root@master01 in-nodeport]#cat deployment.yaml 
apiVersion: apps/v1
kind: Deployment
metadata:
  name: nginx01-ingress
  labels:
    nginx-label: nginx01
spec:
  replicas: 2
  selector:
    matchLabels:
     nginx-label: nginx01
  template:
    metadata:
      labels:
        nginx-label: nginx01
    spec:
      containers:
      - name: nginx
        image: nginx:1.18.0
        ports:
        - containerPort: 80
[root@master01 in-nodeport]#kubectl apply -f deployment.yaml 
deployment.apps/nginx01-ingress created
[root@master01 in-nodeport]#kubectl get pod -owide
NAME                               READY   STATUS    RESTARTS   AGE   IP             NODE     NOMINATED NODE   READINESS GATES
nginx01-ingress-5d89744488-g7v6w   1/1     Running   0          8s    10.244.2.7     node02   <none>           <none>
nginx01-ingress-5d89744488-x66jh   1/1     Running   0          8s    10.244.1.215   node01   <none>           <none>
------------------------------------------------------------------------------------
#自定义web访问界面
[root@master01 in-nodeport]#kubectl exec -it nginx01-ingress-5d89744488-g7v6w bash
root@nginx01-ingress-5d89744488-g7v6w/~# echo "this is web01" >/usr/share/nginx/html/index.html 
root@nginx01-ingress-5d89744488-g7v6w/~# exit
exit
[root@master01 in-nodeport]#kubectl exec -it nginx01-ingress-5d89744488-x66jh bash
root@nginx01-ingress-5d89744488-x66jh:/# echo "this is web02" >/usr/share/nginx/html/index.html
root@nginx01-ingress-5d89744488-x66jh:/# exit
exit
4.2 创建service
[root@master01 in-nodeport]#vim service.yaml 
[root@master01 in-nodeport]#cat service.yaml 
apiVersion: v1
kind: Service
metadata:
  name: in-ng-svc
spec:
  type: NodePort                 #设置类型为NodePort,用于暴露端口
  ports:
  - port: 80
    targetPort: 80
  selector:
    nginx-label: nginx01
[root@master01 in-nodeport]#kubectl apply -f service.yaml 
service/in-ng-svc created
[root@master01 in-nodeport]#kubectl get svc in-ng-svc 
NAME        TYPE       CLUSTER-IP      EXTERNAL-IP   PORT(S)        AGE
in-ng-svc   NodePort   10.96.174.168   <none>        80:32502/TCP   10s
4.3 创建Ingress规则
[root@master01 in-nodeport]#vim ingress.yaml
[root@master01 in-nodeport]#cat ingress.yaml
apiVersion: networking.k8s.io/v1     #网络API组的v1版本。
kind: Ingress                        #创建一个Ingress 资源
metadata:
  name: nginx-ingress-test
spec:
  rules:                       #定义ingress规则
  - host: www.china.com        #指定当HTTP请求的Host头部为www.benet.com时触发规则
    http:                      #定义HTTP路由规则  
      paths:                   #定义路径列表及其对应的后端服务
      - path: /                #定义要匹配的路径。这里使用了根路径,也就是web服务的站点目录
        pathType: Prefix       #表示使用前缀匹配方式
        backend:               #定义与上述路径匹配时应该路由到的后端服务
          service:             #指定后端服务的名称
            name: in-ng-svc    #
            port:              #定义后端服务的端口
              number: 80       #端口号为80
-------------------------------------------------------------------------------------
#上述文件表示,客户端通过www.china.com访问时,会触发定义的ingress规则,
#而后通过ingress-controller转发到指定的后端服务(service)当中,后端服务再将请求转发给绑定的pod
[root@master01 in-nodeport]#kubectl apply -f ingress.yaml
ingress.networking.k8s.io/nginx-ingress-test created
[root@master01 in-nodeport]#kubectl get ingress
NAME                 CLASS    HOSTS           ADDRESS   PORTS   AGE
nginx-ingress-test   <none>   www.china.com             80      9s

5.使用客户端进行访问

//master01查看ingress的service对外暴露的端口
[root@master01 in-nodeport]#kubectl get svc -n ingress-nginx 
NAME            TYPE       CLUSTER-IP    EXTERNAL-IP   PORT(S)                      AGE
ingress-nginx   NodePort   10.96.43.71   <none>        80:31705/TCP,443:32391/TCP   137m

//客户端使用nginx-ingress-controller的service对外暴露的端口进行访问
[root@nfs ~]#cat /etc/hosts |grep www.china.com
192.168.83.40 node01 www.china.com     
#添加客户端的域名解析,IP地址为nginx-ingress-controller的pod所以节点的IP地址
[root@nfs ~]#curl www.china.com:31705 
this is web01
[root@nfs ~]#curl www.china.com:31705
this is web02
[root@nfs ~]#curl www.china.com:31705
this is web01
[root@nfs ~]#curl www.china.com:31705
this is web02
----------------------------------------------------------------------------------
可以看到,访问的方式,是以轮询的方式,发送到deployment管理的pod上。因为,它的数据流向是
1.用户将请求发送到ingress-controller,而后ingress-controller根据请求的Hosst头部信息,
也就是www.china.com触发ingress规则
2.ingress-controller通过ingress规则,获取到关联的service,以及endpoints关联地址
3.service会将流量平均分配,而后将地址返回给ingress-controller
4.ingress-controller最后将请求发送给合适的pod

四、虚拟主机

Ingress HTTP 代理访问虚拟主机,使用同一个nginx-ingress-controller,根据不同的域名,代理到不同的后端服务

例如访问www.china.com触发规则后,代理到service-01;访问www.zg.com触发规则二

(一)创建pod资源

创建两个不同的pod资源,或者两个不同的deployment资源

[root@master01 vhost]#cat pod.yaml 
apiVersion: v1
kind: Pod
metadata:
  name: nginx-01
  labels:
    nginx: nginx01
spec:
  containers: 
  - name: nginx
    image: nginx:1.18.0
    ports:
    - containerPort: 80
---
apiVersion: v1
kind: Pod
metadata:
  name: nginx-02
  labels:
    nginx: nginx02
spec:   
  containers: 
  - name: nginx
    image: nginx:1.18.0
    ports:
    - containerPort: 80
[root@master01 vhost]#kubectl apply -f pod.yaml 
pod/nginx-01 created
pod/nginx-02 created
[root@master01 vhost]#kubectl get pod -owide
NAME        READY  STATUS  RESTARTS  AGE  IP            NODE     NOMINATED NODE   READINESS GATES
nginx-01    1/1    Running  0        14s  10.244.2.8    node02   <none>           <none>
nginx-02    1/1    Running  0        13s  10.244.1.216  node01   <none>           <none>

自定义web访问页面

[root@master01 vhost]#kubectl exec -it nginx-01 bash
root@nginx-01:/# echo "this is nginx-01" >/usr/share/nginx/html/index.html 
root@nginx-01:/# exit
exit
[root@master01 in-nodeport]#kubectl exec -it nginx-02 bash
root@nginx-02:/# echo "this is nginx-02" >/usr/share/nginx/html/index.html
root@nginx-02:/# exit
exit
[root@master01 vhost]#curl 10.244.2.8
this is nginx-01
[root@master01 vhost]#curl 10.244.1.216
this is nginx-02

(二)创建service资源

[root@master01 vhost]#vim service.yaml 
[root@master01 vhost]#cat service.yaml 
apiVersion: v1
kind: Service
metadata:
  name: service-01
spec:
  ports:
  - port: 80
    targetPort: 80
  selector:
    nginx: nginx01         #使用标签选择,关联的pod为nginx-01
---
apiVersion: v1
kind: Service
metadata:
  name: service-02
spec:
  ports:
  - port: 80
    targetPort: 80
  selector:
    nginx: nginx02         #使用标签选择,关联的pod为nginx-02
[root@master01 vhost]#kubectl apply -f service.yaml 
service/service-01 created
service/service-02 created
[root@master01 vhost]#kubectl get svc
NAME         TYPE        CLUSTER-IP      EXTERNAL-IP   PORT(S)   AGE
service-01   ClusterIP   10.96.198.216   <none>        80/TCP    11s
service-02   ClusterIP   10.96.89.179    <none>        80/TCP    11s

(三)创建ingress规则

[root@master01 vhost]#cat ingress.yaml 
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
  name: nginx-vhost-ingress
spec:
  rules:
  - host: www.chinese.com
    http:
      paths:
      - path: /
        pathType: Prefix
        backend:
          service: 
            name: service-01
            port:
              number: 80
  - host: www.zg.com
    http:
      paths:
      - path: /
        pathType: Prefix
        backend:
          service: 
            name: service-02
            port:
              number: 80
[root@master01 vhost]#kubectl apply -f ingress.yaml 
ingress.networking.k8s.io/nginx-vhost-ingress created
[root@master01 vhost]#kubectl get ingress nginx-vhost-ingress 
NAME                  CLASS    HOSTS                        ADDRESS   PORTS   AGE
nginx-vhost-ingress   <none>   www.chinese.com,www.zg.com             80      12s

(四)客户端访问

[root@nfs ~]#cat /etc/hosts |grep www.chinese.com
192.168.83.40 node01 www.china.com www.chinese.com www.zg.com
#同样在客户端添加解析信息,而后使用nginx-ingress-controller的31705端口访问
[root@nfs ~]#curl www.chinese.com:31705
this is nginx-01
[root@nfs ~]#curl www.chinese.com:31705
this is nginx-01
[root@nfs ~]#curl www.zg.com:31705
this is nginx-02
[root@nfs ~]#curl www.zg.com:31705

五、HTPPS代理

要实现 HTTPS 代理,你需要在Ingress 对象中配置 SSL 证书,并确保 Ingress 控制器支持 HTTPS

(一)获取SSL证书

可以从证书颁发机构(CA)购买 SSL 证书,或者使用 Let's Encrypt 等服务获取免费证书

[root@master01 data]#mkdir /data/https
[root@master01 data]#cd /data/https
[root@master01 data]#openssl req -x509 -sha256 -nodes -days 365 -newkey rsa:2048 -keyout tls.key -out tls.crt -subj "/CN=nginxsvc/O=nginxsvc"
Generating a 2048 bit RSA private key
....................................+++
........+++
writing new private key to 'tls.key'
-----
[root@master01 https]#ls
tls.crt  tls.key
[root@master01 https]#
--------------------------------------------------------------------------------
openssl req #OpenSSL命令行工具的一个子命令,用于创建和处理PKCS#10 证书签名请求以及自签名证书
-x509       #指定要生成一个自签名的证书,而不是一个证书签名请求(CSR)。
-sha256     #使用SHA-256哈希算法来签名证书。
-nodes      #在生成私钥时不加密它。这意味着私钥将以明文形式存储在tls.key文件中
-days 365   #设置证书的有效期为 365 天(一年)。
-newkey rsa:2048  #在生成证书的同时,也生成一个新的RSA私钥,其长度为2048位。
-keyout tls.key   #指定私钥的输出文件名为 tls.key。
-out tls.crt      #指定证书的输出文件名为 tls.crt。
-subj "/CN=nginxsvc/O=nginxsvc"  #设置证书的主题(Subject)字段。
CN(通用名称)被设置为 nginxsvc,O(组织)也被设置为 nginxsvc。通常,CN 应该是域名或服务器名称

(二)创建Kubernetes Secret

将 SSL 证书和私钥存储在 Kubernetes Secret 中,以便 Ingress 控制器可以访问它们

[root@master01 https]#kubectl create secret tls my-tls-secret --key tls.key --cert tls.crt
secret/my-tls-secret created
[root@master01 https]#kubectl get secret my-tls-secret 
NAME            TYPE                DATA   AGE
my-tls-secret   kubernetes.io/tls   2      16s
[root@master01 https]#kubectl describe secret my-tls-secret 
Name:         my-tls-secret
Namespace:    default
Labels:       <none>
Annotations:  <none>

Type:  kubernetes.io/tls

Data
====
tls.crt:  1143 bytes
tls.key:  1708 bytes
----------------------------------------------------------------------------------------
kubectl               #Kubernetes 的命令行工具,用于与集群进行交互。
create secret tls     #指示 kubectl 创建一个 TLS 类型的 Secret。
my-tls-secret         #要创建的 Secret 的名称。
--key tls.key         #指定私钥文件的路径。文件处在当前路径
--cert tls.crt        #指定证书文件的路径。同样,文件处在当前路径

(三)创建pod资源

使用deployment控制器创建,或者直接创建pod

[root@master01 https]#vim pod-https.yaml 
[root@master01 https]#cat pod-https.yaml
apiVersion: v1
kind: Pod
metadata:
  name: nginx-https
  labels:
    nginx: nginx-https
spec:
  containers: 
  - name: nginx
    image: nginx:1.18.0
    ports:
    - containerPort: 80
[root@master01 https]#kubectl apply -f pod-https.yaml 
pod/nginx-https created
[root@master01 https]#kubectl get pod nginx-https -owide
NAME          READY  STATUS   RESTARTS AGE  IP          NODE    NOMINATED NODE  READINESS GATES
nginx-https   1/1    Running  0        12s  10.244.2.9  node02  <none>          <none>

自定义web界面

[root@master01 https]#kubectl exec -it nginx-https bash
root@nginx-https:/# echo "this is nginx-https" >/usr/share/nginx/html/index.html 
root@nginx-https:/# exit
exit
[root@master01 https]#curl 10.244.2.9
this is nginx-https

(四)创建service

[root@master01 https]#vim service-https.yaml 
[root@master01 https]#cat service-https.yaml 
apiVersion: v1
kind: Service
metadata:
  name: service-https
spec:
  ports:
  - port: 80
    targetPort: 80
  selector:
    nginx: nginx-https
[root@master01 https]#kubectl apply -f service-https.yaml 
service/service-https created
[root@master01 https]#kubectl get svc service-https 
NAME            TYPE        CLUSTER-IP      EXTERNAL-IP   PORT(S)   AGE
service-https   ClusterIP   10.96.128.206   <none>        80/TCP    13s

(五)创建ingress规则

[root@master01 https]#vim ingress-https.yaml 
[root@master01 https]#cat ingress-https.yaml 
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
  name: nginx-https-ingress
spec:
  tls:
  - hosts:                       #这是一个列表,指定了哪些主机名应该使用此TLS配置
    - www.https.com              #指定使用该TSL的主机名称为www.https.com,可以定义多个
    secretName: my-tls-secret    #引用Secret,该Secret包含TLS私钥和证书
  rules:
  - host: www.https.com          #与tls中hosts字段定义的主机名一致
    http:
      paths:
      - path: /
        pathType: Prefix
        backend:
          service: 
            name: service-https  #指定后端service名称
            port:
              number: 80
[root@master01 https]#kubectl apply -f ingress-https.yaml 
ingress.networking.k8s.io/nginx-https-ingress created
[root@master01 https]#kubectl get ingress nginx-https-ingress
NAME                  CLASS    HOSTS           ADDRESS       PORTS     AGE
nginx-https-ingress   <none>   www.https.com   10.96.43.71   80, 443   20s

(六)客户端访问

在客户端添加域名信息,使用https访问443端口映射的主机端口

使用虚拟机客户端的web浏览器

或者在物理机的 C:\Windows\System32\drivers\etc\hosts 文件添加www.https.com的解析信息

而后使用物理机浏览器访​问https://www.https.com:映射端口

[root@nfs ~]#cat /etc/hosts |grep www.https.com
192.168.83.40 node01 www.china.com www.chinese.com www.zg.com www.https.com
#添加客户端的解析信息,而后使用虚拟机的web浏览器访问

//在master节点,查看443端口映射的宿主机端口
[root@master01 https]#kubectl get svc -n ingress-nginx 
NAME            TYPE       CLUSTER-IP    EXTERNAL-IP   PORT(S)                      AGE
ingress-nginx   NodePort   10.96.43.71   <none>        80:31705/TCP,443:32391/TCP   3h10m
#使用浏览器访问https://www.https.com:32391端口

六、实现BasicAuth

BasicAuth是一种用于在客户端和服务器之间进行身份验证的协议,特别是用于HTTP请求的身份验证

BasicAuth通过在HTTP请求头中添加一个“Authorization”字段来进行身份验证。这个字段包含了一个Base64编码的用户名和密码信息

(一)创建认证文件

1.下载htpasswd工具

[root@master01 https]#mkdir /data/basicauth
[root@master01 https]#cd /data/basicauth/
[root@master01 basicauth]#yum install httpd-tools.x86_64 -y
#下载httpd-tools工具包,使用htpasswd命令生成证书文件

2.创建认证文件

[root@master01 basicauth]#htpasswd -c auth xiaoming
New password:                       #输入密码
Re-type new password:               #确认密码
Adding password for user xiaoming
[root@master01 basicauth]#ls
auth                                #生成的证书文件名称为auth
------------------------------------------------------------------------------
htpasswd #用于创建和更新存储用户名和密码的文件的实用工具
-c       #创建一个新的密码文件
auth     #存储用户信息的文件,文件名称固定为auth
xiaoming #添加到密码文件中的用户名,回车之后下面输入密码

(二)创建Secret

创建 secret 资源存储用户密码的认证文件

[root@master01 basicauth]#kubectl create secret generic basic-auth --from-file=auth
secret/basic-auth created
[root@master01 basicauth]#kubectl get secrets basic-auth 
NAME         TYPE     DATA   AGE
basic-auth   Opaque   1      15s
[root@master01 basicauth]#kubectl describe secrets basic-auth 
Name:         basic-auth
Namespace:    default
Labels:       <none>
Annotations:  <none>

Type:  Opaque

Data
====
auth:  47 bytes

(三)创建pod资源

[root@master01 basicauth]#vim pod-auth.yaml 
[root@master01 basicauth]#cat pod-auth.yaml 
apiVersion: v1
kind: Pod
metadata:
  name: nginx-auth
  labels:
    nginx: nginx-auth
spec:
  containers: 
  - name: nginx
    image: nginx:1.18.0
    ports:
    - containerPort: 80
[root@master01 basicauth]#kubectl apply -f pod-auth.yaml 
pod/nginx-auth created
[root@master01 basicauth]#kubectl get pod nginx-auth -owide
NAME         READY   STATUS    RESTARTS   AGE   IP             NODE     NOMINATED NODE   READINESS GATES
nginx-auth   1/1     Running   0          19s   10.244.1.217   node01   <none>           <none>
[root@master01 basicauth]#kubectl exec -it nginx-auth bash
root@nginx-auth:/# echo "this is auth" >/usr/share/nginx/html/index.html
root@nginx-auth:/# exit
exit
#自定义web界面

(四)创建service

[root@master01 basicauth]#cat service-auth.yaml 
apiVersion: v1
kind: Service
metadata:
  name: service-auth
spec:
  ports:
  - port: 80
    targetPort: 80
  selector:
    nginx: nginx-auth
[root@master01 basicauth]#kubectl apply -f pod-auth.yaml 
pod/nginx-auth created
[root@master01 basicauth]#kubectl apply -f service-auth.yaml 
service/service-auth created
[root@master01 basicauth]#kubectl get svc service-auth 
NAME           TYPE        CLUSTER-IP     EXTERNAL-IP   PORT(S)   AGE
service-auth   ClusterIP   10.96.127.61   <none>        80/TCP    15s

(五)创建ingress资源

[root@master01 basicauth]#vim ingress-auth.yaml 
[root@master01 basicauth]#cat ingress-auth.yaml 
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
  name: nginx-auth-ingress
  annotations:
    nginx.ingress.kubernetes.io/auth-type: basic
    #指定认证类型为基本认证(basic)
    nginx.ingress.kubernetes.io/auth-secret: basic-auth
    #指定包含基本认证凭据的Secret资源名称basic-auth
    nginx.ingress.kubernetes.io/auth-realm: 'Authentication Required - xiaoming'
    #定义了当用户需要认证时显示的领域(realm)名称,即认证窗口提示信息
spec:
  rules:
  - host: www.auth.com             #指定主机名触发条件
    http:
      paths:
      - path: /
        pathType: Prefix
        backend:
          service: 
            name: service-auth     #关联的后端服务service
            port:
              number: 80

添加解析信息后,使用web浏览器进行访问

[root@nfs ~]#cat /etc/hosts |grep www.auth.com
192.168.83.40 node01 www.auth.com

添加完解析信息后,使用浏览器访问80映射的主机端口,即www.auth.com:31705

七、Nginx重写

当域名更新之后,可以使用重写功能,使旧域名,跳转到新的域名当中

例如当访问www.old.com时,使用重写功能跳转到www.new.com

#metadata.annotations 配置说明

nginx.ingress.kubernetes.io/rewrite-target: <字符串>

此注解允许你修改目标服务的请求 URI。这对于重写来自 Ingress 的流量路径特别有用,尤其是当你想将流量映射到后端服务的不同路径时。

<字符串> 通常是一个包含捕获组的正则表达式,这些捕获组会被替换为实际请求路径中的相应部分。

nginx.ingress.kubernetes.io/ssl-redirect: <布尔值>

默认情况下,如果 Ingress 资源配置了 TLS 证书(通过 tls 部分),并且此注解设置为 true,则所有非 SSL 请求都将被重定向到 SSL(HTTPS)。

<布尔值> 可以是 true 或 false。如果设置为 false,即使配置了 TLS 证书,非 SSL 请求也不会被重定向。

nginx.ingress.kubernetes.io/force-ssl-redirect: <布尔值>

即使 Ingress 资源没有配置 TLS 证书,将此注解设置为 true 也会强制将所有请求重定向到 HTTPS。

<布尔值> 可以是 true 或 false。请注意,将此注解设置为 true 时,你需要确保 Nginx Ingress Controller 能够处理 HTTPS 请求(例如,通过前端代理或负载均衡器终止 SSL)。

nginx.ingress.kubernetes.io/app-root: <字符串>

如果你的应用程序部署在根路径(/)之外,但你想将所有根路径的流量重定向到该应用程序的实际路径,可以使用此注解。

<字符串> 是你的应用程序的实际根路径(例如,/myapp/)。

nginx.ingress.kubernetes.io/use-regex: <布尔值>

此注解指示 Ingress 资源中定义的路径是否使用正则表达式进行匹配。

<布尔值> 可以是 true 或 false。如果设置为 true,paths 下的 path 字段将被视为正则表达式进行匹配

以auth为例,使旧的域名访问时,跳转到该域名

[root@master01 data]#mkdir /data/rewrite
[root@master01 data]#cd  /data/rewrite/
[root@master01 rewrite]#vim ingress-rewrite.yaml
[root@master01 rewrite]#cat ingress-rewrite.yaml
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
  name: nginx-rewrite
  annotations:
    nginx.ingress.kubernetes.io/rewrite-target: http://www.auth.com:31705
#重写目标URL,重写为http://www.auth.com:31705
spec:
  rules:
  - host: www.rewrite.com  #流量应该匹配的主机名,访问该主机名,将会被重写
    http:
      paths:
      - path: /
        pathType: Prefix
        backend:
          service:
            name: nginx-rewrite
            port:
              number: 80
[root@master01 rewrite]#kubectl apply -f ingress-rewrite.yaml 
ingress.networking.k8s.io/nginx-rewrite created
[root@master01 rewrite]#kubectl get ingress nginx-rewrite 
NAME            CLASS    HOSTS             ADDRESS       PORTS   AGE
nginx-rewrite   <none>   www.rewrite.com   10.96.43.71   80      25s

添加解析信息之后使用浏览器访问

[root@nfs ~]#cat /etc/hosts |grep www.rewrite.com
192.168.83.40 node01 www.auth.com www.rewrite.com

更多的重写机制,可以查阅官方文档,或者nginx重写规则进行查看

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1789667.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

mac虚拟光驱工具:Daemon Tools for Mac

Daemon Tools for Mac是一款功能强大的虚拟光驱工具&#xff0c;它为用户提供了在Mac上模拟物理光驱的能力&#xff0c;从而方便用户处理各种光盘映像文件。以下是关于Daemon Tools for Mac的详细介绍&#xff1a; 守护进程工具&#xff1a;Daemon Tools不仅是一个简单的虚拟光…

Tomcat概述及部署

目录 一、Tomcat概述 1.Tomcat的简介 2.Tomcat 核心的三个组件 3.应用场景 4.Tomcat 请求过程 二、部署安装Tomcat 三、Tomcat 虚拟主机配置 四、Tomcat多实例部署 一、Tomcat概述 1.Tomcat的简介 Tomcat 是 Java 语言开发的&#xff0c;Tomcat 服务器是一个免费的开…

花费-效益分析筛选肿瘤标记物最佳组合

基于花费-效益分析的肿瘤标记物最佳组合筛选 本文的想法来自于一篇发表的论文[1]。论文作者有感于临床上存在的不恰当的肿瘤标记物的检测&#xff0c;搜集了各种肿瘤标记物&#xff08;TM&#xff09;的价格、检测结果和最终诊断等数据&#xff0c;使用逻辑回归模型分别计算出…

中国90米土壤渗流因子Fsic数据

Fsic(土壤渗流因子)&#xff1a;土壤渗流因子的计算是根据美国农业部(USDA)土壤质地分类&#xff0c; 进行分类、赋值并归一化,得到土壤渗流因子Fsic的值。将13种土壤质地类型分别在0-1之间均等赋值得到。其中Fsic值越高&#xff0c;代表土壤渗水能力越强&#xff0c;Fsic值域范…

彻底吃透A*算法的最优性

下面的博客将主要介绍A*算法在扩展结点&#xff08;这对于寻路时间很重要&#xff09;和总代价&#xff08;这对于保证最后解的最优性很重要&#xff09;上的最优性&#xff0c;并将淡化对A *完备性的介绍。 A* 算法流程 A*算法的流程如下[1]&#xff1a; 并定义 f ( n ) f(n…

编译openjdk12-33

编译环境 ubuntu20 Ubuntu里用户可以自行选择安装GCC或CLang来进行编译&#xff0c;但必须确保最低的版本为GCC 4.8或者CLang 3.2以上&#xff0c;官方推荐使用GCC 7.8或者CLang 9.1来完成编译。 源码 https://github.com/openjdk/jdk/tree/jdk-12%2B33 安装gcc sudo apt…

喜讯丨泰迪智能科技实力中标“健康大数据与人工智能实验室建设”项目

泰迪智能科技以健康数据分析与应用为主题的实验中心&#xff0c;为学校大健康产业大数据与人工智能应用人才培养提供载体&#xff0c;并基于培养中心根据学生专业的不同&#xff0c;提供不同的健康大数据学习资源&#xff0c;实现健康大数据技术和数据分析应用能力培养普遍提升…

nginx隐藏版本号、错误信息页面隐藏nginx软件、修改 HTTP 头信息中的connection 字段,防止回显具体版本号、curl命令

目录 安装之后隐藏 配置文件 源代码配置安装之前隐藏 修改nginx.h文件中的 13、14行 修改 HTTP 头信息中的connection 字段&#xff0c;防止回显具体版本号 配置文件49行 错误页面程序返回版本号、nginx隐藏 配置文件36行 ​编辑 安装nginx 相关选项说明 curl命令测试…

Spring Security 注册过滤器关键点与最佳实践

在 Spring Security 框架中&#xff0c;注册过滤器是实现身份验证和授权的关键组件。正确配置和使用注册过滤器对于确保应用程序的安全性至关重要。以下是一些关于 Spring Security 注册过滤器的注意事项和最佳实践。 过滤器链顺序&#xff1a; 注册过滤器通常位于过滤器链的末…

医用腕带朔源用的条形码与二维码如何选择

在医疗环境中的医用腕带作为患者身份识别和管理的重要工具&#xff0c;做为条形码和二维码腕带上的溯源技术&#xff0c;更是为患者信息快速获取、准确传递的保障&#xff0c;实现更加高效和准确的患者身份识别和管理&#xff0c;这种技术可以大大提高医疗服务的效率和质量&…

Linux 多线程 生产者消费者 问题

在 Linux 系统中&#xff0c;生产者和消费者问题是一个经典的多线程同步问题&#xff0c;用于描述如何在多线程环境中协调多个线程对共享资源的访问。这个问题通常涉及两个类型的线程&#xff1a;生产者线程和消费者线程。生产者线程负责生成数据并将其放入缓冲区&#xff0c;而…

2024年端午节放假通知

致尊敬的客户以及全体同仁&#xff1a; 2024年端午节将至&#xff0c;根据国务院办公厅通知精神&#xff0c;结合公司的实际情况&#xff0c;现将放假事宜通知如下&#xff1a; 2024年6月8日&#xff08;星期六&#xff09;至6月10日&#xff08;星期一&#xff09;&#xff…

一个简单的方式看看MySQL的锁

突然发现半个月没写了。最近事情太多了。 在日常工作的处理问题的过程中&#xff0c;我发现了一个简单的论证锁的问题&#xff0c;以前我讲的有点复杂&#xff0c;看来应该去改改之前的讲法了。 首先构造一个无主键无索引的表。并且初始化5条数据。 场景A&#xff1a; RR隔离…

颠沛流离学二叉树(完结撒花篇)

本篇会加入个人的所谓鱼式疯言 ❤️❤️❤️鱼式疯言:❤️❤️❤️此疯言非彼疯言 而是理解过并总结出来通俗易懂的大白话, 小编会尽可能的在每个概念后插入鱼式疯言,帮助大家理解的. &#x1f92d;&#x1f92d;&#x1f92d;可能说的不是那么严谨.但小编初心是能让更多人…

[机器学习] 低代码机器学习工具PyCaret库使用指北

PyCaret是一个开源、低代码Python机器学习库&#xff0c;能够自动化机器学习工作流程。它是一个端到端的机器学习和模型管理工具&#xff0c;极大地加快了实验周期&#xff0c;提高了工作效率。PyCaret本质上是围绕几个机器学习库和框架&#xff08;如scikit-learn、XGBoost、L…

【Kubernetes】k8s集群的污点、容忍、驱逐 以及排障思路

污点和容忍以及驱逐 一、污点&#xff08;Taint&#xff09; 污点介绍 节点亲和性&#xff0c;是Pod的一种属性&#xff08;偏好或硬性要求&#xff09;&#xff0c;它使Pod被吸引到一类特定的节点。Taint 则相反&#xff0c;它使节点能够排斥一类特定的 Pod。 Taint 和 Tol…

【ai】livekit服务本地开发模式1:example app信令交互详细流程

文档要安装git lfs 下载当前最新版本1.6.1windows版本:启动dev模式 服务器启动 (.venv) PS D:\XTRANS\pythonProject\LIVEKIT> cd .

python实现——分类类型数据挖掘任务(图形识别分类任务)

分类类型数据挖掘任务 基于卷积神经网络&#xff08;CNN&#xff09;的岩石图像分类。有一岩石图片数据集&#xff0c;共300张岩石图片&#xff0c;图片尺寸224x224。岩石种类有砾岩&#xff08;Conglomerate&#xff09;、安山岩&#xff08;Andesite&#xff09;、花岗岩&am…

【笔记】Sturctured Streaming笔记总结(Python版)

目录 相关资料 一、概述 1.1 基本概念 1.2 两种处理模型 &#xff08;1&#xff09;微批处理 &#xff08;2&#xff09;持续处理 1.3 Structured Streaming和Spark SQL、Spark Streaming关系 二、编写Structured Streaming程序的基本步骤 三、输入源 3.1 File源 &a…

python-题库篇-为什么数组下标从0 开始而不是 1

为什么很多编程语言要把 0 作为第一个下标索引&#xff0c;而不是直观的 1 呢&#xff1f; 这个问题 Dijkstra 已经解答过了&#xff0c;没错&#xff0c;就是你知道的 Dijkstra&#xff0c;Dijkstra 最短路径算法&#xff0c;荷兰语全名是 Edsger Wybe Dijkstra&#xff0c;于…