2025,每天10分钟,跟我学K8S(二十)- Ingress

        上篇文章介绍service时有说了暴露了service对外的三种方式ClusterIP、NodePort与LoadBalance,这几种方式都是在service的维度提供的,service的作用体现在两个方面,对集群内部,它不断跟踪pod的变化,更新endpoint中对应pod的对象,提供了ip不断变化的pod的服务发现机制,对集群外部,他类似负载均衡器,可以在集群内外部对pod进行访问。但是,单独用service暴露服务的方式,在实际生产环境中不太合适:

        ClusterIP的方式只能在集群内部访问。

        NodePort方式的话,测试环境使用还行,当有几十上百的服务在集群中运行时,NodePort的端口管理是灾难。

        LoadBalance方式受限于云平台,且通常在云平台部署SLB还需要额外的费用。

        那除了这种方法,是否还有其他更方便的方式呢?当然是有的,k8s还提供了一种集群维度暴露服务的方式,也就是ingress。ingress可以简单理解为service的service,他通过独立的ingress对象来制定请求转发的规则,把请求路由到一个或多个service中。这样就把服务与请求规则解耦了,可以从业务维度统一考虑业务的暴露,而不用为每个service单独考虑。

举个例子,可以通过一个ingress对象来实现图中的请求转发:

        ingress规则是很灵活的,可以根据不同域名、不同path转发请求到不同的service,并且支持https/http。

ingress的组成:

        ingress由两部分组成,ingress控制器和ingress,简单的抽象理解就是ingress控制器就是一个nginx服务,而ingress就是nginx的配置文件

ingress控制器

        实际负责实现ingress规则的组件

ingress

        K8S中的资源对象,用于管理集群外部到集群内部服务的流量路由。它定义了如何将外部流量路由到集群内的服务。

ingress的安装演示:

        上面说了这么多,那实际安装一个ingress来演示

1.ingress的版本选择

可以参考GitHub - kubernetes/ingress-nginx: Ingress NGINX Controller for KubernetesIngress NGINX Controller for Kubernetes. Contribute to kubernetes/ingress-nginx development by creating an account on GitHub.https://github.com/kubernetes/ingress-nginx?tab=readme-ov-file#supported-versions-table

2.下载对应版本

这里选择的是次新版本,v1.11.4的版本https://raw.githubusercontent.com/kubernetes/ingress-nginx/controller-v1.11.4/deploy/static/provider/baremetal/deploy.yamlhttps://raw.githubusercontent.com/kubernetes/ingress-nginx/controller-v1.11.4/deploy/static/provider/baremetal/deploy.yaml

3.修改配置文件

3.1修改镜像地址

将所有的registry.k8s.io 修改为k8s.m.daocloud.io

3.2 修改Deployment 为DaemonSet

