Kubernetes 声明网络策略

本文可以帮助您开始使用 Kubernetes 的 NetworkPolicy API 声明网络策略去管理 Pod 之间的通信

Before you begin

您首先需要有一个支持网络策略的 Kubernetes 集群。已经有许多支持 NetworkPolicy 的网络提供商,包括:

  • Calico
  • Romana
  • Weave 网络

注意:以上列表是根据产品名称按字母顺序排序,而不是按推荐或偏好排序。下面示例对于使用了上面任何提供商的 Kubernetes 集群都是有效的

创建一个nginx deployment 并且通过服务将其暴露

为了查看 Kubernetes 网络策略是怎样工作的,可以从创建一个nginx deployment 并且通过服务将其暴露开始

$ kubectl run nginx --image=nginx --replicas=2
deployment "nginx" created
$ kubectl expose deployment nginx --port=80 
service "nginx" exposed

在 default 命名空间下运行了两个 nginx pod,而且通过一个名字为 nginx 的服务进行了暴露

$ kubectl get svc,pod
NAME                        CLUSTER-IP    EXTERNAL-IP   PORT(S)    AGE
svc/kubernetes              10.100.0.1    <none>        443/TCP    46m
svc/nginx                   10.100.0.16   <none>        80/TCP     33s

NAME                        READY         STATUS        RESTARTS   AGE
po/nginx-701339712-e0qfq    1/1           Running       0          35s
po/nginx-701339712-o00ef    1/1           Running       0          35s

测试服务能够被其它的 pod 访问

您应该可以从其它的 pod 访问这个新的 nginx 服务。为了验证它,从 default 命名空间下的其它 pod 来访问该服务。请您确保在该命名空间下没有执行孤立动作。

启动一个 busybox 容器,然后在容器中使用 wget 命令去访问 nginx 服务:

$ kubectl run busybox --rm -ti --image=busybox /bin/sh
Waiting for pod default/busybox-472357175-y0m47 to be running, status is Pending, pod ready: false

Hit enter for command prompt

/ # wget --spider --timeout=1 nginx
Connecting to nginx (10.100.0.16:80)
/ #

限制访问 nginx 服务

如果说您想限制 nginx 服务,只让那些拥有标签 access: true 的 pod 访问它,那么您可以创建一个只允许从那些 pod 连接的 NetworkPolicy:

kind: NetworkPolicy
apiVersion: networking.k8s.io/v1
metadata:
  name: access-nginx
spec:
  podSelector:
    matchLabels:
      run: nginx
  ingress:
  - from:
    - podSelector:
        matchLabels:
          access: "true"

为服务指定策略

使用 kubectl 工具根据上面的 nginx-policy.yaml 文件创建一个 NetworkPolicy:

$ kubectl create -f nginx-policy.yaml
networkpolicy "access-nginx" created

当访问标签没有定义时测试访问服务

如果您尝试从没有设定正确标签的 pod 中去访问 nginx 服务,请求将会超时:

$ kubectl run busybox --rm -ti --image=busybox /bin/sh
Waiting for pod default/busybox-472357175-y0m47 to be running, status is Pending, pod ready: false

Hit enter for command prompt

/ # wget --spider --timeout=1 nginx 
Connecting to nginx (10.100.0.16:80)
wget: download timed out
/ #

定义访问标签后再次测试

创建一个拥有正确标签的 pod,您将看到请求是被允许的:

$ kubectl run busybox --rm -ti --labels="access=true" --image=busybox /bin/sh
Waiting for pod default/busybox-472357175-y0m47 to be running, status is Pending, pod ready: false

Hit enter for command prompt

/ # wget --spider --timeout=1 nginx
Connecting to nginx (10.100.0.16:80)
/ #

译者:jianzhangbjz / 原文链接

K8S中文社区微信公众号

Kubernetes 为 Namespace 配置最小和最大 CPU 限制

本文展示了如何设置 namespace 中容器和 Pod 使用的 CPU 资源的最小和最大值。您可以设置 LimitRange 对象中 CPU 的最小和最大值。如果 Pod 没有符合 LimitRange 施加的限制,那么它就不能在 namespace 中创建。

Before you begin

You need to have a Kubernetes cluster, and the kubectl command-line tool must be configured to communicate with your cluster. If you do not already have a cluster, you can create one by using Minikube.

集群中的每个节点至少需要 1 CPU。

创建一个 namespace

请创建一个 namespace,这样您在本练习中创建的资源就可以和集群中其余资源相互隔离。

kubectl create namespace constraints-cpu-example

创建一个 LimitRange 和一个 Pod

这是 LimitRange 的配置文件:

cpu-constraints.yaml 
apiVersion: v1
kind: LimitRange
metadata:
  name: cpu-min-max-demo-lr
spec:
  limits:
  - max:
      cpu: "800m"
    min:
      cpu: "200m"
    type: Container

创建 LimitRange:

kubectl create -f https://k8s.io/docs/tasks/administer-cluster/cpu-constraints.yaml --namespace=constraints-cpu-example

查看 LimitRange 的详细信息:

kubectl get limitrange cpu-min-max-demo-lr --output=yaml --namespace=constraints-cpu-example

输出显示了符合预期的最小和最大 CPU 限制。但请注意,即使您没有在配置文件中为 LimitRange 指定默认值,它们也会被自动创建。

limits:
- default:
    cpu: 800m
  defaultRequest:
    cpu: 800m
  max:
    cpu: 800m
  min:
    cpu: 200m
  type: Container

现在,每当在 constraints-cpu-example namespace 中创建一个容器时,Kubernetes 都会执行下列步骤:

  • 如果容器没有指定自己的 CPU 请求(CPU request)和限制(CPU limit),系统将会为其分配默认值。
  • 验证容器的 CPU 请求大于等于 200 millicpu。
  • 验证容器的 CPU 限制小于等于 800 millicpu。

这是一份包含一个容器的 Pod 的配置文件。这个容器的配置清单指定了 500 millicpu 的 CPU 请求和 800 millicpu 的 CPU 限制。这些配置符合 LimitRange 施加的最小和最大 CPU 限制。

cpu-constraints-pod.yaml 
apiVersion: v1
kind: Pod
metadata:
  name: constraints-cpu-demo
spec:
  containers:
  - name: constraints-cpu-demo-ctr
    image: nginx
    resources:
      limits:
        cpu: "800m"
      requests:
        cpu: "500m"

创建 Pod:

kubectl create -f https://k8s.io/docs/tasks/administer-cluster/cpu-constraints-pod.yaml --namespace=constraints-cpu-example

验证 Pod 的容器是否运行正常:

kubectl get pod constraints-cpu-demo --namespace=constraints-cpu-example

查看关于 Pod 的详细信息:

kubectl get pod constraints-cpu-demo --output=yaml --namespace=constraints-cpu-example

输出显示了容器的 CPU 请求为 500 millicpu,CPU 限制为 800 millicpu。这符合 LimitRange 施加的限制条件。

resources:
  limits:
    cpu: 800m
  requests:
    cpu: 500m

删除 Pod:

kubectl delete pod constraints-cpu-demo --namespace=constraints-cpu-example

尝试创建一个超过最大 CPU 限制的 Pod

这是一份包含一个容器的 Pod 的配置文件。这个容器的配置清单指定了 500 millicpu 的 CPU 请求和 1.5 cpu 的 CPU 限制。

cpu-constraints-pod-2.yaml 
apiVersion: v1
kind: Pod
metadata:
  name: constraints-cpu-demo-2
spec:
  containers:
  - name: constraints-cpu-demo-2-ctr
    image: nginx
    resources:
      limits:
        cpu: "1.5"
      requests:
        cpu: "500m"

尝试创建 Pod:

kubectl create -f https://k8s.io/docs/tasks/administer-cluster/cpu-constraints-pod-2.yaml --namespace=constraints-cpu-example

输出显示 Pod 没有能够成功创建,因为容器指定的 CPU 限制值太大:

Error from server (Forbidden): error when creating "docs/tasks/administer-cluster/cpu-constraints-pod-2.yaml":
pods "constraints-cpu-demo-2" is forbidden: maximum cpu usage per Container is 800m, but limit is 1500m.

尝试创建一个不符合最小 CPU 请求的 Pod

这是一份包含一个容器的 Pod 的配置文件。这个容器的配置清单指定了 100 millicpu 的 CPU 请求和 800 millicpu 的 CPU 限制。

cpu-constraints-pod-3.yaml 
apiVersion: v1
kind: Pod
metadata:
  name: constraints-cpu-demo-4
spec:
  containers:
  - name: constraints-cpu-demo-4-ctr
    image: nginx
    resources:
      limits:
        cpu: "800m"
      requests:
        cpu: "100m"

尝试创建 Pod:

kubectl create -f https://k8s.io/docs/tasks/administer-cluster/cpu-constraints-pod-3.yaml --namespace=constraints-cpu-example

输出显示 Pod 没有能够成功创建,因为容器指定的 CPU 请求值太小:

Error from server (Forbidden): error when creating "docs/tasks/administer-cluster/cpu-constraints-pod-3.yaml":
pods "constraints-cpu-demo-4" is forbidden: minimum cpu usage per Container is 200m, but request is 100m.

创建一个没有指定任何 CPU 请求和限制的 Pod

这是一份包含一个容器的 Pod 的配置文件。这个容器没有指定 CPU 请求,也没有指定 CPU 限制。

cpu-constraints-pod-4.yaml 
apiVersion: v1
kind: Pod
metadata:
  name: constraints-cpu-demo-4
spec:
  containers:
  - name: constraints-cpu-demo-4-ctr
    image: vish/stress

创建 Pod:

kubectl create -f https://k8s.io/docs/tasks/administer-cluster/cpu-constraints-pod-4.yaml --namespace=constraints-cpu-example

查看关于 Pod 的详细信息:

kubectl get pod constraints-cpu-demo-4 --namespace=constraints-cpu-example --output=yaml

输出显示 Pod 的容器具有 800 millicpu 的 CPU 请求和 800 millicpu 的 CPU 限制。容器是如何获取这些值的呢?

resources:
  limits:
    cpu: 800m
  requests:
    cpu: 800m

因为您的容器没有指定自己的 CPU 请求和限制,所以它将从 LimitRange 获取 默认的 CPU 请求和限制值

到目前为止,您的容器可能在运行,也可能没有运行。回想起来,有一个先决条件就是节点必须至少拥有 1 CPU。如果每个节点都只有 1 CPU,那么任何一个节点上都没有足够的可用 CPU 来容纳 800 millicpu 的请求。如果碰巧使用的节点拥有 2 CPU,那么它可能会有足够的 CPU 来容纳 800 millicpu 的请求。

删除 Pod:

kubectl delete pod constraints-cpu-demo-4 --namespace=constraints-cpu-example

应用最小和最大 CPU 限制

LimitRange 在 namespace 中施加的最小和最大 CPU 限制只有在创建和更新 Pod 时才会被应用。改变 LimitRange 不会对之前创建的 Pod 造成影响。

最小和最大 CPU 限制的动因

作为一个集群管理员,您可能希望对 Pod 能够使用的 CPU 资源数量施加限制。例如:

  • 集群中每个节点拥有 2 CPU。您不希望任何 Pod 请求超过 2 CPU 的资源,因为集群中没有节点能支持这个请求。
  • 集群被生产部门和开发部门共享。 您希望生产负载最多使用 3 CPU 而将开发负载限制为 1 CPU。这种情况下,您可以为生产环境和开发环境创建单独的 namespace,并对每个 namespace 应用 CPU 限制。

清理

删除 namespace:

kubectl delete namespace constraints-cpu-example

What’s next

对于集群管理员

对于应用开发者

译者:xiaosuiba 原文链接

K8S中文社区微信公众号

Kubernetes Pod 优先级和抢占

FEATURE STATE: Kubernetes v1.8 alpha

Kubernetes 1.8 及其以后的版本中可以指定 Pod 的优先级。优先级表明了一个 Pod 相对于其它 Pod 的重要性。当 Pod 无法被调度时,scheduler 会尝试抢占(驱逐)低优先级的 Pod,使得这些挂起的 pod 可以被调度。在 Kubernetes 未来的发布版本中,优先级也会影响节点上资源回收的排序。

注: 抢占不遵循 PodDisruptionBudget;更多详细的信息,请查看 限制部分

怎么样使用优先级和抢占

想要在 Kubernetes 1.8 版本中使用优先级和抢占,请参考如下步骤:

  1. 启用功能。
  2. 增加一个或者多个 PriorityClass。
  3. 创建拥有字段 PriorityClassName 的 Pod,该字段的值选取上面增加的 PriorityClass。当然,您没有必要直接创建 pod,通常您可以把 PriorityClassName 增加到类似 Deployment 这样的集合对象的 Pod 模板中。

以下章节提供了有关这些步骤的详细信息。

启用优先级和抢占

Kubernetes 1.8 版本默认没有开启 Pod 优先级和抢占。为了启用该功能,需要在 API server 和 scheduler 的启动参数中设置:

--feature-gates=PodPriority=true

