我有以下复制控制器在Kubernetes上的GKE:

apiVersion: v1
kind: ReplicationController
metadata:
  name: myapp
  labels:
    app: myapp
spec:
  replicas: 2
  selector:
    app: myapp
    deployment: initial
  template:
    metadata:
      labels:
        app: myapp
        deployment: initial
    spec:
      containers:
      - name: myapp
        image: myregistry.com/myapp:5c3dda6b
        ports:
        - containerPort: 80
      imagePullPolicy: Always
      imagePullSecrets:
        - name: myregistry.com-registry-key

现在,如果我说

kubectl rolling-update myapp --image=us.gcr.io/project-107012/myapp:5c3dda6b

执行滚动更新,但不重新拉取。为什么?


当前回答

一个流行的解决方法是用一个虚拟注释(或标签)修补部署:

kubectl patch deployment <name> -p \
  "{\"spec\":{\"template\":{\"metadata\":{\"annotations\":{\"date\":\"`date +'%s'`\"}}}}}"

假设您的部署满足这些要求,这将导致k8提取任何新映像并重新部署。

其他回答

现在,命令kubectl rollout restart deploy your - deployment结合imagePullPolicy: Always策略将允许您使用最新版本的映像重新启动所有pod。

当给定映像参数时,滚动更新命令假定映像与复制控制器中当前存在的映像不同。

一个流行的解决方法是用一个虚拟注释(或标签)修补部署:

kubectl patch deployment <name> -p \
  "{\"spec\":{\"template\":{\"metadata\":{\"annotations\":{\"date\":\"`date +'%s'`\"}}}}}"

假设您的部署满足这些要求,这将导致k8提取任何新映像并重新部署。

必须在容器数据中而不是在规范数据中对imagePullPolicy进行分组。然而,我对此提出了一个问题,因为我觉得这很奇怪。此外,没有错误消息。

因此,这个规范代码片段是有效的:

spec:
  containers:
  - name: myapp
    image: myregistry.com/myapp:5c3dda6b
    ports:
    - containerPort: 80
    imagePullPolicy: Always
  imagePullSecrets:
    - name: myregistry.com-registry-key

这个答案的目的是在节点已经下载了同名图像的情况下强制拉取图像,因此即使您将新图像推到容器注册表中,当您启动一些pod时,您的pod会显示“image already present”。

对于Azure容器注册表中的一个案例(可能AWS和GCP也提供了这个):

您可以查看Azure容器注册表,通过检查清单创建日期,可以确定哪个映像是最近的映像。 然后,复制它的摘要散列(格式为sha256:xxx…xxx)。 您可以通过运行下面的命令来缩小当前的副本。注意,这显然会停止容器并导致停机。

kubectl scale --replicas=0 deployment <deployment-name> -n <namespace-name>

然后您可以获得部署的副本。通过运行Yaml:

kubectl get deployments.apps <deployment-name> -o yaml > deployment.yaml

然后将带有图像字段的行从<image-name>:<tag>更改为<image-name>@sha256:xxx…Xxx,保存文件。 现在你可以再次放大你的复制品了。新图片将以其独特的摘要被拉出。

注意:假设imagePullPolicy: Always字段存在于容器中。