在 GKE 上安装 Istio

本指南介绍了如何开始使用 Istio on GKE 插件,包括新集群和现有集群的安装选项。您可以使用 gcloud 命令行工具或通过 Google Cloud Console 安装该插件。

如需详细了解 Istio on GKE 插件以及它是否适合您使用,请参阅概览

前期准备

请按照以下步骤启用 Kubernetes Engine API:

  1. 访问 Google Cloud Console 中的 Kubernetes Engine 页面
  2. 创建或选择项目。
  3. 稍作等待,让 API 和相关服务完成启用过程。 此过程可能耗时几分钟。
  4. 确保您的 Cloud 项目已启用结算功能。 了解如何确认您的项目是否已启用结算功能

确保您已安装以下命令行工具:

  • gcloud 用于创建和删除 Kubernetes Engine 集群,包括创建和更新带有 Istio on GKE 插件的集群。gcloud 包含在 Google Cloud SDK 中:请按照说明进行安装并将其初始化以便与 GCP 项目配合使用。如果已经安装了 gcloud,请验证其版本是否至少为 208.0.0:
    gcloud version
    请注意,由于您可以改用 Google Cloud Console,因此您不必安装 gcloud 即可创建已启用 Istio 的新集群,但它仍然适合管理现有集群和安装其他工具(例如 kubectl)。
  • kubectl 用于管理 Kubernetes(即 GKE 使用的集群编排系统)。您可以使用 gcloud 安装 kubectl
    gcloud components install kubectl

gcloud 命令行工具设置默认值

如需节省在 gcloud 命令行工具中输入项目 IDCompute Engine 地区选项的时间,您可以设置以下默认值:
gcloud config set project project-id
gcloud config set compute/zone compute-zone

选择安全选项

创建或更新包含 Istio on GKE 的集群时,您可以从两种默认的网格级安全选项中进行选择,选择哪个选项取决于初始应用需求。

  • 严格 mTLS:采用此安全模式时,Istio 默认会在网格中的所有服务与控制层面组件之间实施双向 TLS (mTLS) 加密,除非您将此设置替换针对特定目的地的规则。网格内的所有调用均已加密,且服务不会接受未加密的流量。
  • 宽松 mTLS:采用此安全模式时,Istio 默认允许网格中的服务接受加密的流量和未加密的流量,并且所有服务均默认发送未加密的调用。与严格 mTLS 模式一样,您可以针对特定服务替换此设置。如果您有服务仍需要接受未加密的流量(例如,如果您尚未将服务完全迁移到 Istio,并且有流量来自网格外部的旧版客户端),请使用此选项。Istio on GKE 会提供此模式,而不仅仅是在未启用安全功能的情况下安装 Istio,这样做便于以后更轻松地迁移到严格 mTLS 模式,从而获得额外的安全保障。

如需了解如何更新安全默认值并进一步配置 Istio 安全性,请参阅下文的更新安全默认值

受支持的 GKE 集群版本

在创建或更新包含 Istio on GKE 的集群时,安装的 Istio on GKE 版本取决于集群版本。我们建议您使用具有最新版 Istio(即 1.4.10-gke.5)的集群版本。如果您使用的是旧版本,请在此 Istio on GKE 版本可用后立即升级集群。

如需查看受支持版本的列表,请参阅 Istio on GKE 版本

在 GKE 上安装 Istio

您可以在新集群或现有集群中安装 Istio on GKE。在这两种情况下,此操作都会安装 Istio 控制层面。如需充分利用 Istio 的功能,您需要在服务网格的 Pod 中注入 Envoy Sidecar 代理

创建一个包含 Istio on GKE 的集群

我们建议您在使用此插件时至少创建一个机器类型具有 2 个 vCPU 的 4 节点集群。您可以使用默认的 GKE 新集群设置来部署 Istio 本身,但这样做可能无法提供足够的资源来探索示例应用。请注意,Istio on GKE 插件与 Workload Identity 不兼容。

如需使用 Istio on GKE 创建集群,请执行以下操作:

控制台

  1. 转到 Cloud Console 中的 Kubernetes 页面,然后选择创建集群
  2. 使用默认的标准集群对话框,选择所需的节点和机器数量,请谨记推荐 Istio 使用的最小集群大小。
  3. 主版本下拉菜单中,选择 Istio on GKE 推荐的集群版本(如果无法使用推荐的版本,请选择受支持的版本)。
  4. 选择可用性、网络、安全性及其他功能以显示其他配置选项,包括 Istio on GKE。
  5. 选择启用 Istio(Beta 版)
  6. 从下拉菜单中选择您要用于集群的 mTLS 安全模式。
  7. 点击创建以创建集群。

命令行

如需创建一个默认已启用 Istio 并实施双向 TLS 的 GKE 集群,请运行以下命令,将 CLUSTER_NAME 替换为您选择的集群名称,并将 CLUSTER_VERSION 替换为兼容的集群版本

gcloud beta container clusters create CLUSTER_NAME \
    --addons=Istio --istio-config=auth=MTLS_STRICT \
    --cluster-version=CLUSTER_VERSION \
    --machine-type=n1-standard-2 \
    --num-nodes=4

或者,如需创建一个已启用 Istio 且采用宽松 mTLS 模式的 GKE 集群,请执行以下操作:

gcloud beta container clusters create CLUSTER_NAME \
    --addons=Istio --istio-config=auth=MTLS_PERMISSIVE \
    --cluster-version=CLUSTER_VERSION \
    --machine-type=n1-standard-2 \
    --num-nodes=4

将 Istio on GKE 添加到现有集群

如需使用该插件更新集群,可能需要先调整集群的大小,以确保您有足够的资源可供 Istio 使用。创建新集群时,我们建议至少创建一个机器类型包含 2 个 vCPU 的 4 节点集群。

您的集群还必须运行受支持的集群主版本,才能使用该插件。请注意,Istio on GKE 插件与 Workload Identity 不兼容。

如需使用 Istio on GKE 插件更新现有集群,请执行以下操作:

控制台

  1. 转到 Cloud Console 中的“Kubernetes 集群”页面,然后选择您要更新的集群
  2. 选择修改
  3. Istio(Beta 版)下,选择已启用以显示 Istio mTLS(Beta 版)
  4. 从下拉菜单中选择您要用于集群的 mTLS 安全模式。
  5. 点击保存以更新您的集群。

命令行

如需将默认实施了双向 TLS 的 Istio 添加到现有集群中,请运行以下命令,将 CLUSTER_NAME 替换为集群名称:

gcloud beta container clusters update CLUSTER_NAME \
    --update-addons=Istio=ENABLED --istio-config=auth=MTLS_STRICT

如需将采用宽松 mTLS 模式的 Istio 添加到现有集群中,请执行以下操作:

gcloud beta container clusters update CLUSTER_NAME \
    --update-addons=Istio=ENABLED --istio-config=auth=MTLS_PERMISSIVE

请注意,clusters update 命令可能需要其他参数,具体取决于您的实际集群配置。

如果集群上已有应用,您可以参阅 Istio 文档以了解如何迁移该应用,使其由 Istio 管理。

验证安装