在 API server 中还需要设置如下启动参数:

--runtime-config=scheduling.k8s.io/v1alpha1=true

功能启用后,您能创建 PriorityClass,也能创建使用 PriorityClassName 集的 Pod。

如果在尝试该功能后想要关闭它,那么您可以把 PodPriority 这个命令行标识从启动参数中移除,或者将它的值设置为false,然后再重启 API server 和 scheduler。功能关闭后,原来的 Pod 会保留它们的优先级字段,但是优先级字段的内容会被忽略,抢占不会生效,在新的 pod 创建时,您也不能设置 PriorityClassName。

PriorityClass

PriorityClass 是一个不受命名空间约束的对象,它定义了优先级类名跟优先级整数值的映射。它的名称通过 PriorityClass 对象 metadata 中的 name 字段指定。值在必选的 value 字段中指定。值越大,优先级越高。

PriorityClass 对象的值可以是小于或者等于 10 亿的 32 位任意整数值。更大的数值被保留给那些通常不应该取代或者驱逐的关键的系统级 Pod 使用。集群管理员应该为它们想要的每个此类映射创建一个 PriorityClass 对象。

PriorityClass 还有两个可选的字段:globalDefault 和 description。globalDefault 表示 PriorityClass 的值应该给那些没有设置 PriorityClassName 的 Pod 使用。整个系统只能存在一个 globalDefault 设置为 true 的 PriorityClass。如果没有任何 globalDefault 为 true 的 PriorityClass 存在,那么,那些没有设置 PriorityClassName 的 Pod 的优先级将为 0。

description 字段的值可以是任意的字符串。它向所有集群用户描述应该在什么时候使用这个 PriorityClass。

注1:如果您升级已经存在的集群环境,并且启用了该功能,那么,那些已经存在系统里面的 Pod 的优先级将会设置为 0。

注2:此外,将一个 PriorityClass 的 globalDefault 设置为 true,不会改变系统中已经存在的 Pod 的优先级。也就是说,PriorityClass 的值只能用于在 PriorityClass 添加之后创建的那些 Pod 当中。

注3:如果您删除一个 PriorityClass,那些使用了该 PriorityClass 的 Pod 将会保持不变,但是,该 PriorityClass 的名称不能在新创建的 Pod 里面使用。

PriorityClass 示例

apiVersion: v1
kind: PriorityClass
metadata:
  name: high-priority
value: 1000000
globalDefault: false
description: "This priority class should be used for XYZ service pods only."

Pod priority

有了一个或者多个 PriorityClass 之后,您在创建 Pod 时就能在模板文件中指定需要使用的 PriorityClass 的名称。优先级准入控制器通过 priorityClassName 字段查找优先级数值并且填入 Pod 中。如果没有找到相应的 PriorityClass,Pod 将会被拒绝创建。

下面的 YAML 是一个使用了前面创建的 PriorityClass 对 Pod 进行配置的示例。优先级准入控制器会检测配置文件,并将该 Pod 的优先级解析为 1000000。

apiVersion: v1
kind: Pod
metadata:
  name: nginx
  labels:
    env: test
spec:
  containers:
  - name: nginx
    image: nginx
    imagePullPolicy: IfNotPresent
  priorityClassName: high-priority

抢占

Pod 生成后,会进入一个队列等待调度。scheduler 从队列中选择一个 Pod,然后尝试将其调度到某个节点上。如果没有任何节点能够满足 Pod 指定的所有要求,对于这个挂起的 Pod,抢占逻辑就会被触发。当前假设我们把挂起的 Pod 称之为 P。抢占逻辑会尝试查找一个节点,在该节点上移除一个或多个比 P 优先级低的 Pod 后, P 能够调度到这个节点上。如果节点找到了,部分优先级低的 Pod 就会从该节点删除。Pod 消失后,P 就能被调度到这个节点上了。

限制抢占(alpha 版本)

饥饿式抢占

Pod 被抢占时,受害者(被抢占的 Pod)会有 优雅终止期。他们有大量的时间完成工作并退出。如果他们不这么做,就会被强行杀死。这个优雅中止期在调度抢占 Pod 以及挂起的 Pod(P)能够被调度到节点(N)之间形成了一个时间间隔。在此期间,调度会继续对其它挂起的 Pod 进行调度。当受害者退出或者终止的时候,scheduler 尝试调度挂起队列中的 Pod,在 scheduler 正式把 Pod P 调度到节点 N 之前,会继续考虑把其它 Pod 调度到节点 N 上。这种情况下,当所有受害者退出时,很有可能 Pod P 已经不再适合于节点 N。因此,scheduler 将不得不抢占节点 N 上的其它 Pod,或者抢占其它节点,以便 P 能被调度。这种情况可能会在第二轮和随后的抢占回合中再次重复,而 P 可能在一段时间内得不到调度。这种场景可能会导致各种集群中的问题,特别是在具有高 Pod 创建率的集群中。

我们将在 Pod 抢占的 beta 版本解决这个问题。计划的解决方案可以在 这里 找到。

PodDisruptionBudget is not supported

Pod 破坏预算(Pod Disruption Budget,PDB) 允许应用程序所有者在自愿中断应用的同时限制应用副本的数量。然而,抢占的 alpha 版本在选择抢占受害者时,并没有遵循 PDB。我们计划在 beta 版本增加对 PDB 遵循的支持,但即使是在 beta 版本,也只能做到尽力支持。scheduler 将会试图查找那些不会违反 PDB 的受害者,如果这样的受害者没有找到,抢占依然会发生,即便违反了 PDB,这些低优先级的 Pod 仍将被删除。

低优先级 Pod 之间的亲和性

在版本1.8中,只有当这个问题的答案是肯定的时候才考虑一个节点使用抢占:“如果优先级低于挂起的 Pod 的所有 Pod 从节点中移除后,挂起的 Pod 是否能够被调度到该节点上?”

注: 抢占没有必要移除所有低优先级的 Pod。如果在不移除所有低优先级的 Pod 的情况下,挂起的 Pod 就能调度到节点上,那么就只需要移除部分低优先级的 Pod。即便如此,上述问题的答案还需要是肯定的。如果答案是否定的,抢占功能不会考虑该节点。

如果挂起的 Pod 对节点上的一个或多个较低优先级的 Pod 具有亲和性,那么在没有那些较低优先级的 Pod 的情况下,无法满足 Pod 关联规则。这种情况下,scheduler 不抢占节点上的任何 Pod。它会去查找另外的节点。scheduler 有可能会找到合适的节点,也有可能无法找到,因此挂起的 Pod 并不能保证都能被调度。

