升级步骤

本页介绍如何将现有的 Istio 部署(包括控制平面和 sidecar 代理)升级到新版本。升级过程可能涉及新的二进制文件以及配置和 API schemas 等其他更改。升级过程可能导致一些服务停机。为了最大限度地减少停机时间,请使用多副本以保证 Istio 控制平面组件和应用程序具有高可用性。

在下面的步骤中,我们假设 Istio 组件在 istio-system namespace 中安装和升级。

升级步骤

控制平面升级


Istio 控制平面组件包括:Citadel、Ingress 网关、Egress 网关、Pilot、Policy、Telemetry 和 Sidecar 注入器。我们可以使用 Kubernetes 的滚动更新机制来升级控制平面组件。

您可以使用 Kubernetes 的滚动更新机制来升级控制平面组件。这适用于使用 kubectl apply 部署 Istio 组件的情况,包括使用 helm template 生成的配置。

  • 使用 kubectl apply 升级 Istio 所有的 CRD。稍微等待几秒钟,让 Kubernetes API 服务器接收升级后的 CRD:
  1. $ for i in install/kubernetes/helm/istio-init/files/crd*yaml; do kubectl apply -f $i; done
  • 例如,将 Istio 的核心组件添加到 Kubernetes 的清单文件中。
  1. $ helm template install/kubernetes/helm/istio --name istio \
  2. --namespace istio-system > $HOME/istio.yaml

如果要启用 全局双向 TLS,请将 global.mtls.enabledglobal.controlPlaneSecurityEnabled 设置为 true 以获取最后一个命令:

  1. $ helm template install/kubernetes/helm/istio --name istio --namespace istio-system \
  2. --set global.mtls.enabled=true --set global.controlPlaneSecurityEnabled=true > $HOME/istio-auth.yaml

如果使用 1.9 之前的 Kubernetes 版本,则应添加 —set sidecarInjectorWebhook.enabled=false

  • 通过清单升级 Istio 控制平面组件,例如:
  1. $ kubectl apply -f $HOME/istio.yaml

  1. $ kubectl apply -f $HOME/istio-auth.yaml

滚动更新过程会将所有部署和配置升级到新版本。完成此过程后,您的 Istio 控制平面应该会更新为新版本。您现有的应用程序应该继续工作。如果新控制平面存在任何严重问题,您可以通过应用旧版本的 yaml 文件来回滚更改。

如果你使用 Helm 和 Tiller 安装了 Istio,首选升级选项是让 Helm 负责升级。

  1. $ helm upgrade --install istio-init install/kubernetes/helm/istio-init --namespace istio-system
  • 检查所有的 CRD 创建 job 是否已成功完成,以验证 Kubernetes API 服务器是否已收到所有 CRD:
  1. $ kubectl get job --namespace istio-system | grep istio-init-crd
  • 升级 istio chart:
  1. $ helm upgrade istio install/kubernetes/helm/istio --namespace istio-system

Sidecar 升级

控制平面升级后,已经运行 Istio 的应用程序仍将使用旧版本的 sidecar。要想升级 sidecar,您需要重新注入它。

如果您使用自动 sidecar 注入(automatic sidecar injection),您可以通过对所有 pod 进行滚动升级来升级 sidecar,这样新版本的 sidecar 将被自动重新注入。一些技巧可以重新加载所有 pod。例如,有一个 bash 脚本 可以通过 patch 优雅结束时长(grace termination period)来触发滚动更新。

如果您使用手动注入,可以通过执行以下命令来升级 sidecar:

  1. $ kubectl apply -f <(istioctl kube-inject -f $ORIGINAL_DEPLOYMENT_YAML)

如果 sidecar 以前被注入了一些定制的注入配置文件,您需要将配置文件中的版本标签更改为新文件版本并像下面这样重新注入 sidecar:

  1. $ kubectl apply -f <(istioctl kube-inject \
  2. --injectConfigFile inject-config.yaml \
  3. --filename $ORIGINAL_DEPLOYMENT_YAML)

通过 annotation 将身份验证策略迁移为启用 per-service 双向 TLS

如果使用 service annotation 覆盖 service 的全局双向 TLS,则需要将其替换为 认证策略目的规则

例如,如果您在启用双向 TLS 的情况下安装 Istio,并使用如下所示的 service annotation 对 service foo 禁用它:

  1. kind: Service
  2. metadata:
  3. name: foo
  4. namespace: bar
  5. annotations:
  6. auth.istio.io/8000: NONE

