使用Service对外暴露应用

在Kubernetes中,Pod会快速地被创建和删除,这导致Pod的IP地址不固定,因此无法直接对外提供服务。Service提供了一个固定的IP地址,外部服务(前端)可以通过这个固定的IP地址访问到后端Pod,而无需关心后端具体是哪些Pod以及它们的IP地址。Service的这种机制实现了前后端的解耦,从而对外提供稳定的服务。本文介绍如何通过ACS控制台和kubectl命令来创建和暴露服务。

方式一:通过控制台创建服务

  1. 登录容器计算服务控制台,在左侧导航栏选择集群

  2. 集群页面,单击目标集群名称,在左侧导航栏,选择网络 > 服务,然后在页面右侧,单击创建

  3. 创建服务对话框中,配置相关信息,单击确认

    配置项

    说明

    示例

    服务名称

    设置服务的名称。

    my-nginx-svc

    服务类型

    选择服务类型,即服务访问的方式。包括:

    • 虚拟集群IP:即ClusterIP,通过集群的内部IP暴露服务。选择该值后,服务只能在集群内部访问。

      说明

      选择虚拟集群IP时,支持配置实例间服务发现(Headless Service)。您可以使用Headless Service与其他服务发现机制进行通信,无需与Kubernetes的实现捆绑。

    • 负载均衡:即LoadBalancer,阿里云提供的负载均衡服务(SLB),支持选择公网访问私网访问,可以路由到ClusterIP服务。

      • 新建slb:当选择按规格计费时,可以通过单击修改规格,修改SLB规格。

      • 使用已有负载均衡: 您可以在已有的列表中选择SLB规格。

      说明
      • 使用已有的负载均衡实例会强制覆盖已有监听。

      • 通过Service创建的SLB无法复用,可能导致SLB被意外删除。仅支持复用您手动在控制台或调用OpenAPI创建的SLB。

      • 复用同一个SLB的多个Service,避免前端监听端口一致,否则会造成端口冲突。

      • 复用SLB时,Kubernetes将使用监听的名字以及虚拟服务器组的名字作为唯一标识符。请勿修改监听和虚拟服务器组的名字。

      • 不支持跨集群复用SLB。

    创建服务

    • 服务类型:负载均衡 (LoadBalancer)

    • 负载均衡类型:传统型负载均衡 CLB

    • 选择资源:新建资源

    新建CLB资源

    • 访问方式:私网访问

    • 其他配置使用默认值

    服务关联

    选择服务要绑定的后端应用。若不进行关联部署,则不会创建相关的Endpoints对象。关于服务关联的详细介绍,请参见Services without selectors

    • 名称:app

    • :nginx

    端口映射

    添加服务端口(对应Service YAML文件中的port)和容器端口(对应Service YAML文件中的targetPort),容器端口需要与后端Pod中暴露的容器端口一致。

    • 服务端口:80

    • 容器端口:80

    • 协议:TCP

    注解

    为该服务添加一个注解(Annotation),配置虚拟集群IP类或负载均衡类服务资源的注解。

    说明

    服务类型负载均衡时,阿里云相关注解才会生效。例如,设置service.beta.kubernetes.io/alicloud-loadbalancer-bandwidth:2,表示将该服务的带宽峰值设置为2 Mbit/s,从而控制服务的流量。更多参数,请参见通过Annotation配置传统型负载均衡CLB

    标签

    为该服务添加一个标签,标识该服务。

  4. 创建完成后,在当前服务页面中,可以找到新创建的服务my-nginx-svc

方式二:通过kubectl创建服务

  1. 在CloudShell上通过kubectl管理Kubernetes集群

  2. 参考以下内容,创建my-nginx-svc.yaml文件。

    展开查看my-nginx-svc.yaml

    apiVersion: v1
    kind: Service
    metadata:
      annotations:
        service.beta.kubernetes.io/alibaba-cloud-loadbalancer-address-type: "intranet"
      labels:
        app: nginx
      name: my-nginx-svc
      namespace: default
    spec:
      ports:
      - port: 80
        protocol: TCP
        targetPort: 80
      selector:
        app: nginx
      type: LoadBalancer

    字段

    说明

    kind

    定义资源对象为Service。

    metadata

    定义Service的名称、Label和命名空间等基本信息。

    metadata.annotations

    容器计算服务ACS支持丰富的负载均衡相关的注解(Annotations)。例如,在以上YAML示例中,service.beta.kubernetes.io/alibaba-cloud-loadbalancer-address-type指定Service的访问方式为intranet(私网访问)。更多注解,请参见通过Annotation配置传统型负载均衡CLB

    spec.selector

    定义Service的选择器。Service会根据Selector和Pod Label的匹配关系,确定Service所要关联暴露的后端Pod。

    spec.ports.port

    定义Service暴露给ClusterIP的端口,集群内部客户端访问Service的入口,即clusterIP:port

    spec.ports.targetPort

    定义后端Pod的端口。从port进来的流量,经由kube-proxy流入到后端Pod的targetPort上,最后进入容器。

    spec.type

    定义Service的访问方式。

    • LoadBalancer:使用阿里云负载均衡SLB公开服务。当Service没有指定已有SLB时,默认创建的SLB实例类型为公网。您可以通过设置注解service.beta.kubernetes.io/alibaba-cloud-loadbalancer-address-typeintranet,来创建私网访问的Service以及相应的私网SLB。

    • ClusterIP:在集群内部公开服务,可用于集群内部访问。

    重要

    阿里云容器计算服务ACS当前并不提供NodePort类型Service的使用,创建该类型的service会失败或无法生效。

  3. 执行以下命令,创建Service。

    kubectl apply -f my-nginx-svc.yaml
  4. 执行以下命令,验证服务是否创建成功。

    kubectl get svc my-nginx-svc

    预期输出:

    NAME           TYPE           CLUSTER-IP     EXTERNAL-IP     PORT(S)   AGE
    my-nginx-svc   LoadBalancer   172.16.XX.XX   192.168.XX.XX   80/TCP    13s

其他相关操作

更新Service

  • 方式一:执行以下命令,更新Service。

    kubectl edit service my-nginx-svc
  • 方式二:手动删除旧的Service,修改YAML文件后,重新创建Service。

    kubectl apply -f my-nginx-svc.yaml

查看Service

  1. 执行以下命令,查看Service。

    kubectl get service my-nginx-svc

    预期输出:

    NAME           TYPE           CLUSTER-IP     EXTERNAL-IP     PORT(S)   AGE
    my-nginx-svc   LoadBalancer   172.16.XX.XX   192.168.XX.XX   80/TCP    13s

删除Service

  1. 执行以下命令,删除Service。

    kubectl delete service my-nginx-svc