我们可能会在未来的版本中解决这个问题,但目前还没有一个明确的计划。我们也不会因为它而对 beta 或者 GA 版本的推进有所阻滞。部分原因是,要查找满足 Pod 亲和性规则的低优先级 Pod 集的计算过程非常昂贵,并且抢占过程也增加了大量复杂的逻辑。此外,即便在抢占过程中保留了这些低优先级的 Pod,从而满足了 Pod 间的亲和性,这些低优先级的 Pod 也可能会在后面被其它 Pod 给抢占掉,这就抵消了遵循 Pod 亲和性的复杂逻辑带来的好处。

对于这个问题,我们推荐的解决方案是:对于 Pod 亲和性,只跟相同或者更高优先级的 Pod 之间进行创建。

跨节点抢占

假定节点 N 启用了抢占功能,以便我们能够把挂起的 Pod P 调度到节点 N 上。只有其它节点的 Pod 被抢占时,P 才有可能被调度到节点 N 上面。下面是一个示例:

  • Pod P 正在考虑节点 N。
  • Pod Q 正运行在跟节点 N 同区的另外一个节点上。
  • Pod P 跟 Pod Q 之间有反亲和性。
  • 在这个区域内没有跟 Pod P 具备反亲和性的其它 Pod。
  • 为了将 Pod P 调度到节点 N 上,Pod Q 需要被抢占掉,但是 scheduler 不能执行跨节点的抢占。因此,节点 N 将被视为不可调度节点。

如果将 Pod Q 从它的节点移除,反亲和性随之消失,那么 Pod P 就有可能被调度到节点 N 上。

如果找到一个性能合理的算法,我们可以考虑在将来的版本中增加跨节点抢占。在这一点上,我们不能承诺任何东西,beta 或者 GA 版本也不会因为跨节点抢占功能而有所阻滞。

译者:chentao1596 原文链接

K8S中文社区微信公众号

Kubernetes 使用 Kubefed 创建集群联邦

Kubernetes 的1.5及以上版本提供了一个命令行工具kubefed , 用于管理用户的集群联邦。kubefed 可以帮助你部署一个集群联邦的控制面板,您可以通过 这个面板来添加或者删除一个联邦里面的集群。

这篇教程指导如何使用 kubefed 来管理一个 Kubernetes 集群联邦。

注意: kubefed 在 Kubernetes 1.6版本中仍然是一个 beta 功能.

前提要求

这篇教程假设您已经有了正常运行的 Kubernetes 集群。如果需要在您的平台 上部署集群,请查阅文档getting started.

安装 kubefed

使用下列命令下载对应最新发行的客户端安装包并将安装包里的二进制文件解压出来:

# Linux
curl -LO https://storage.googleapis.com/kubernetes-release/release/$(curl -s https://storage.googleapis.com/kubernetes-release/release/stable.txt)/kubernetes-client-linux-amd64.tar.gz
tar -xzvf kubernetes-client-linux-amd64.tar.gz

# OS X
curl -LO https://storage.googleapis.com/kubernetes-release/release/$(curl -s https://storage.googleapis.com/kubernetes-release/release/stable.txt)/kubernetes-client-darwin-amd64.tar.gz
tar -xzvf kubernetes-client-darwin-amd64.tar.gz

# Windows
curl -LO https://storage.googleapis.com/kubernetes-release/release/$(curl -s https://storage.googleapis.com/kubernetes-release/release/stable.txt)/kubernetes-client-windows-amd64.tar.gz
tar -xzvf kubernetes-client-windows-amd64.tar.gz

注意: 上述命令里的 URL 提供的都是适合 amd64 架构的包,如果您需要其他架构的 包,请更换为对应的 URL ,在这里列出了所有可用的发行版本, 发布页面.

将解压出来的内容复制到你的环境变量 $PATH 里的随便一个路径, 并设置可执行权限。

sudo cp kubernetes/client/bin/kubefed /usr/local/bin
sudo chmod +x /usr/local/bin/kubefed
sudo cp kubernetes/client/bin/kubectl /usr/local/bin
sudo chmod +x /usr/local/bin/kubectl

在 Ubuntu 上使用 snap 安装

kubefed 也提供了可用的 snap 软件包。

  1. 如果您使用的是 Ubuntu 或者其他支持 snap 包管理器的 Linux 发现版本,可以使用下列命令安装:
    sudo snap install kubefed --classic
    
  2. 运行 kubefed version 来验证您安装的版本是不是最新的。

选择一个主集群

您将需要选择您其中的一个集群作为主集群,这个主集群将运行组成联邦控制面板 的所有组件。确保在您本地的 kubeconfig 里有一个对应您的主集群的 kubeconfig 条目。可以使用下列命令来验证是否有需求的 kubeconfig 条目:

kubectl config get-contexts

输出里必须有一个条目对应您的主集群,类似下面的内容:

CURRENT   NAME                                          CLUSTER                                       AUTHINFO                                      NAMESPACE
*         gke_myproject_asia-east1-b_gce-asia-east1     gke_myproject_asia-east1-b_gce-asia-east1     gke_myproject_asia-east1-b_gce-asia-east1

当您部署联邦集群控制面板时,您将需要提供主集群的 kubeconfig 内容(就是上面条目对应的 name ) 。

部署一个联邦控制面板

想要在你的主集群上部署联邦控制面板,运行 kubefed init 。 使用 kubefed init 时,需要提供以下参数:

  • 联邦名字
  • --host-cluster-context, 主集群的 kubeconfig 内容
  • --dns-provider, 可选 'google-clouddns', aws-route53 或者 coredns
  • --dns-zone-name, 联邦服务的域名后缀

如果您的主集群不是运行在一个云的环境,或者是这个环境不支持常见的云功能,比如负载均衡, 那您可能还需要提供其他的参数。请查阅下面的内容 on-premises 主集群 。

下面的命令部署了一个联邦集群,名称为 fellowship,主集群上下 文(host cluster context)为 rivendell,域名后缀为 example.com.:

kubefed init fellowship \
    --host-cluster-context=rivendell \
    --dns-provider="google-clouddns" \
    --dns-zone-name="example.com."

--dns-zone-name 定义的联邦集群的域名后缀必须是一个属于您的已存在的域名, 而且必须是受您的 DNS 提供商所管理的,结尾必须有个点号。

等联邦控制面板初始化完毕,查询 namespace :

kubectl get namespace --context=fellowship

如果没有列出来名字为 default 的 namespace (这是因为一个 Bug bug). 请使用下列命令自己创建一个:

kubectl create namespace default --context=fellowship