如需验证 Istio on GKE 安装是否成功,请执行以下操作:

  1. 如果您刚刚创建了集群而非更新了集群,请检查并确保它已启动且运行的是 1.10.6 或更高版本的 GKE:
    gcloud container clusters list
    
    输出内容类似如下:
    NAME        LOCATION       MASTER_VERSION  MASTER_IP      MACHINE_TYPE   NODE_VERSION   NUM_NODES  STATUS
    istio-demo  us-central1-b  1.11.2-gke.15   35.239.252.38  n1-standard-2  1.11.2-gke.15  4          RUNNING
    
  2. 为您的新集群获取凭据,让您可以使用 kubectl 与之互动。
    gcloud container clusters get-credentials CLUSTER_NAME
    
  3. 确保已部署以下 Kubernetes 服务:istio-citadelistio-egressgatewayistio-pilotistio-ingressgatewayistio-policyistio-sidecar-injectoristio-telemetry(您也会看到其他已部署的服务):
    kubectl get service -n istio-system
    
    NAME                       TYPE           CLUSTER-IP      EXTERNAL-IP   PORT(S)                                                                                                                   AGE
    istio-citadel              ClusterIP      10.47.245.92    <none>        8060/TCP,9093/TCP                                                                                                         12s
    istio-egressgateway        ClusterIP      10.47.248.129   <none>        80/TCP,443/TCP                                                                                                            12s
    istio-galley               ClusterIP      10.47.248.109   <none>        443/TCP,9093/TCP                                                                                                          12s
    istio-ingressgateway       LoadBalancer   10.47.248.117   <pending>     80:31380/TCP,443:31390/TCP,31400:31400/TCP,15011:30221/TCP,8060:32445/TCP,853:30663/TCP,15030:32010/TCP,15031:32633/TCP   12s
    istio-pilot                ClusterIP      10.47.251.133   <none>        15010/TCP,15011/TCP,8080/TCP,9093/TCP                                                                                     12s
    istio-policy               ClusterIP      10.47.255.244   <none>        9091/TCP,15004/TCP,9093/TCP                                                                                               12s
    istio-sidecar-injector     ClusterIP      10.47.240.36    <none>        443/TCP                                                                                                                   12s
    istio-statsd-prom-bridge   ClusterIP      10.47.247.135   <none>        9102/TCP,9125/UDP                                                                                                         12s
    istio-telemetry            ClusterIP      10.47.242.73    <none>        9091/TCP,15004/TCP,9093/TCP,42422/TCP                                                                                     12s
    promsd                     ClusterIP      10.47.241.188   <none>        9090/TCP                                                                                                                  12s
    
  4. 确保已部署相应的 Kubernetes Pod,并且所有容器均已启动且正在运行:istio-pilot-*istio-policy-*istio-telemetry-*istio-egressgateway-*istio-ingressgateway-*istio-sidecar-injector-*istio-citadel-*

    kubectl get pods -n istio-system
    
    NAME                                        READY   STATUS      RESTARTS   AGE
    istio-citadel-555d845b65-xfdmj              1/1     Running     0          2d
    istio-cleanup-secrets-8x2pl                 0/1     Completed   0          2d
    istio-egressgateway-667d854c49-9q5dl        1/1     Running     0          2d
    istio-galley-6c9cd5b8bb-4j4jk               1/1     Running     0          2d
    istio-ingressgateway-6c796c5594-f972p       1/1     Running     0          2d
    istio-pilot-77f74fc6f-rpbfj                 2/2     Running     0          2d
    istio-policy-655b87fff-4wbwq                2/2     Running     0          2d
    istio-security-post-install-tm2rm           0/1     Completed   1          2d
    istio-sidecar-injector-668c9fb4db-p6lwt     1/1     Running     0          2d
    istio-statsd-prom-bridge-5b645f6f4d-6pbgf   1/1     Running     0          2d
    istio-telemetry-d9848f498-wf6kh             2/2     Running     0          2d
    promsd-6b989699d8-l7jxt                 1/1     Running     0          2d
    

启用 Sidecar 注入

为充分利用 Istio 的功能,应用中每项服务的 Pod 中都需要运行一个 Envoy Sidecar 代理。Envoy 代理会拦截服务的所有入站和出站流量并与 Istio 控制层面通信。您可以通过更新 Pod 的 Kubernetes 配置来手动注入 Envoy 代理,也可以使用 Istio 的基于网络钩子的自动 Sidecar 注入功能。

默认情况下,系统会停用所有命名空间的 Istio Sidecar 自动注入功能。如需启用自动注入功能,请将以下命令中的 NAMESPACE 替换为应用服务的命名空间名称或替换为 default

kubectl label namespace NAMESPACE istio-injection=enabled

由于 Sidecar 是在创建 Pod 时添加的,因此必须重启所有正在运行的 Pod,更改才会生效。如需在命名空间中停用自动注入功能,请移除标签并重启 Pod 以移除其 Sidecar。

如需手动注入 Envoy Sidecar,请参阅安装 Sidecar

配置控制层面

虽然 Istio on GKE 管理大多数控制层面设置,但在生产环境中,我们还是建议您根据以下设置为您的使用场景选择并指定适当的值。您可以使用 kubectl 或选择的 Kubernetes 工具更改这些值。当插件升级安装后,这些设置不会改变。

横向扩缩