通过之前的学习,我们知道这是为了让每个node都能对外提供服务,同时注销掉strategy,因为daemonset没有这些。

    3.3新增一行hostNetwork: true

    添加该字段让docker使用物理机网络,在物理机暴露服务端口(80),注意物理机80端口提前不能被占用

    3.4 修改dnsPolicy: ClusterFirst为 dnsPolicy: ClusterFirstWithHostNet 

    使用hostNetwork后容器会使用物理机网络包括DNS,会无法解析内部service,使用此参数让容器使用K8S的DNS

    4.安装ingress

    kubectl apply -f deploy.yaml

    在创建了一些列的对象后,通过查看对应ingress这个namespace下的pod,看到安装了一个nginx-controller的pod 和2个admission的job

    # kubectl get pod  -n ingress-nginx
    NAME                                        READY   STATUS      RESTARTS   AGE
    ingress-nginx-admission-create-925gj        0/1     Completed   0          84s
    ingress-nginx-admission-patch-z2rpd         0/1     Completed   1          84s
    ingress-nginx-controller-7974db866b-rpz4q   1/1     Running     0          84s
    

    再查看下ingress-nginx这个namespace下的svc

    # kubectl get svc -n ingress-nginx 
    NAME                                 TYPE        CLUSTER-IP      EXTERNAL-IP   PORT(S)                      AGE
    ingress-nginx-controller             NodePort    10.10.130.196   <none>        80:11604/TCP,443:13703/TCP   35m
    ingress-nginx-controller-admission   ClusterIP   10.10.247.32    <none>        443/TCP                      35m
    

    看到启动了一个NodePort类型的svc,名为ingress-nginx-controller,对外暴露的端口为11604-->80,13703-->443.  这2个是随机端口。请记住这2个对外的NodePort端口。

    5.创建ingress的配置并应用

    下文配置是在网上看到觉得写的挺好的,拿来直接用

    # cat ingree_demo.yaml 
    # 部署3个nginx实例
    apiVersion: apps/v1
    kind: Deployment
    metadata:
      name: nginx-deployment
    spec:
      replicas: 3
      selector:
        matchLabels:
          app: nginx-pod
      template:
        metadata:
          labels:
            app: nginx-pod
        spec:
          containers:
          - name: nginx
            image: m.daocloud.io/docker.io/nginx
            ports:
            - containerPort: 80
    ---
    # 部署3个tomcat实例
    apiVersion: apps/v1
    kind: Deployment
    metadata:
      name: tomcat-deployment
    spec:
      replicas: 3
      selector:
        matchLabels:
          app: tomcat-pod
      template:
        metadata:
          labels:
            app: tomcat-pod
        spec:
          containers:
          - name: tomcat
            image: m.daocloud.io/docker.io/tomcat
            ports:
            - containerPort: 8080
    ---
    # 部署nginx的Service
    apiVersion: v1
    kind: Service
    metadata:
      name: nginx-service
    spec:
      selector:
        app: nginx-pod
      type: ClusterIP
      ports:
      - port: 80
        targetPort: 80
    ---
    # 部署tomcat的Service
    apiVersion: v1
    kind: Service
    metadata:
      name: tomcat-service
    spec:
      selector:
        app: tomcat-pod
      type: ClusterIP
      ports:
      - port: 8080
        targetPort: 8080
    ---
    # 创建ingress
    apiVersion: networking.k8s.io/v1
    kind: Ingress
    metadata:
      name: ingress-http
      annotations:   # 注意要开启这两行
        kubernetes.io/ingress.class: "nginx"  
    spec:
      # 上面的IngressClass名称
      ingressClassName: "nginx"
      rules:
      # 域名,稍后要通过这个域名访问服务
      - host: nginx.k8s.com
        http:
          paths:
          # 路径,访问域名时后面添加的路径
          - path: /
            pathType: Prefix
            backend:
              # 要代理的服务和服务的端口
              service:
                name: nginx-service
                port: 
                  number: 80
      - host: tomcat.k8s.com
        http:
          paths:
          - path: /
            pathType: Prefix
            backend:
              service:
                name: tomcat-service
                port: 
                  number: 8080
    
    
    
    
    
    # kubectl apply -f ingree_demo.yaml 
    deployment.apps/nginx-deployment created
    deployment.apps/tomcat-deployment created
    service/nginx-service created
    service/tomcat-service created
    ingress.networking.k8s.io/ingress-http created
    

    6.查看pod和ingress对象

    通过查看得知,创建了3个tomcat的pod和3个nginx的pod;创建了了1个tomcat的service和1个nginx的service;创建了一个ingress,里面包含2个域名nginx.k8s.com,tomcat.k8s.com  

    # kubectl get pod,svc,ingress
    NAME                                    READY   STATUS    RESTARTS   AGE
    pod/nginx-deployment-7d49b7f58-djkcj    1/1     Running   0          95s
    pod/nginx-deployment-7d49b7f58-l9xlz    1/1     Running   0          95s
    pod/nginx-deployment-7d49b7f58-wmpwd    1/1     Running   0          95s
    pod/tomcat-deployment-9ddfdb848-4v5sx   1/1     Running   0          95s
    pod/tomcat-deployment-9ddfdb848-t9jpq   1/1     Running   0          95s
    pod/tomcat-deployment-9ddfdb848-vhd9n   1/1     Running   0          95s
    
    NAME                     TYPE        CLUSTER-IP    EXTERNAL-IP   PORT(S)    AGE
    service/kubernetes       ClusterIP   10.10.0.1     <none>        443/TCP    40d
    service/nginx-service    ClusterIP   10.10.81.35   <none>        80/TCP     95s
    service/tomcat-service   ClusterIP   10.10.3.65    <none>        8080/TCP   95s
    
    NAME                                     CLASS   HOSTS                          ADDRESS        PORTS   AGE
    ingress.networking.k8s.io/ingress-http   nginx   nginx.k8s.com,tomcat.k8s.com   172.21.176.3   80      95s

    通过kubectl describe ingress ingress-http ,可以看出来流量转发的走向

    访问nginx.k8s.com/   --> service服务(nginx-service:80) --> 后端pod (10.20.213.52:80,10.20.213.56:80,10.20.213.57:80)

    访问tomcat.k8s.com/   --> service服务(tomcat-service:8080) --> 后端pod (10.20.213.44:8080,10.20.213.45:8080,10.20.213.58:8080)                  

    # kubectl describe ingress ingress-http 
    Name:             ingress-http
    Labels:           <none>
    Namespace:        default
    Address:          172.21.176.3
    Ingress Class:    nginx
    Default backend:  <default>
    Rules:
      Host            Path  Backends
      ----            ----  --------
      nginx.k8s.com   
                      /   nginx-service:80 (10.20.213.52:80,10.20.213.56:80,10.20.213.57:80)
      tomcat.k8s.com  
                      /   tomcat-service:8080 (10.20.213.44:8080,10.20.213.45:8080,10.20.213.58:8080)
    Annotations:      <none>
    Events:
      Type    Reason  Age                From                      Message
      ----    ------  ----               ----                      -------
      Normal  Sync    10m (x2 over 10m)  nginx-ingress-controller  Scheduled for sync
    

    7.访问测试

    通过修改host的方式,将nginx.k8s.com 和 tomcat.k8s.com 域名解析到任意Node的公网IP。然后通过web去访问测试

    # ping nginx.k8s.com
    PING nginx.k8s.com (172.21.176.3) 56(84) bytes of data.
    64 bytes from k8s-master 172.21.176.3): icmp_seq=1 ttl=64 time=1.54 ms
    
    
    root@k8s-master:~# curl nginx.k8s.com:11604
    <!DOCTYPE html>
    <html>
    <head>
    <title>Welcome to nginx!</title>
    <style>
    html { color-scheme: light dark; }
    body { width: 35em; margin: 0 auto;
    font-family: Tahoma, Verdana, Arial, sans-serif; }
    </style>
    </head>
    <body>
    <h1>Welcome to nginx!</h1>
    ....
    
    
    
    root@k8s-master:~# ping tomcat.k8s.com
    PING tomcat.k8s.com (172.21.176.3) 56(84) bytes of data.
    64 bytes from ht.prod.k8s001-local.wh (172.21.176.3): icmp_seq=1 ttl=64 time=0.310 ms
    
    # 通过nodeport端口访问
    root@k8s-master:~# curl  tomcat.k8s.com:11604
    <!doctype html><html lang="en"><head><title>HTTP Status 404 – Not Found
    .....
    
    # 通过ingress 80端口访问
    root@k8s-master:~# curl  nginx.k8s.com
    <!DOCTYPE html>
    <html>
    <head>
    <title>Welcome to nginx!</title>
    ......

    web页面打开测试

    posted @ 2025-03-20 17:51  Devopser06  阅读(81)  评论(0)    收藏  举报  来源