您的主集群里的节点必须有足够的权限来管理您所使用的 DNS 服务,比如说, 如果您使用的集群是运行在 Google Compute Engine 上面,您必须启用 Google Cloud DNS API。

默认情况下,Google Container Engine (GKE) 集群里的节点创建时是不启用 Google Cloud DNS API 的, 如果您需要使用一个 GKE 集群作为联邦主集群,请在创建的时候使用 gcloud和正确的 --scopes 标签。您无法修改一个 GKE 集群来直接添加这个 scope ,但是可以创建一个新的节点群并删除旧的节点。 注意 这样会导致集群里的 Pod 被重新调度。

添加新的节点群,请运行下列命令:

scopes="$(gcloud container node-pools describe --cluster=gke-cluster default-pool --format='value[delimiter=","](config.oauthScopes)')"
gcloud container node-pools create new-np \
    --cluster=gke-cluster \
    --scopes="${scopes},https://www.googleapis.com/auth/ndev.clouddns.readwrite"

删除旧的节点群,请运行:

gcloud container node-pools delete default-pool --cluster gke-cluster

kubefed init 在主集群里配置联邦控制面板,并在您本地的 kubeconfig 添加联邦 API 服务的 配置条目。注意,在 Kubernetes 1.6 beta 发行版本中,kubefed init 并不会自动将新部署的集群联邦的 上下文配置为当前的内容, 因此您需要手动配置,运行下面的命令:

kubectl config use-context fellowship

在这里 fellowship 是您的联邦名字。

基本和令牌验证支持

kubefed init 默认只会用于联邦 API 服务验证的 TLS 证书和密钥, 并写入到本地的 kubeconfig 文件里面。如果您需要 debug 而启用基本验证 或者令牌验证,您可以通过传递 --apiserver-enable-basic-auth 或者 --apiserver-enable-token-auth 标签来实现。

kubefed init fellowship \
    --host-cluster-context=rivendell \
    --dns-provider="google-clouddns" \
    --dns-zone-name="example.com." \
    --apiserver-enable-basic-auth=true \
    --apiserver-enable-token-auth=true

给联邦组件传递命令行参数

kubefed init 使用了默认参数配置联邦 API 服务和联邦控制管理服务,从而部署了 一个联邦控制管理面板。而其中的一些参数是衍生自 kubefed init 的标签。 然而用户也可以自己通过对应的标签来定义这些参数。

您即可以使用--apiserver-arg-overrides 这个标签来定义联邦 API 服务的参数, 也可以使用--controllermanager-arg-overrides 来定义联邦控制管理服务的参数。

kubefed init fellowship \
    --host-cluster-context=rivendell \
    --dns-provider="google-clouddns" \
    --dns-zone-name="example.com." \
    --apiserver-arg-overrides="--anonymous-auth=false,--v=4" \
    --controllermanager-arg-overrides="--controllers=services=false"

配置一个 DNS 服务提供商

联邦管理服务会使用 DNS 来通过域名开放联邦服务。有些云服务提供商会 自动提供所需配置,前提是主集群的云提供商跟所使用的 DNS 服务提供商是 同一家。如果不是这种情况的话,您就需要给联邦管理控制器提供 DNS 配置信 息,而反过来,这个配置信息也会传递给联邦管理服务。可以把配置信息保存 在文件里,然后通过文件的本地文件系统路径传递 给 kubefed init 的 --dns-provider-config 标签来向联邦管理控制器 提供配置。比如,将配置保存在 $HOME/coredns-provider.conf 。

[Global]
etcd-endpoints = http://etcd-cluster.ns:2379
zones = example.com.

然后将这个文件路径传递给 kubefed init:

kubefed init fellowship \
    --host-cluster-context=rivendell \
    --dns-provider="coredns" \
    --dns-zone-name="example.com." \
    --dns-provider-config="$HOME/coredns-provider.conf"

On-premises 主集群

API 服务类型

kubefed init 在主集群上以 Kubernetes 服务 的方式开放联邦的 API 服务。默认情况下,这个服务是作为负载均衡服务. 大部分 on-premises 和 bare-metal 的环境和一些云环境,都缺乏负载均衡服务。 因此 kubefed init 允许将联邦的 API 服务作为NodePort 服务 在这样的环境里开放出来。这可以通过传递 --api-server-service-type=NodePort 标签来实现。 您也可以传递 --api-server-advertise-address=<IP-address> 来指定公开的联邦 API 服务的地址。 否则,主集群上的其中一个节点地址将会被作为默认地址。

kubefed init fellowship \
    --host-cluster-context=rivendell \
    --dns-provider="google-clouddns" \
    --dns-zone-name="example.com." \
    --api-server-service-type="NodePort" \
    --api-server-advertise-address="10.0.10.20"

给 etcd 提供存储

联邦控制面板将它的数据存放在 etcd. 而etcd 的数据必须存放在一个PersistentVolume里 才能确保在联邦控制面板重启之后能提供正确的操作。在支持 动态分配存储卷的主集群上, kubefed init 动态分配一个 PersistentVolume 并绑定到一个 PersistentVolumeClaim 用于存储 etcd 的数据。如果您的主集群不支持动态分配, 您可以固定的分配一个 PersistentVolume. kubefed init 创建一个有下面的配置的 PersistentVolumeClaim:

apiVersion: v1
kind: PersistentVolumeClaim
metadata:
  annotations:
    volume.alpha.kubernetes.io/storage-class: "yes"
  labels:
    app: federated-cluster
  name: fellowship-federation-apiserver-etcd-claim
  namespace: federation-system
spec:
  accessModes:
  - ReadWriteOnce
  resources:
    requests:
      storage: 10Gi

想要固定的分配一个 PersistentVolume, 您就必须确保您所创建的 PersistentVolume 有正确的存储类型,访问模式和 PersistentVolumeClaim 所需要的存储空间。

或者,您也可以通过给 kubefed init 传递标签 --etcd-persistent-storage=false 来完全的禁止永久存储。然而,我们并不建议您这么做,因为这样的话,您的联邦控制面板 重启之后将无法正常工作。

kubefed init fellowship \
    --host-cluster-context=rivendell \
    --dns-provider="google-clouddns" \
    --dns-zone-name="example.com." \
    --etcd-persistent-storage=false

kubefed init 仍然不支持往一个已建立的联邦控制面板连接一个已存在的 PersistentVolumeClaim。 我们计划在将来的 kubefed 版本提供这方面的支持。

CoreDNS 支持

联邦服务现在支持 CoreDNS 作为 DNS 提供商, 如果您现在的集群或者联邦集群的环境不支持基于云的 DNS 服务,那您可以 运行您自己的 CoreDNS 实例并将公布的联邦 DNS 服务指向该节点。

