云控制器管理器管理

特性状态: Kubernetes v1.11 [beta]

由于云厂商与 Kubernetes 项目的开发和发布速度不同,将特定于厂商的代码抽象到 `cloud-controller-manager` 二进制文件中,使得云厂商可以独立于 Kubernetes 核心代码进行演进。

`cloud-controller-manager` 可以链接到任何满足 cloudprovider.Interface 接口的云厂商。为了向后兼容,Kubernetes 核心项目中提供的 cloud-controller-manager 使用与 kube-controller-manager 相同的云库。在 Kubernetes 核心中已支持的云厂商,预计将使用树内 cloud-controller-manager 逐步从 Kubernetes 核心中迁移出来。

管理

要求

每个云厂商都有自己运行云厂商集成的要求,这些要求与运行 kube-controller-manager 时的要求应该不会有太大区别。一般来说,你需要:

  • 云认证/授权:你的云可能需要一个令牌或 IAM 规则来允许访问其 API。
  • Kubernetes 认证/授权:cloud-controller-manager 可能需要设置 RBAC 规则才能与 Kubernetes apiserver 通信。
  • 高可用性:与 kube-controller-manager 一样,你可能希望通过领导者选举(默认为开启)为 cloud controller manager 设置高可用环境。

运行 cloud-controller-manager

成功运行 cloud-controller-manager 需要修改你的集群配置。

  • kubeletkube-apiserverkube-controller-manager 必须根据用户对外部 CCM 的使用情况进行设置。如果用户有外部 CCM(而不是 Kubernetes Controller Manager 中的内部云控制器循环),则必须指定 --cloud-provider=external。否则,不应指定该参数。

请记住,配置你的集群以使用 cloud controller manager 将在以下几个方面改变你的集群行为:

  • 指定了 --cloud-provider=external 的组件将在初始化期间添加一个效果为 NoSchedule 的污点 node.cloudprovider.kubernetes.io/uninitialized。这标志着节点需要外部控制器进行第二次初始化,之后才能被调度工作。请注意,如果 cloud controller manager 不可用,集群中的新节点将无法被调度。此污点很重要,因为调度器可能需要关于节点的云特定信息,例如其区域或类型(高 CPU、GPU、大内存、抢占式实例等)。
  • 集群中关于节点的云信息将不再使用本地元数据检索,而是所有检索节点信息的 API 调用都将通过 cloud controller manager 进行。这意味着你可以限制 kubelet 对云 API 的访问以提高安全性。对于大型集群,你可能需要考虑 cloud controller manager 是否会达到速率限制,因为它现在负责处理集群内几乎所有对你云的 API 调用。

cloud controller manager 可以实现:

  • 节点控制器 - 负责使用云 API 更新 Kubernetes 节点以及删除在你的云上已被删除的 Kubernetes 节点。
  • 服务控制器 - 负责在你的云上为 LoadBalancer 类型的 Service 配置负载均衡器。
  • 路由控制器 - 负责在你的云上设置网络路由。
  • 如果你正在运行树外(out-of-tree)厂商,可以实现任何你想要的其他特性。

示例

如果你正在使用 Kubernetes 核心中当前支持的云厂商,并且想采用 cloud controller manager,请参阅Kubernetes 核心中的 cloud controller manager

对于不在 Kubernetes 核心中的 cloud controller manager,你可以在由云厂商或 SIG(特别兴趣小组)维护的仓库中找到相应的项目。

对于已在 Kubernetes 核心中的厂商,你可以在集群中将树内 cloud controller manager 作为 DaemonSet 运行,使用以下内容作为指导:

# This is an example of how to set up cloud-controller-manager as a Daemonset in your cluster.
# It assumes that your masters can run pods and has the role node-role.kubernetes.io/master
# Note that this Daemonset will not work straight out of the box for your cloud, this is
# meant to be a guideline.

---
apiVersion: v1
kind: ServiceAccount
metadata:
  name: cloud-controller-manager
  namespace: kube-system
---
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRoleBinding
metadata:
  name: system:cloud-controller-manager
roleRef:
  apiGroup: rbac.authorization.k8s.io
  kind: ClusterRole
  name: cluster-admin
subjects:
- kind: ServiceAccount
  name: cloud-controller-manager
  namespace: kube-system
---
apiVersion: apps/v1
kind: DaemonSet
metadata:
  labels:
    k8s-app: cloud-controller-manager
  name: cloud-controller-manager
  namespace: kube-system
spec:
  selector:
    matchLabels:
      k8s-app: cloud-controller-manager
  template:
    metadata:
      labels:
        k8s-app: cloud-controller-manager
    spec:
      serviceAccountName: cloud-controller-manager
      containers:
      - name: cloud-controller-manager
        # for in-tree providers we use registry.k8s.io/cloud-controller-manager
        # this can be replaced with any other image for out-of-tree providers
        image: registry.k8s.io/cloud-controller-manager:v1.8.0
        command:
        - /usr/local/bin/cloud-controller-manager
        - --cloud-provider=[YOUR_CLOUD_PROVIDER]  # Add your own cloud provider here!
        - --leader-elect=true
        - --use-service-account-credentials
        # these flags will vary for every cloud provider
        - --allocate-node-cidrs=true
        - --configure-cloud-routes=true
        - --cluster-cidr=172.17.0.0/16
      tolerations:
      # this is required so CCM can bootstrap itself
      - key: node.cloudprovider.kubernetes.io/uninitialized
        value: "true"
        effect: NoSchedule
      # these tolerations are to have the daemonset runnable on control plane nodes
      # remove them if your control plane nodes should not run pods
      - key: node-role.kubernetes.io/control-plane
        operator: Exists
        effect: NoSchedule
      - key: node-role.kubernetes.io/master
        operator: Exists
        effect: NoSchedule
      # this is to restrict CCM to only run on master nodes
      # the node selector may vary depending on your cluster setup
      nodeSelector:
        node-role.kubernetes.io/master: ""

限制

运行 cloud controller manager 可能会带来一些限制。尽管这些限制正在未来版本中得到解决,但对于生产工作负载而言,了解这些限制非常重要。

对卷的支持

cloud controller manager 没有实现 kube-controller-manager 中的任何卷控制器,因为卷集成还需要与 kubelet 协调。随着我们发展 CSI(容器存储接口)并增强对 flex volume 插件的支持,cloud controller manager 将增加必要的支持,以便云厂商可以完全集成卷。了解更多关于树外 CSI 卷插件的信息,请点击这里

可伸缩性

cloud-controller-manager 查询你的云厂商 API 以检索所有节点的信息。对于非常大的集群,请考虑可能的瓶颈,例如资源需求和 API 速率限制。

鸡与蛋的问题

cloud controller manager 项目的目标是将云特性的开发与 Kubernetes 核心项目解耦。不幸的是,Kubernetes 项目的许多方面都假定云厂商特性与项目紧密集成。因此,采用这种新架构可能会产生一些情况,即对云厂商提出信息请求,但如果原始请求未完成,cloud controller manager 可能无法返回该信息。

一个很好的例子是 Kubelet 中的 TLS 引导(bootstrapping)特性。TLS 引导假定 Kubelet 能够向云厂商(或本地元数据服务)请求其所有地址类型(私有、公共等),但 cloud controller manager 如果未首先初始化,就无法设置节点的地址类型,而初始化需要 Kubelet 具有与 apiserver 通信的 TLS 证书。

随着这项倡议的演进,将在未来版本中进行更改以解决这些问题。

接下来做什么

要构建和开发你自己的 cloud controller manager,请阅读开发 Cloud Controller Manager