请配置下列其中一项,以确保有足够的 Istio 控制层面组件副本能够处理您的网格流量。在生产环境中,我们建议您至少使用 istio-policyistio-telemetryistio-pilotistio-sidecar-injector 的副本中的两个。

  • 横向 Pod 自动扩缩会根据观察到的 CPU 利用率自动扩缩副本数量。我们会为自动扩缩控制层面组件提供默认的最大值和最小值,但您可以根据自己的需求修改这些值。例如,下方展示了如何使用 kubectl edit 来指定您要修改 Istio-Telemetry 的自动扩缩器设置:

    kubectl edit -n istio-system HorizontalPodAutoscalers/istio-telemetry
    
  • 如果未使用自动扩缩,您可以为每个控制层面元素设置副本数(Citadel 除外,它始终是单例),用于手动横向扩缩。例如,下方展示了如何使用 kubectl 来指定您想要两个 Pilot 实例:

    kubectl scale -n istio-system --replicas=2 deployment/istio-pilot
    

资源请求量

默认情况下,系统不会设置资源请求量,但在生产环境中,我们建议将资源请求量设置为适当的值,以确保节点有足够的资源能够支持 Pod。您应该为 Pod 中的每个容器设置资源请求量,否则 CPU on HPA 会显示 unknown,自动扩缩将无法工作。

如需了解每个组件的资源设置的建议起点,请参阅 Istio 安装选项指南。例如,适用于 Mixer 的资源请求量和限制位于 mixer 选项下。

kubectl edit -n istio-system Deployments/istio-telemetry

Pod 中断预算

对于给定的部署,您可以通过 PodDisruptionBudgets 指定应用能够接受并继续工常工作的最少可用副本数。

您应该为必须在 Istio on GKE 升级期间保持可用的所有部署配置 PodDisruptionBudgets。如果您尚未部署和配置自己的入站流量网关,我们建议您至少针对插件提供的 Istio 入站流量网关 (istio-ingressgateway) 执行上述操作,否则在升级过程中外部流量可能无法到达您的应用。

如上文所述,Pod 中断预算设置应与横向扩缩设置一起配置。副本数量或自动扩缩器最低副本数需要大于 Pod 中断预算最小值,因为 Istio on GKE 的升级过程会导致各个副本在更新时不可用。此操作可确保在升级期间不会违反 PodDisruptionBudget 中的 minAvailable 设置,升级会按预期运行。

自定义安装内容

虽然 Istio on GKE 为许多使用场景都提供了合理的默认行为,但您可以通过多种方式自定义安装内容,包括配置遥测工具和添加网关。本部分介绍如何进行受支持的自定义。

更新安全默认值

将运行中集群内默认的 Istio mTLS 安全模式从严格切换为宽松或从宽松切换为严格时,请使用将 Istio 添加到集群中时的同一命令:

控制台

  1. 转到 Cloud Console 中的“Kubernetes 集群”页面,然后选择您要更新的集群
  2. 选择修改
  3. Istio(Beta 版)下,选择已启用以显示 Istio mTLS(Beta 版)
  4. 从下拉菜单中选择您要用于集群的 mTLS 安全模式。
  5. 点击保存以更新您的集群。

命令行

如需更改集群以便使用默认实施了双向 TLS 的 Istio,请运行以下命令,将 CLUSTER_NAME 替换为集群名称:

$ gcloud beta container clusters update CLUSTER_NAME \
    --update-addons=Istio=ENABLED --istio-config=auth=MTLS_STRICT

或者,如需将集群切换为宽松 mTLS 模式,请执行以下操作:

$ gcloud beta container clusters update CLUSTER_NAME \
    --update-addons=Istio=ENABLED --istio-config=auth=MTLS_PERMISSIVE

请注意,如果您在启用严格 mTLS 模式的同时仍然有需要发送或接收未加密流量的服务,则您的应用可能会中断!如需详细了解如何迁移到严格 mTLS 模式,请参阅双向 TLS 迁移。您还可以指定更精细的目的地专用身份验证政策。目的地专用身份验证政策始终都会替换任何全局默认的 mTLS 设置,即使您从严格模式切换为宽松模式或从宽松模式切换为严格模式也是如此。

如需详细了解如何配置和使用 Istio 安全功能,包括设置基于角色的授权,请参阅 Istio 网站

跟踪和日志记录

默认情况下,如果您已为项目和集群启用了相关功能,则与 Istio on GKE 一起安装的网格可以将日志记录和指标数据发送到 Cloud Logging 和 Cloud Monitoring。默认情况下,低于 1.1.7 的 Istio on GKE 版本也会发送跟踪记录数据。如需了解详情,请参阅 Google Cloud 的运维套件支持