您需要用此身份验证策略和目标规则替换它(删除旧 annotation 是可选的)

  1. apiVersion: "authentication.istio.io/v1alpha1"
  2. kind: "Policy"
  3. metadata:
  4. name: "disable-mTLS-foo"
  5. namespace: bar
  6. spec:
  7. targets:
  8. - name: foo
  9. ports:
  10. - number: 8000
  11. peers:
  12. ---
  13. apiVersion: "networking.istio.io/v1alpha3"
  14. kind: "DestinationRule"
  15. metadata:
  16. name: "disable-mTLS-foo"
  17. namespace: "bar"
  18. spec:
  19. host: "foo"
  20. trafficPolicy:
  21. tls:
  22. mode: ISTIO_MUTUAL
  23. portLevelSettings:
  24. - port:
  25. number: 8000
  26. tls:
  27. mode: DISABLE

如果您已经有 foo 的目标规则,则必须编辑该规则而不是创建新规则。创建新的目标规则时,请确保包含其他设置,如load balancerconnection pooloutlier detection(如有必要)。最后,如果 foo 没有 sidecar,你可以跳过身份验证策略,但仍然需要添加目标规则。

如果 8000 是 service foo 提供的唯一端口(或者您希望禁用所有端口的双向 TLS),则策略可以简化为:

  1. apiVersion: "authentication.istio.io/v1alpha1"
  2. kind: "Policy"
  3. metadata:
  4. name: "disable-mTLS-foo"
  5. namespace: bar
  6. spec:
  7. targets:
  8. - name: foo
  9. peers:
  10. ---
  11. apiVersion: "networking.istio.io/v1alpha3"
  12. kind: "DestinationRule"
  13. metadata:
  14. name: "disable-mTLS-foo"
  15. namespace: "bar"
  16. spec:
  17. host: "foo"
  18. trafficPolicy:
  19. tls:
  20. mode: DISABLE

将 mtls_excluded_services 配置迁移到目标规则

如果您在启用双向 TLS 的情况下安装了 Istio,并且使用网格配置 mtls_excluded_services 来在连接这些服务(例如 Kubernetes API server)时禁用双向 TLS,则需要通过添加目标规则来替换它。例如:

  1. apiVersion: networking.istio.io/v1alpha3
  2. kind: DestinationRule
  3. metadata:
  4. name: "kubernetes-master"
  5. namespace: "default"
  6. spec:
  7. host: "kubernetes.default.svc.cluster.local"
  8. trafficPolicy:
  9. tls:
  10. mode: DISABLE

迁移 RbacConfig 到 ClusterRbacConfig

RbacConfig 因为 bug 已经被废弃。如果你正在使用 RbacConfig,必须迁移到 ClusterRbacConfig。这个 bug 在某些情况下会将这个对象的范围降低到 namespace 级别。ClusterRbacConfig 的声明跟 RbacConfig 完全一样,但是以正确的集群级别范围实现。

为了自动化迁移,我们开发了脚本convert_RbacConfig_to_ClusterRbacConfig.sh. 这个脚本在 Istio 的安装包中。

下载并运行如下命令:

  1. $ curl -L https://raw.githubusercontent.com/istio/istio/release-1.1git/tools/convert_RbacConfig_to_ClusterRbacConfig.sh | sh -

这个脚本自动化下如下操作:

  • 这个脚本创建跟已经存在的 RBAC 配置一样的集群 RBAC 配置,因为 Kubernetes 不允许自定义资源的 kind: 在被创建之后修改。

例如,如果你创建如下 RBAC 配置:

  1. apiVersion: "rbac.istio.io/v1alpha1"
  2. kind: RbacConfig
  3. metadata:
  4. name: default
  5. spec:
  6. mode: 'ON_WITH_INCLUSION'
  7. inclusion:
  8. namespaces: ["default"]

这个脚本创建如下的集群 RBAC 配置:

  1. apiVersion: "rbac.istio.io/v1alpha1"
  2. kind: ClusterRbacConfig
  3. metadata:
  4. name: default
  5. spec:
  6. mode: 'ON_WITH_INCLUSION'
  7. inclusion:
  8. namespaces: ["default"]
  • 这个脚本应用这个配置,并等待几秒钟以使配置生效。

  • 这个脚本在成功应用集群 RBAC 配置之后,删除之前的 RBAC 自定义资源。