通过网关注入安装网关

本操作步骤说明如何通过网关注入安装网关。

INFO

以下操作步骤适用于 ingress 和 egress 网关部署。

前提条件

操作步骤

  1. 创建网关命名空间:

    kubectl create namespace <gateway_namespace>
    NOTE

    请将网关和 Istio 控制平面安装在不同的命名空间中。

    你可以将网关安装在专用的网关命名空间中。 这种方式允许网关被多个运行在不同命名空间的应用共享。 另外,也可以将网关安装在应用命名空间中。 这种方式下,网关作为该命名空间内应用的专用网关。

  2. 创建名为 secret-reader.yaml 的 YAML 文件,定义网关部署所需的 service account、role 和 role binding。 这些配置允许网关读取 secret,以获取 TLS 凭据。

    secret-reader.yaml
    apiVersion: v1
    kind: ServiceAccount
    metadata:
      name: secret-reader
      namespace: <gateway_namespace>
    ---
    apiVersion: rbac.authorization.k8s.io/v1
    kind: Role
    metadata:
      name: secret-reader
      namespace: <gateway_namespace>
    rules:
      - apiGroups: [""]
        resources: ["secrets"]
        verbs: ["get", "watch", "list"]
    ---
    apiVersion: rbac.authorization.k8s.io/v1
    kind: RoleBinding
    metadata:
      name:  secret-reader
      namespace: <gateway_namespace>
    roleRef:
      apiGroup: rbac.authorization.k8s.io
      kind: Role
      name: secret-reader
    subjects:
      - kind: ServiceAccount
        name:  secret-reader
  3. 运行以下命令应用该 YAML 文件:

    kubectl apply -f secret-reader.yaml
  4. 创建名为 gateway-deployment.yaml 的 YAML 文件,定义网关的 Kubernetes Deployment 对象。

    gateway-deployment.yaml
    apiVersion: apps/v1
    kind: Deployment
    metadata:
      name: <gateway_name>
      namespace: <gateway_namespace>
    spec:
      selector:
        matchLabels:
          istio: <gateway_name>
      template:
        metadata:
          annotations:
            inject.istio.io/templates: gateway
          labels:
            istio: <gateway_name>
            sidecar.istio.io/inject: "true"
        spec:
          containers:
            - name: istio-proxy
              image: auto
              securityContext:
                capabilities:
                  drop:
                    - ALL
                allowPrivilegeEscalation: false
                privileged: false
                readOnlyRootFilesystem: true
                runAsNonRoot: true
              ports:
                - containerPort: 15090
                  protocol: TCP
                  name: http-envoy-prom
              resources:
                limits:
                  cpu: 2000m
                  memory: 1024Mi
                requests:
                  cpu: 100m
                  memory: 128Mi
          serviceAccountName: secret-reader
          nodeSelector:
            node-role.kubernetes.io/infra: ""
          tolerations:
            - effect: NoSchedule
              key: node-role.kubernetes.io/infra
              value: reserved
              operator: Equal
    1. 表示 Istio 控制平面使用网关注入模板,而非默认的 sidecar 模板。
    2. 确保为网关部署设置唯一标签。 唯一标签是 Istio Gateway 资源选择网关工作负载的必要条件。
    3. 通过设置 sidecar.istio.io/inject 标签为 true 启用网关注入。 如果 Istio 资源名称非默认,必须使用 istio.io/rev: <istio_revision> 标签,其中 revision 表示 Istio 资源的活动版本。
    4. 将 image 字段设置为 auto,以便每次 Pod 启动时自动更新镜像。
    5. serviceAccountName 设置为之前创建的 ServiceAccount 名称。
    6. (可选)设置 nodeSelector,将网关 Pod 调度到 Infra Nodes
    7. (可选)设置 tolerations,允许网关 Pod 被调度到 Infra Nodes
  5. 运行以下命令应用该 YAML 文件:

    kubectl apply -f gateway-deployment.yaml
  6. 运行以下命令,验证网关 Deployment 是否成功发布:

    kubectl rollout status deployment/<gateway_name> -n <gateway_namespace>

    你应该看到类似如下输出:

    示例输出

    Waiting for deployment "<gateway_name>" rollout to finish: 0 of 1 updated replicas are available...
    deployment "<gateway_name>" successfully rolled out
  7. 创建名为 gateway-service.yaml 的 YAML 文件,定义网关的 Kubernetes Service 对象。

    gateway-service.yaml
    apiVersion: v1
    kind: Service
    metadata:
      name: <gateway_name>
      namespace: <gateway_namespace>
    spec:
      type: ClusterIP
      selector:
        istio: <gateway_name>
      ports:
        - name: status-port
          port: 15021
          protocol: TCP
          targetPort: 15021
        - name: http2
          port: 80
          protocol: TCP
          targetPort: 80
        - name: https
          port: 443
          protocol: TCP
          targetPort: 443
    1. 当将 spec.type 设置为 ClusterIP 时,网关 Service 对象只能在集群内部访问。 若网关需处理来自集群外部的入口流量,应将 spec.type 设置为 LoadBalancer
    2. selector 设置为之前创建的网关部署 Pod 模板中指定的唯一标签或标签集合。
  8. 运行以下命令应用该 YAML 文件:

    kubectl apply -f gateway-service.yaml
  9. 运行以下命令,验证网关服务是否正确指向网关 Pod 的端点:

    kubectl get endpoints <gateway_name> -n <gateway_namespace>

你应该看到类似如下示例输出:

示例输出

NAME              ENDPOINTS                                             AGE
<gateway_name>    10.131.0.181:15021,10.131.0.181:80,10.131.0.181:443   1m
  1. 可选 :创建名为 gateway-hpa.yaml 的 YAML 文件,定义网关的水平 Pod 自动扩缩器。 以下示例将最小副本数设置为 2,最大副本数设置为 5,当平均 CPU 利用率超过 Pod 模板中部署定义的 CPU 资源限制的 80% 时,自动扩容。

    gateway-hpa.yaml
    apiVersion: autoscaling/v2
    kind: HorizontalPodAutoscaler
    metadata:
      name: <gateway_name>
      namespace: <gateway_namespace>
    spec:
      minReplicas: 2
      maxReplicas: 5
      metrics:
      - resource:
          name: cpu
          target:
            averageUtilization: 80
            type: Utilization
        type: Resource
      scaleTargetRef:
        apiVersion: apps/v1
        kind: Deployment
        name: <gateway_name>
    1. spec.scaleTargetRef.name 设置为之前创建的网关部署名称。
  2. 可选 :运行以下命令应用该 YAML 文件:

    kubectl apply -f gateway-hpa.yaml
  3. 可选 :创建名为 gateway-pdb.yaml 的 YAML 文件,定义网关的 Pod 中断预算。 以下示例允许只有在驱逐后集群中至少还剩 1 个健康的网关 Pod 时,才允许驱逐网关 Pod。

    gateway-pdb.yaml
    apiVersion: policy/v1
    kind: PodDisruptionBudget
    metadata:
      name: <gateway_name>
      namespace: <gateway_namespace>
    spec:
      minAvailable: 1
      selector:
        matchLabels:
          istio: <gateway_name>
    1. spec.selector.matchLabels 设置为之前创建的网关部署 Pod 模板中指定的唯一标签或标签集合。
  4. 可选 :运行以下命令应用该 YAML 文件:

    kubectl apply -f gateway-pdb.yaml