O cloud controller manager (CCM) integra o Kubernetes aos serviços de infraestrutura da Alibaba Cloud, como Classic Load Balancer (CLB) e Virtual Private Cloud (VPC). Esse componente permite anexar nós do cluster e servidores externos ao mesmo backend do CLB, evitando interrupções de tráfego durante a migração. Também é possível encaminhar tráfego de negócios para vários clusters Kubernetes para backup e recuperação de desastres, garantindo alta disponibilidade das aplicações. Este tópico descreve como implantar o CCM em um cluster Kubernetes autogerenciado.
Pré-requisitos
Um VNode está implantado no cluster Kubernetes autogerenciado.
Se o cluster Kubernetes estiver implantado em um data center on-premises, garanta a conectividade de rede entre o data center e a Alibaba Cloud.
Informações básicas
O CCM é um componente da Alibaba Cloud que integra o Kubernetes aos serviços de infraestrutura da plataforma. Ele oferece os seguintes recursos:
-
Gerencia o balanceamento de carga
Quando o tipo de Service é definido como LoadBalancer, o CCM cria e configura um Classic Load Balancer (CLB) da Alibaba Cloud para esse Service, incluindo recursos como instância do CLB, listeners e grupos de servidores de backend. Se os Endpoints do Service ou os nós do cluster mudarem, o CCM atualizará automaticamente o grupo de servidores de backend do CLB.
-
Habilita a comunicação entre nós
Ao usar o Flannel como componente de rede do cluster, o CCM estabelece conectividade entre containers e nós. Ele grava o bloco CIDR de pod de cada nó na tabela de rotas da VPC, permitindo a comunicação entre nós para os containers. Esse recurso vem habilitado por padrão e não requer configuração.
Para mais informações, consulte cloud controller manager.
O CCM é open source. Para detalhes do projeto, consulte cloud-provider-alibaba-cloud.
Preparações
Ignore esta seção se o cluster Kubernetes autogerenciado não utilizar instâncias do Elastic Compute Service (ECS) como nós. Caso contrário, siga estas etapas para configurar o providerID dos nós ECS, permitindo que o CCM gerencie as rotas.
-
Implante o OpenKruise para usar o controlador BroadcastJob.
Execute os comandos a seguir:
helm repo add openkruise https://openkruise.github.io/charts/ helm repo update helm install kruise openkruise/kruise --version 1.3.0Para mais informações, consulte a documentação do OpenKruise.
-
Configure o providerID dos nós ECS usando um BroadcastJob.
-
Salve o conteúdo a seguir como provider.yaml.
apiVersion: rbac.authorization.k8s.io/v1 kind: ClusterRole metadata: name: ecs-node-initor rules: - apiGroups: - "" resources: - nodes verbs: - get - patch --- apiVersion: v1 kind: ServiceAccount metadata: name: ecs-node-initor --- kind: ClusterRoleBinding apiVersion: rbac.authorization.k8s.io/v1 metadata: name: ecs-node-initor subjects: - kind: ServiceAccount name: ecs-node-initor namespace: default roleRef: kind: ClusterRole name: ecs-node-initor apiGroup: rbac.authorization.k8s.io --- apiVersion: apps.kruise.io/v1alpha1 kind: BroadcastJob metadata: name: create-ecs-node-provider-id spec: template: spec: serviceAccount: ecs-node-initor restartPolicy: OnFailure affinity: nodeAffinity: requiredDuringSchedulingIgnoredDuringExecution: nodeSelectorTerms: - matchExpressions: - key: type operator: NotIn values: - virtual-kubelet tolerations: - operator: Exists containers: - name: create-ecs-node-provider-id image: registry.cn-beijing.aliyuncs.com/eci-release/provider-initor:v1 command: [ "/usr/bin/init" ] env: - name: NODE_NAME valueFrom: fieldRef: fieldPath: spec.nodeName completionPolicy: type: Never failurePolicy: type: FailFast restartLimit: 3 -
Implante o BroadcastJob.
kubectl apply -f provider.yaml
-
-
Verifique os resultados do BroadcastJob.
kubectl get pods -o wideSe todos os pods relacionados a create-ecs-node-provider-id estiverem no estado Completed, o providerID dos nós ECS correspondentes foi configurado com sucesso. Veja um exemplo de saída:
NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES create-ecs-node-provider-id-9jvms 0/1 Completed 0 34m 172.23.xxx cn-shanghai.10.10.156.206 <none> 1/1 create-ecs-node-provider-id-f5sb8 0/1 Completed 0 34m 172.23.xxx cn-shanghai.10.10.156.202 <none> 1/1 create-ecs-node-provider-id-f6r2c 0/1 Completed 0 34m 172.23.xxx cn-shanghai.10.10.156.201 <none> 1/1 create-ecs-node-provider-id-nhrsp 0/1 Completed 0 34m 172.23.xxx cn-shanghai.10.10.156.203 <none> 1/1 create-ecs-node-provider-id-ntn4d 0/1 Completed 0 34m 172.23.xxx cn-shanghai.10.10.156.204 <none> 1/1 create-ecs-node-provider-id-rr2bk 0/1 Completed 0 34m 172.23.xxx cn-shanghai.10.10.156.205 <none> 1/1 -
(Opcional) Limpe o BroadcastJob.
kubectl delete -f provider.yaml
Procedimento
-
Crie um ConfigMap.
-
Salve o par de AccessKey da sua conta Alibaba Cloud como variáveis de ambiente.
export ACCESS_KEY_ID=LTAI******************** export ACCESS_KEY_SECRET=HAeS**************************Para obter informações sobre como conseguir um AccessKey ID e um AccessKey Secret, consulte Obter um par de AccessKey.
-
Execute o script a seguir para criar o ConfigMap.
Salve o conteúdo abaixo como configmap-ccm.sh, substitua o valor de region pelo seu ID de região e execute o script.
#!/bin/bash ## create ConfigMap kube-system/cloud-config for CCM. accessKeyIDBase64=`echo -n "$ACCESS_KEY_ID" |base64 -w 0` accessKeySecretBase64=`echo -n "$ACCESS_KEY_SECRET"|base64 -w 0` cat <<EOF >cloud-config.yaml apiVersion: v1 kind: ConfigMap metadata: name: cloud-config namespace: kube-system data: cloud-config.conf: |- { "Global": { "accessKeyID": "$accessKeyIDBase64", "accessKeySecret": "$accessKeySecretBase64", "region": "cn-hangzhou" } } EOF kubectl create -f cloud-config.yamlbash configmap-ccm.shApós a execução do script, um ConfigMap chamado cloud-config é criado no namespace kube-system.
-
-
Implante o CCM.
-
Modifique
${ImageVersion}e{$ClusterCIDR}e salve o conteúdo a seguir como ccm.yaml.Obtenha a
ImageVersionno changelog do CCM. Para mais informações, consulte cloud controller manager.Visualize o
ClusterCIDRexecutando o comandokubectl cluster-info dump | grep -m1 cluster-cidr.
apiVersion: rbac.authorization.k8s.io/v1 kind: ClusterRole metadata: name: system:cloud-controller-manager rules: - apiGroups: - coordination.k8s.io resources: - leases verbs: - get - list - update - create - apiGroups: - "" resources: - persistentvolumes - services - secrets - endpoints - serviceaccounts verbs: - get - list - watch - create - update - patch - apiGroups: - "" resources: - nodes verbs: - get - list - watch - delete - patch - update - apiGroups: - "" resources: - services/status verbs: - update - patch - apiGroups: - "" resources: - nodes/status verbs: - patch - update - apiGroups: - "" resources: - events - endpoints verbs: - create - patch - update --- apiVersion: v1 kind: ServiceAccount metadata: name: cloud-controller-manager namespace: kube-system --- kind: ClusterRoleBinding apiVersion: rbac.authorization.k8s.io/v1 metadata: name: system:cloud-controller-manager roleRef: apiGroup: rbac.authorization.k8s.io kind: ClusterRole name: system:cloud-controller-manager subjects: - kind: ServiceAccount name: cloud-controller-manager namespace: kube-system --- kind: ClusterRoleBinding apiVersion: rbac.authorization.k8s.io/v1 metadata: name: system:shared-informers roleRef: apiGroup: rbac.authorization.k8s.io kind: ClusterRole name: system:cloud-controller-manager subjects: - kind: ServiceAccount name: shared-informers namespace: kube-system --- kind: ClusterRoleBinding apiVersion: rbac.authorization.k8s.io/v1 metadata: name: system:cloud-node-controller roleRef: apiGroup: rbac.authorization.k8s.io kind: ClusterRole name: system:cloud-controller-manager subjects: - kind: ServiceAccount name: cloud-node-controller namespace: kube-system --- kind: ClusterRoleBinding apiVersion: rbac.authorization.k8s.io/v1 metadata: name: system:pvl-controller roleRef: apiGroup: rbac.authorization.k8s.io kind: ClusterRole name: system:cloud-controller-manager subjects: - kind: ServiceAccount name: pvl-controller namespace: kube-system --- kind: ClusterRoleBinding apiVersion: rbac.authorization.k8s.io/v1 metadata: name: system:route-controller roleRef: apiGroup: rbac.authorization.k8s.io kind: ClusterRole name: system:cloud-controller-manager subjects: - kind: ServiceAccount name: route-controller namespace: kube-system --- apiVersion: apps/v1 kind: DaemonSet metadata: labels: app: cloud-controller-manager tier: control-plane name: cloud-controller-manager namespace: kube-system spec: selector: matchLabels: app: cloud-controller-manager tier: control-plane template: metadata: labels: app: cloud-controller-manager tier: control-plane annotations: scheduler.alpha.kubernetes.io/critical-pod: '' spec: serviceAccountName: cloud-controller-manager tolerations: - effect: NoSchedule operator: Exists key: node-role.kubernetes.io/master - effect: NoSchedule operator: Exists key: node.cloudprovider.kubernetes.io/uninitialized nodeSelector: node-role.kubernetes.io/master: "" containers: - command: - /cloud-controller-manager - --leader-elect=true - --cloud-provider=alicloud - --use-service-account-credentials=true - --cloud-config=/etc/kubernetes/config/cloud-config.conf - --configure-cloud-routes=true - --route-reconciliation-period=3m - --leader-elect-resource-lock=endpoints # Replace ${ClusterCIDR} with your own cluster CIDR. # Example: 172.16.0.0/16 - --cluster-cidr=${ClusterCIDR} # Replace ${ImageVersion} with the latest release version. # Example: v2.1.0 image: registry.cn-hangzhou.aliyuncs.com/acs/cloud-controller-manager-amd64:${ImageVersion} livenessProbe: failureThreshold: 8 httpGet: host: 127.0.0.1 path: /healthz port: 10258 scheme: HTTP initialDelaySeconds: 15 timeoutSeconds: 15 name: cloud-controller-manager resources: requests: cpu: 200m volumeMounts: - mountPath: /etc/kubernetes/ name: k8s - mountPath: /etc/ssl/certs name: certs - mountPath: /etc/pki name: pki - mountPath: /etc/kubernetes/config name: cloud-config hostNetwork: true volumes: - hostPath: path: /etc/kubernetes name: k8s - hostPath: path: /etc/ssl/certs name: certs - hostPath: path: /etc/pki name: pki - configMap: defaultMode: 420 items: - key: cloud-config.conf path: cloud-config.conf name: cloud-config name: cloud-config -
Execute o comando a seguir para implantar o CCM.
kubectl create -f ccm.yaml
-
Verificar a implantação
-
Crie um Service do tipo LoadBalancer e um Deployment de backend de exemplo.
-
Salve o conteúdo a seguir como ccm-test.yaml.
Para evitar falhas ao baixar imagens, substitua o endereço da imagem por um da região do seu VNode.
apiVersion: v1 kind: Service metadata: name: nginx namespace: default annotations: service.beta.kubernetes.io/alibaba-cloud-loadbalancer-address-type: "intranet" spec: ports: - port: 80 protocol: TCP targetPort: 80 selector: app: nginx type: LoadBalancer --- apiVersion: apps/v1 kind: Deployment metadata: name: test-nginx spec: replicas: 2 selector: matchLabels: app: nginx template: metadata: labels: app: nginx spec: containers: - name: nginx image: registry-vpc.cn-beijing.aliyuncs.com/eci_open/nginx:1.14.2 -
Implante o Service e o Deployment.
kubectl create -f ccm-test.yamlApós a implantação, o CCM cria e configura um CLB da Alibaba Cloud para o Service, incluindo a instância do CLB, listeners e grupos de servidores de backend.
-
-
Verifique se o Service funciona conforme o esperado.
Execute o comando curl com o endereço IP externo do Service. Uma resposta bem-sucedida, como no exemplo abaixo, confirma que o serviço Nginx de backend está acessível.
[root@k8s-master ~]# kubectl get service NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE kubernetes ClusterIP 10.xxx.x.1 <none> 443/TCP 7d1h nginx LoadBalancer 10.xxx.02.253 172.16.5.xxx 80:32554/TCP 14m [root@k8s-master ~]# kubectl get pods | grep nginx test-nginx-84cbc7685b-gvlvq 1/1 Running 0 22s test-nginx-84cbc7685b-w9np2 1/1 Running 0 22s [root@k8s-master ~]# curl 172.16.5.xxx <!DOCTYPE html> <html> <head> <title>Welcome to nginx!</title> <style> 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>
Para mais informações sobre o uso de Services, consulte Uso do CCM.