想要配置联邦集群使用 CoreDNS, 只需要给 kubefed init 的标签 --dns-provider 和 --dns-provider-config 配置相应的值就可以了。

kubefed init fellowship \
    --host-cluster-context=rivendell \
    --dns-provider="coredns" \
    --dns-zone-name="example.com." \
    --dns-provider-config="$HOME/coredns-provider.conf"

更多信息请查看 给联邦集群搭建 CoreDNS 作为 DNS 服务提供.

往联邦添加集群

一旦您部署成功一个联邦控制面板,您就需要让控制面板知道需要管理哪些集群。 因此您可以使用 kubefed join 命令往控制面板 添加集群。

要使用 kubefed join, 您需要提供集群的名字和--host-cluster-context 指定的联邦控制面板的主集群。

注意: 您在使用 join 命令时使用的名字将会作为待添加集群在这个联邦里的 标识。这个名字必须符合这篇文章所描述的规则 标识符文档. 如果您的待添加集群的 context 符合这个规则,您可以在 join 命令里使用相同的名字。否则,您将需要使用一个不同 的名字作为集群的标识。更多信息请查阅 命名规则和自定义。

下面的命令将名字为 gondor 的集群添加到运行在主集群 rivendell 上面 的联邦集群里:

kubefed join gondor --host-cluster-context=rivendell

注意: Kubernetes 要求您手动添加集群到联邦里面,因为联邦控制面板只管理 那些可响应的集群,添加集群就会告诉联邦控制面板,这个被添加的集群是可响应的, 以便联邦管理。

命名规则和自定义

您提供给 kubefed join 的集群名字必须是一个有效的 RFC 1035 标签而且是符合 标识符文档所列举的规范.

而且,联邦控制面板需要有被添加集群的验证信息以便管理。这些验证信息 是从本地的 kubeconfig 获取的。kubefed join 使用这个集群的名字作为 参数在本地的 kubeconfig 里查找集群的信息。如果找不到匹配的集群验证信息, 它就会报错并退出。

如果联邦里的集群名字不遵循RFC 1035 标签命名规则,这可能会造成错误。如果是这样的话,您可以通过给 --cluster-context 标签指定一个符合RFC 1035标签命名规则的名字。 比如说,如果你要添加的集群的 context 为gondor_needs-no_king , 那可以这样添加 这个集群:

kubefed join gondor --host-cluster-context=rivendell --cluster-context=gondor_needs-no_king

Secret 命名

上面描述的联邦控制面板需要的集群验证信息,会作为 secret 保存在主集群里。 而这个 secret 的名字就衍生自这个集群的名字。

然后,Kubernetes 里的 secret 对象命名,必须遵从这个文档 RFC 1123 , 所描述的 DNS 子域名的命名规则。如果不是这样的话,您可以将 secret 名字使用 --secret-name 的标签, 传递给 kubefed join 。 比如说,如果集群名字是 noldor , 而 secret 名字是11kingdom , 您可以这样添加这个集群:

kubefed join noldor --host-cluster-context=rivendell --secret-name=11kingdom

注意: 如果您的集群名字并不符合 DNS 子域名的命名规则,您所需要做的只是通过 --secret-name 标签, 来提供这个 secret 的名字而已。kubefed join 会自动为您创建这个 secret .

kube-dns 配置

每个被添加的集群里的 kube-dns 的配置必需更新,以便启用联邦服务发现功能。 如果这个被添加的集群是1.5或者更高的版本,而您的 kubefed 是1.6或者更新, 那这个配置在集群被添加时或者使用 kubefed join 或 unjoin 这样的命令的时候, 会自动更新。

除此之外,您都必须更新 kube-dns 的配置,详情请查阅 更新管理指南中的 KubeDNS 章节.

从联邦里移除一个集群

要从联邦里移除一个集群,执行命令 kubefed unjoin 并使用联邦的标签 --host-cluster-context 和集群的名字:

kubefed unjoin gondor --host-cluster-context=rivendell

清除联邦控制面板

在目前的 kubefed beta 版本里并未完全实现对联邦控制面板的彻底清理。 然而,目前而言,删除联邦系统对应的 namespace 会删除所有的资源,除了自动分配 给联邦集群的 etcd 服务的永久存储。您可以这样删除联邦的 namespace :

kubectl delete ns federation-system
K8S中文社区微信公众号

将 kubeadm 集群从 1.7 升级到 1.8

本指南用于指导如何将 kubeadm 集群从 1.7.x 版本升级到 1.8.x 版本,也可用于从 1.7.x 到 1.7.y 及从 1.8.x 到 1.8.y,其中 y > x。 如果您当前使用 1.6 版本的集群,请查看 将 kubeadm 集群从 1.6 升级到 1.7

Before you begin

在开始前:

  • 您需要有一个正常工作的 1.7.0 或更高版本的 kubeadm Kubernetes 集群,以进行此处描述的流程。
  • 请确保已经仔细阅读 版本更新
  • 由于 kubeadm upgrade 不会升级 etcd,请确保已对其进行了备份。例如,您可以使用 etcdctl backup 命令完成这个工作。
  • 请注意,kubeadm upgrade 只会升级 Kubernetes 内建(Kubernetes-internal)组件,不会触及任何工作负载。作为最佳实践,您应该备份所有重要数据。例如任何应用层级的状态数据,如应用可能依赖的数据库(如 MySQL 或 MongoDB)等,在开始升级前必须对其进行备份。

此外,请注意升级仅支持一个小版本号。也就是说,您只能从 1.7 升级到 1.8 而不能从 1.7 升级到 1.9。

升级控制平面(control plane)

您需要在 master 节点上执行这些步骤:

  1. 像这样使用 curl 安装最新版本的 kubeadm:
