kubernetes Service-02 Headless Service

165 阅读3分钟

概述

Kubernetes (K8s) 中的 Headless Service 是一种特殊类型的服务对象,其主要特征在于它不会被分配一个虚拟的Cluster IP地址。在标准的Kubernetes服务中,创建服务时系统会自动分配一个集群内可以访问的IP地址,这个地址用于代理和负载均衡到该服务所关联的一组Pod

然而,在Headless Service的场景下,服务定义中的spec.clusterIP字段被设置为None,这意味着:

  • 无负载均衡:由于不分配Cluster IPkube-proxy不会为此服务执行任何负载均衡操作。
  • DNS解析:尽管不提供Cluster IP,但Kubernetes的内部DNS系统(如kube-dnscoreDNS)仍然会为服务下的每个Pod生成单独的DNS条目。客户端可以通过服务的DNS名称(通常是服务名.svc.cluster.local的形式)解析出关联Pod的直接IP地址列表,而不是单一的服务IP。
  • 直接Pod访问:这使得客户端可以直接与后端Pod建立连接,非常适合那些需要直接与特定Pod交互的应用程序,例如主从复制集群(如MongoDBCassandra等)、分布式存储系统或需要基于某种逻辑(如一致性哈希)选择Pod的应用场景。
  • StatefulSet配合使用Headless Service常与StatefulSet配合使用,以确保Pod具有稳定的、可预测的网络标识符(如hostname),这对于有状态应用非常重要,因为它们通常依赖于稳定的身份标识和网络可达性来进行数据同步或其他集群内部的协调工作。

示例

  • 创建Deployment
    apiVersion: apps/v1
    kind: Deployment
    metadata:
      name: nginx-deployment
    spec:
      selector:
        matchLabels: 
          app: nginx
      replicas: 3 
      template: 
        metadata:
          labels:
            app: nginx
        spec:
          containers:
          - name: nginx
            image: nginx:1.21.6
            ports:
            - containerPort: 80
    
    创建并查看结果
    [root@master1 service]# kubectl apply -f 06.yaml
    deployment.apps/nginx-deployment created
    
    [root@master1 service]# kubectl get pod
    NAME                               READY   STATUS    RESTARTS   AGE
    nginx-deployment-85dd6f4cc-5q9gw   1/1     Running   0          5s
    nginx-deployment-85dd6f4cc-h85hk   1/1     Running   0          5s
    nginx-deployment-85dd6f4cc-wxhsd   1/1     Running   0          5s
    
    [root@master1 service]# kubectl get deployment
    NAME               READY   UP-TO-DATE   AVAILABLE   AGE
    nginx-deployment   3/3     3            3           5m6s
    
  • 创建 Headless Service
      apiVersion: v1
      kind: Service
      metadata:
        name: nginx-service-headless
      spec:
        ports:
          - port: 80
            protocol: TCP
            targetPort: 80
        clusterIP: None
        selector:
          app: nginx  
        type: ClusterIP
    
    创建并查看结果
    [root@master1 service]# kubectl apply -f 07.yaml
      service/nginx-service-headless created
    [root@master1 service]# kubectl get svc
      NAME                     TYPE        CLUSTER-IP      EXTERNAL-IP   PORT(S)   AGE
      my-service               ClusterIP   10.10.150.224   <none>        80/TCP    47h
      nginx-service-headless   ClusterIP   None 
    
  • 查看Headless Service关联的Pod
    [root@master1 service]# kubectl describe service nginx-service-headless
      Name:              nginx-service-headless
      Namespace:         pod-ns
      Labels:            <none>
      Annotations:       <none>
      Selector:          app=nginx
      Type:              ClusterIP
      IP Families:       <none>
      IP:                None
      IPs:               None
      Port:              <unset>  80/TCP
      TargetPort:        80/TCP
      Endpoints:         10.244.166.145:80,10.244.166.146:80,10.244.166.147:80
      Session Affinity:  None
      Events:            <none>
      You have new mail in /var/spool/mail/root
      
    [root@master1 service]# kubectl get pod -o wide
      NAME                               READY   STATUS    RESTARTS   AGE   IP               NODE    NOMINATED NODE   READINESS GATES
      nginx-deployment-85dd6f4cc-5q9gw   1/1     Running   0          10m   10.244.166.145   node1   <none>           <none>
      nginx-deployment-85dd6f4cc-h85hk   1/1     Running   0          10m   10.244.166.147   node1   <none>           <none>
      nginx-deployment-85dd6f4cc-wxhsd   1/1     Running   0          10m   10.244.166.146   node1   <none>           <none>
    
  • 创建 Busybox Pod 登录到容器中 访问 Headless Service
    / # wget nginx-service-headless.pod-ns.svc.cluster.local
      Connecting to nginx-service-headless.pod-ns.svc.cluster.local (10.244.166.145:80)
      saving to 'index.html'
      index.html           100% |**************************************************************************************************************************************************|   615  0:00:00 ETA
      'index.html' saved
      / # more index.html
      <!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>
      <p>If you see this page, the nginx web server is successfully installed and
      working. Further configuration is required.</p>
    
      <p>For online documentation and support please refer to
      <a href="http://nginx.org/">nginx.org</a>.<br/>
      Commercial support is available at
      <a href="http://nginx.com/">nginx.com</a>.</p>
    
      <p><em>Thank you for using nginx.</em></p>
      </body>
      </html>
    
    访问了PodIP
    Connecting to nginx-service-headless.pod-ns.svc.cluster.local (10.244.166.145:80)
    

总结来说,Kubernetes Headless Service是一个用于支持无需负载均衡、需要直接访问Pod实例或者要求客户端自行管理连接逻辑的高级特性。它为那些希望精细控制服务发现和通信的应用提供了灵活性。