使用跟踪和日志记录功能可能会产生额外费用,尤其是有大量数据来自您的网格时。如果您希望在未完全停用项目的 Google Cloud 运维套件 API 的情况下停用此功能,请按如下所示更新 Istio on GKE 配置。

停用 Istio on GKE 的 Cloud Logging 功能

  1. 打开 stackdriver-log 规则进行修改:

    kubectl edit -n istio-system rule stackdriver-log
    
  2. match 条件 (context.protocol == "http" || context.protocol == "grpc") && (context.reporter.kind | "inbound" == "inbound") 替换为 "false"

  3. 保存并关闭规则。

  4. 打开 stackdriver-log-tcp 规则。

    kubectl edit -n istio-system rule stackdriver-log-tcp
    
  5. match 条件 (context.protocol == "tcp") && (context.reporter.kind | "inbound" == "inbound") 替换为 "false"

  6. 保存并关闭规则。

停用 Istio on GKE 的 Google Cloud 运维套件跟踪功能

如果您拥有 Istio on GKE 1.1.3-gke.0 版或更低版本,或者您手动启用了 Google Cloud 的运维套件跟踪功能,则可以按照如下所示将其停用:

  1. 打开 stackdriver-tracing-rule 规则进行修改:

    kubectl edit -n istio-system rule stackdriver-tracing-rule
    
  2. match 条件 context.protocol == "http" || context.protocol == "grpc" 替换为 "false"

  3. 保存并关闭规则。

启用 Istio on GKE 的 Google Cloud 运维套件跟踪功能

如果您使用的是 1.1.7 版或更高版本,并且想要启用 Google Cloud 的运维套件跟踪功能,请执行以下操作:

  1. 确保已在 Google Cloud 项目中启用 Cloud Trace API

  2. 打开 stackdriver-tracing-rule 规则进行修改:

    kubectl edit -n istio-system rule stackdriver-tracing-rule
    
  3. match 条件 "false" 替换为 context.protocol == "http" || context.protocol == "grpc"

  4. 保存并关闭规则。

添加网关

系统将在安装 Istio on GKE 的过程中提供一个 Istio 入站流量网关:默认入站流量网关适用于所安装资源(RBAC、服务、部署)无需进行太多自定义的部署。您可以在 Istio 网关配置中添加字段,也可以修改以下控制层面设置

  • 横向扩缩
  • 资源请求量
  • Pod 中断预算

当您升级 GKE 时,系统会自动升级 Istio on GKE 插件以及该插件安装的所有资源(包括默认入站流量网关)。请勿更改默认入站流量网关配置中的任何其他值,因为这些更改将在自动升级期间恢复为默认值。

对于需要进行自定义的更为复杂的场景,您需要创建新的入站流量网关。如果您添加入站或出站流量网关,这些网关将由您掌控,因此不会在自动升级过程中遭到修改。

请注意,默认情况下,1.1 版及更高版本不会安装 Istio 出站流量网关。如需添加入站或出站流量网关,请执行以下操作:

  1. 向当前用户授予集群管理员权限:

    1. 将您的用户帐号设置为当前用户。

      gcloud auth login
    2. 向当前用户授予集群管理员权限。

      kubectl create clusterrolebinding cluster-admin-binding \
      --clusterrole=cluster-admin \
      --user="$(gcloud config get-value core/account)"
      
  2. 按照添加网关中的步骤添加网关。

访问外部服务

来自启用了 Istio 的 Pod 中的所有出站流量都将重定向至其 Sidecar 代理。默认情况下,Istio 将 Sidecar 代理配置为传递未知服务的请求,但您可以配置更严格的控制机制。虽然您可以创建 ServiceEntries 以便向允许的目的地发送出站请求,但出于安全考虑,您可能需要按照安全控制 Istio 中的出站流量博文所述添加出站流量网关。

后续步骤

  • 请尝试安装并探索图书信息示例以查看 Istio 的用途。如需获取示例应用和 istioctl 工具,请转到 Istio 版本页下载与运行命令的操作系统相对应的安装文件。然后,请按照 GKE 的安装 Istio 教程中的说明部署和测试该应用(无需部署 Istio 本身)。
  • 如需详细了解 Istio,请参阅开源文档
  • 如果需要从集群中移除 Istio 插件,请参阅卸载 Istio on GKE