确保Kubernetes部署已完成,所有pod都已更新并可用

时间:2016-05-25 22:00:22

标签: bash kubernetes

The status of a deployment表示您可以查看部署observedGeneration vs generation,以及observedGeneration >= generation时部署成功。这没关系,但我有兴趣知道新容器何时实际运行在所有我的pod中,所以如果我点击服务我肯定知道我&#39 ;击中代表最新部署容器的服务器。

来自K8S Slack成员的另一个提示:

kubectl get deployments | grep <deployment-name> | sed 's/ /,/g' | cut -d ' ' -f 4

我部署了一个错误的图像,导致ErrImagePull,但部署仍然报告了8个最新日期副本的正确数量(可用副本为7)。

2 个答案:

答案 0 :(得分:28)

更新#2: Kubernetes 1.5将附带更好的版本kubectl rollout status,并在1.6中进一步改进,可能会替换下面列出的自定义解决方案/脚本。

更新#1:我已将我的答案转换为script hosted on Github,目前已收到少量改进的PR。

原始回答:

首先,我相信你得到的kubectl命令不正确:它用逗号替换所有空格,但是在用空格分隔后尝试获取第4个字段。

为了验证部署(或升级)是否适用于所有pod,我认为您应该检查可用副本的数量是否与所需副本的数量相匹配。也就是说,AVAILABLE输出中的DESIREDkubectl列是否相等。虽然您可以通过

获得可用副本的数量(第5列)

kubectl get deployment nginx | tail -n +2 | awk '{print $5}'

和所需副本的数量(第2列)到

kubectl get deployment nginx | tail -n +2 | awk '{print $2}'

更简洁的方法是使用kubectl的jsonpath输出,特别是如果你想要考虑官方文档中提到的生成要求。

这是我编写的一个快速bash脚本,它希望在命令行上获得部署名称,等待观察到的生成成为指定的生成,然后等待可用的副本达到指定的数量:

#!/bin/bash
set -o errexit
set -o pipefail
set -o nounset

deployment=

get_generation() {
  get_deployment_jsonpath '{.metadata.generation}'
}

get_observed_generation() {
  get_deployment_jsonpath '{.status.observedGeneration}'
}

get_replicas() {
  get_deployment_jsonpath '{.spec.replicas}'
}

get_available_replicas() {
  get_deployment_jsonpath '{.status.availableReplicas}'
}

get_deployment_jsonpath() {
  local readonly _jsonpath="$1"

  kubectl get deployment "${deployment}" -o "jsonpath=${_jsonpath}"
}

if [[ $# != 1 ]]; then
  echo "usage: $(basename $0) <deployment>" >&2
  exit 1
fi

readonly deployment="$1"

readonly generation=$(get_generation)
echo "waiting for specified generation ${generation} to be observed"
while [[ $(get_observed_generation) -lt ${generation} ]]; do
  sleep .5
done
echo "specified generation observed."

readonly replicas="$(get_replicas)"
echo "specified replicas: ${replicas}"

available=-1
while [[ ${available} -ne ${replicas} ]]; do
  sleep .5
  available=$(get_available_replicas)
  echo "available replicas: ${available}"
done

echo "deployment complete."

答案 1 :(得分:1)

只需使用rollout status

kubectl rollout status deployment/<deployment-name>

它将在前台运行,等待并显示状态,并在成功完成或失败时完成部署时退出。 如果要编写Shell脚本,请在命令后立即检查返回代码,如下所示。

kubectl rollout status deployment/<deployment-name>
if [[ "$?" -ne 0 ]] then
    echo "deployment failed!"
    exit 1
fi

要进一步自动化脚本,请执行以下操作:

deployment_name=$(kubectl get deployment -n <your namespace> | awk '!/NAME/{print $1}')  
kubectl rollout status deployment/"${deployment_name}" -n <your namespace>
if [[ "$?" -ne 0 ]] then
    echo "deployment failed!"
    #exit 1
else
    echo "deployment succeeded"
fi

如果您在默认名称空间中运行,则可以省去 -n <您的名称空间> 。 命令 awk'!/ NAME / {print $ 1}')提取第一个字段(部署名称),而忽略作为标题的第一行( NAME READY UP-TO-DATE可用年龄)。 如果您有多个部署文件,则还可以向awk添加更多正则表达式或模式: awk'!/ NAME / <要解析的模式> / {print $ 1}')