$ export VERSION=$(curl -sSL https://dl.k8s.io/release/stable.txt) # or manually specify a released Kubernetes version
$ export ARCH=amd64 # or: arm, arm64, ppc64le, s390x
$ curl -sSL https://dl.k8s.io/release/${VERSION}/bin/linux/${ARCH}/kubeadm > /usr/bin/kubeadm
$ chmod a+rx /usr/bin/kubeadm

警示:升级控制平面前在系统上升级 kubeadm 包将导致升级失败。即使 kubeadm 已经放入 Kubernetes 仓库中,您仍应该手动安装它。Kubeadm 团队正在修复这个限制。

验证下载的 kubeadm 是否工作正常,是否为预期的版本:

$ kubeadm version
  1. 如果这是您第一次使用 kubeadm upgrade,为了保存配置文件以便用于以后的升级,请执行:

请注意,下列命令的运行需要您回顾首次运行 kubeadm init 时传递的参数。

如果您使用过标志,请执行:

$ kubeadm config upload from-flags [flags]

这里的 flags 可以为空。

如果您使用的是配置文件,请执行:

$ kubeadm config upload from-file --config [config]

这里的 config 是必须的。

  1. 在 master 节点上执行下列步骤:
$ kubeadm upgrade plan
[preflight] Running pre-flight checks
[upgrade] Making sure the cluster is healthy:
[upgrade/health] Checking API Server health: Healthy
[upgrade/health] Checking Node health: All Nodes are healthy
[upgrade/health] Checking Static Pod manifests exists on disk: All manifests exist on disk
[upgrade/config] Making sure the configuration is correct:
[upgrade/config] Reading configuration from the cluster...
[upgrade/config] FYI: You can look at this config file with 'kubectl -n kube-system get cm kubeadm-config -o yaml'
[upgrade] Fetching available versions to upgrade to:
[upgrade/versions] Cluster version: v1.7.1
[upgrade/versions] kubeadm version: v1.8.0
[upgrade/versions] Latest stable version: v1.8.0
[upgrade/versions] Latest version in the v1.7 series: v1.7.6

Components that must be upgraded manually after you've upgraded the control plane with 'kubeadm upgrade apply':
COMPONENT   CURRENT      AVAILABLE
Kubelet     1 x v1.7.1   v1.7.6

Upgrade to the latest version in the v1.7 series:

COMPONENT            CURRENT   AVAILABLE
API Server           v1.7.1    v1.7.6
Controller Manager   v1.7.1    v1.7.6
Scheduler            v1.7.1    v1.7.6
Kube Proxy           v1.7.1    v1.7.6
Kube DNS             1.14.4    1.14.4

You can now apply the upgrade by executing the following command:

	kubeadm upgrade apply v1.7.6

_____________________________________________________________________

Components that must be upgraded manually after you've upgraded the control plane with 'kubeadm upgrade apply':
COMPONENT   CURRENT      AVAILABLE
Kubelet     1 x v1.7.1   v1.8.0

Upgrade to the latest experimental version:

COMPONENT            CURRENT   AVAILABLE
API Server           v1.7.1    v1.8.0
Controller Manager   v1.7.1    v1.8.0
Scheduler            v1.7.1    v1.8.0
Kube Proxy           v1.7.1    v1.8.0
Kube DNS             1.14.4    1.14.4

You can now apply the upgrade by executing the following command:

	kubeadm upgrade apply v1.8.0

Note: Before you do can perform this upgrade, you have to update kubeadm to v1.8.0

_____________________________________________________________________

kubeadm upgrade plan 将检查您的集群是否处于可升级状态,并以用户友好的方式获取可升级的版本。

  1. 选择一个版本进行升级,例如执行下面的 kubeadm upgrade apply:
$ kubeadm upgrade apply v1.8.0
[preflight] Running pre-flight checks
[upgrade] Making sure the cluster is healthy:
[upgrade/health] Checking API Server health: Healthy
[upgrade/health] Checking Node health: All Nodes are healthy
[upgrade/health] Checking Static Pod manifests exists on disk: All manifests exist on disk
[upgrade/config] Making sure the configuration is correct:
[upgrade/config] Reading configuration from the cluster...
[upgrade/config] FYI: You can look at this config file with 'kubectl -n kube-system get cm kubeadm-config -o yaml'
[upgrade/version] You have chosen to upgrade to version "v1.8.0"
[upgrade/versions] Cluster version: v1.7.1
[upgrade/versions] kubeadm version: v1.8.0
[upgrade/prepull] Will prepull images for components [kube-apiserver kube-controller-manager kube-scheduler]
[upgrade/prepull] Prepulling image for component kube-scheduler.
[upgrade/prepull] Prepulling image for component kube-apiserver.
[upgrade/prepull] Prepulling image for component kube-controller-manager.
[apiclient] Found 0 Pods for label selector k8s-app=upgrade-prepull-kube-scheduler
[apiclient] Found 1 Pods for label selector k8s-app=upgrade-prepull-kube-scheduler
[apiclient] Found 1 Pods for label selector k8s-app=upgrade-prepull-kube-apiserver
[apiclient] Found 1 Pods for label selector k8s-app=upgrade-prepull-kube-controller-manager
[upgrade/prepull] Prepulled image for component kube-apiserver.
[upgrade/prepull] Prepulled image for component kube-controller-manager.
[upgrade/prepull] Prepulled image for component kube-scheduler.
[upgrade/prepull] Successfully prepulled the images for all the control plane components
[upgrade/apply] Upgrading your Static Pod-hosted control plane to version "v1.8.0"...
[upgrade/staticpods] Writing upgraded Static Pod manifests to "/etc/kubernetes/tmp/kubeadm-upgraded-manifests432902769"
[controlplane] Wrote Static Pod manifest for component kube-apiserver to "/etc/kubernetes/tmp/kubeadm-upgraded-manifests432902769/kube-apiserver.yaml"
[controlplane] Wrote Static Pod manifest for component kube-controller-manager to "/etc/kubernetes/tmp/kubeadm-upgraded-manifests432902769/kube-controller-manager.yaml"
[controlplane] Wrote Static Pod manifest for component kube-scheduler to "/etc/kubernetes/tmp/kubeadm-upgraded-manifests432902769/kube-scheduler.yaml"
[upgrade/staticpods] Moved upgraded manifest to "/etc/kubernetes/manifests/kube-apiserver.yaml" and backed up old manifest to "/etc/kubernetes/tmp/kubeadm-backup-manifests155856668/kube-apiserver.yaml"
[upgrade/staticpods] Waiting for the kubelet to restart the component
[apiclient] Found 1 Pods for label selector component=kube-apiserver
[upgrade/staticpods] Component "kube-apiserver" upgraded successfully!
[upgrade/staticpods] Moved upgraded manifest to "/etc/kubernetes/manifests/kube-controller-manager.yaml" and backed up old manifest to "/etc/kubernetes/tmp/kubeadm-backup-manifests155856668/kube-controller-manager.yaml"
[upgrade/staticpods] Waiting for the kubelet to restart the component
[apiclient] Found 1 Pods for label selector component=kube-controller-manager
[upgrade/staticpods] Component "kube-controller-manager" upgraded successfully!
[upgrade/staticpods] Moved upgraded manifest to "/etc/kubernetes/manifests/kube-scheduler.yaml" and backed up old manifest to "/etc/kubernetes/tmp/kubeadm-backup-manifests155856668/kube-scheduler.yaml"
[upgrade/staticpods] Waiting for the kubelet to restart the component
[apiclient] Found 1 Pods for label selector component=kube-scheduler
[upgrade/staticpods] Component "kube-scheduler" upgraded successfully!
[uploadconfig] Storing the configuration used in ConfigMap "kubeadm-config" in the "kube-system" Namespace
[bootstraptoken] Configured RBAC rules to allow Node Bootstrap tokens to post CSRs in order for nodes to get long term certificate credentials
[bootstraptoken] Configured RBAC rules to allow the csrapprover controller automatically approve CSRs from a Node Bootstrap Token
[addons] Applied essential addon: kube-dns
[addons] Applied essential addon: kube-proxy

[upgrade/successful] SUCCESS! Your cluster was upgraded to "v1.8.0". Enjoy!

[upgrade/kubelet] Now that your control plane is upgraded, please proceed with upgrading your kubelets in turn.

kubeadm upgrade apply 将执行下列步骤:

  • 检查集群是否处于可升级状态,包括:
    • API Server 是否可达,
    • 所有节点是否均处于 Ready 状态,并且
    • 控制平面处于健康状态
  • 强制启用版本偏移策略(version skew policy)。
  • 保证控制平面镜像可用或可以拉取到机器上。
  • 升级控制平面组件,当任何一个组件启动失败时对升级操作进行回退。
  • 应用新的 kube-dns 和 kube-proxy 清单文件并强制启用所有创建的必要 RBAC 规则。
  1. 手动升级软件定义网络(Software Defined Network,SDN)。当前您的容器网络接口提供商(Container Network Interface,CNI)可能有自己的升级指导。请查阅 插件 页面,找到您的 CNI 提供商并查看是否有必要的额外升级步骤。
  2. 为自动证书轮换添加必要的 RBAC 权限。将来 kubeadm 将自动执行这个步骤。
$ kubectl create clusterrolebinding kubeadm:node-autoapprove-certificate-rotation --clusterrole=system:certificates.k8s.io:certificatesigningrequests:selfnodeclient --group=system:nodes

升级 master 和 node 软件包

对于集群中的每个节点(以下称为 $HOST),请运行下列命令升级其 kubelet。

  1. 准备节点以进行维护,将其标记为不可调度并移除工作负载:
$ kubectl drain $HOST --ignore-daemonsets

在 master 节点执行这个命令时,预计会出现这个错误,并且可以安全地将其忽略(因为 master 节点上有 static pod 运行):

node "master" already cordoned
error: pods not managed by ReplicationController, ReplicaSet, Job, DaemonSet or StatefulSet (use --force to override): etcd-kubeadm, kube-apiserver-kubeadm, kube-controller-manager-kubeadm, kube-scheduler-kubeadm
  1. 使用 Linux 发行版特定的包管理器升级 $HOST 节点上的 Kubernetes 软件包版本:

如果节点运行基于 Debian 的发行版(如 Ubuntu),请执行:

$ apt-get update
$ apt-get upgrade

如果节点运行 CentOS 或类似发行版,请执行:

$ yum update

现在,节点上应该运行的是新版本的 kubelet。请在 $HOST 上执行下列命令对此进行验证:

$ systemctl status kubelet
  1. 将节点标记为可调度(schedulable)以使其上线:
$ kubectl uncordon $HOST
  1. 在对所有集群节点的 kubelet 进行升级之后,请执行以下命令以确认所有节点又重新变为可用状态(从任何地方,例如集群外部):
$ kubectl get nodes

如果上述命令结果中所有节点的 STATUS 列都显示为 Ready,升级工作就已成功完成。

从损坏状态恢复

如果 kubeadm upgrade 因某些原因失败并且不能回退(可能因为执行过程中意外的关闭了节点实例),您可以再次运行 kubeadm upgrade,因为其具有幂等性,所以最终应该能够保证集群的实际状态和您所定义的理想状态一致。

您可以使用 kubeadm upgrade 命令和 x.x.x –> x.x.x 及 –force 参数,以从损坏状态恢复。

译者:xiaosuiba 原文链接

K8S中文社区微信公众号

将 kubeadm 集群从 1.6 升级到 1.7

本指南用于将kubeadm集群从1.6.x升级到1.7.x。升级操作不支持低于 1.6 版本的集群,kubeadm 在 1.6 成为 Beta 版本。

警告:这些指令将覆盖所有 kubeadm 管理的资源(静态 pod 清单文件、kube-system 命名空间中的 service account 和 RBAC 规则等。),因此,对于在集群设置之后进行的资源定制化,在升级之后需要重新应用。升级不会干扰 kube-system 命名空间之外的其它静态 pod 清单文件或对象。

Before you begin

您需要运行版本为 1.6.x 的 Kubernetes 集群。

在 master 上

  1. 升级系统包。更新 kubectl、kubeadm、kubelet 和 kubernetes-cni 的系统包。

    a. 在 Debian 上这样完成:

    sudo apt-get update
    sudo apt-get upgrade
    

    b. 在 CentOS/Fedora 上则运行:

    sudo yum update
    
  2. 重启 kubelet。
    systemctl restart kubelet
    
  3. 删除 kube-proxy DaemonSet。虽然这个步骤自动升级了大部分组件,但当前仍需要手动删除 kube-proxy 以使其可以使用正确的版本重建:
    sudo KUBECONFIG=/etc/kubernetes/admin.conf kubectl delete daemonset kube-proxy -n kube-system
    
  4. 执行 kubeadm 升级。警告:当引导集群时,所有传递给第一个 kubeadm init 的参数都必须在用于升级的 kubeadm init 命令中指定。我们计划在 v1.8 引入这个限制。
    sudo kubeadm init --skip-preflight-checks --kubernetes-version <DESIRED_VERSION>
    

    例如,如果要升级到 1.7.0,可以运行:

    sudo kubeadm init --skip-preflight-checks --kubernetes-version v1.7.0
    
  5. 升级 CNI provider。您的 CNI provider 现在可能有它自己升级说明。检查 addons 页面,找到您的 CNI provider 并查看是否有必要的额外升级步骤。

在每个 node 上

  1. 升级系统包。更新 kubectl、kubeadm、kubelet 和 kubernetes-cni 的系统包。

    a. 在 Debian 上这样完成:

    sudo apt-get update
    sudo apt-get upgrade
    

    b. 在 CentOS/Fedora 上则运行:

    sudo yum update
    
  2. 重启 kubelet。
    systemctl restart kubelet

译者:xiaosuiba 原文链接

K8S中文社区微信公众号