zh:sync /security/authorization/authz-ingress/ (#12019)

* zh:sync /security/authorization/authz-ingress/

* updated text by comments

* updated text by comments 2
This commit is contained in:
Michael 2022-09-29 14:04:07 +08:00 committed by GitHub
parent 4b0d544d58
commit 3210cb1cab
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
1 changed files with 26 additions and 33 deletions

View File

@ -15,9 +15,9 @@ test: yes
* 阅读 [Istio 授权概念](/zh/docs/concepts/security/#authorization)。
* 使用 [Istio 安装指南](/zh/docs/setup/install/istioctl/) 安装 Istio。
* 使用 [Istio 安装指南](/zh/docs/setup/install/istioctl/)安装 Istio。
* 在命名空间中部署工作负载`httpbin`,例如`foo`,并使用以下命令通过 Istio 入口网关公开它:
* 在命名空间中部署工作负载 `httpbin`,例如 `foo`,并使用以下命令通过 Istio 入口网关公开它:
{{< text bash >}}
$ kubectl create ns foo
@ -31,11 +31,9 @@ test: yes
$ kubectl get pods -n istio-system -o name -l istio=ingressgateway | sed 's|pod/||' | while read -r pod; do istioctl proxy-config log "$pod" -n istio-system --level rbac:debug; done
{{< /text >}}
* Follow the instructions in
[确定入口 IP 和端口](/zh/docs/tasks/traffic-management/ingress/ingress-control/#determining-the-ingress-ip-and-ports)
to define the `INGRESS_HOST` and `INGRESS_PORT` environment variables.
* 遵从[确定入口 IP 和端口](/zh/docs/tasks/traffic-management/ingress/ingress-control/#determining-the-ingress-ip-and-ports)中的指示说明来定义 `INGRESS_HOST``INGRESS_PORT` 环境变量。
* Verify that the `httpbin` workload and ingress gateway are working as expected using this command:
* 使用以下命令验证 `httpbin` 工作负载和入口网关正在按预期工作:
{{< text bash >}}
$ curl "$INGRESS_HOST:$INGRESS_PORT"/headers -s -o /dev/null -w "%{http_code}\n"
@ -43,36 +41,28 @@ test: yes
{{< /text >}}
{{< warning >}}
如果您没有看到预期的输出,请在几秒钟后重试。 缓存和传播开销可能会导致延迟。
如果您没有看到预期的输出,请在几秒钟后重试。缓存和传播开销可能会导致延迟。
{{< /warning >}}
## 将流量引入 Kubernetes 和 Istio {#getting-traffic-into-Kubernetes-and-Istio}
所有将流量引入 Kubernetes 的方法都涉及在所有工作节点上打开一个端口,实现这一点的主要功能是`NodePort`服务和`LoadBalancer`服务,甚至 Kubernetes 的`Ingress`资源也必须由 Ingress 控制器支持,该控制器将创建`NodePort`或`LoadBalancer`服务。
所有将流量引入 Kubernetes 的方法都涉及在所有工作节点上打开一个端口,实现这一点的主要功能是 `NodePort` 服务和 `LoadBalancer` 服务,甚至 Kubernetes 的 `Ingress` 资源也必须由 Ingress 控制器支持,该控制器将创建 `NodePort` `LoadBalancer` 服务。
* `NodePort` 只是在每个工作节点上打开一个 30000-32767 范围内的端口,并使用标签选择器来识别将流量发送到哪些 Pod。 您必须在工作节点前面手动创建某种负载均衡器或使用轮询模式的 DNS。
* `NodePort` 只是在每个工作节点上打开一个 30000-32767 范围内的端口,并使用标签选择器来识别将流量发送到哪些 Pod。您必须在工作节点前面手动创建某种负载均衡器或使用轮询模式的 DNS。
* `LoadBalancer` 就像`NodePort` 一样,除了它还创建一个特定于环境的外部负载均衡器来处理将流量分配到工作节点。 例如,在 AWS EKS 中,`LoadBalancer` 服务将创建一个以您的工作程序节点为目标的经典 ELB。 如果您的 Kubernetes 环境没有 `LoadBalancer` 实现,那么它的行为就像 `NodePort` Istio 入口网关创建一个`LoadBalancer`服务。
* `LoadBalancer` 就像 `NodePort` 一样,除了它还创建一个特定于环境的外部负载均衡器来处理将流量分配到工作节点。例如,在 AWS EKS 中,`LoadBalancer` 服务将创建一个以您的工作程序节点为目标的经典 ELB。如果您的 Kubernetes 环境没有 `LoadBalancer` 实现,那么它的行为就像 `NodePort`。Istio 入口网关创建一个 `LoadBalancer`服务。
如果处理来自 `NodePort``LoadBalancer` 的流量的 Pod 没有在接收流量的工作节点上运行怎么办? Kubernetes 有自己的内部代理,称为 kube-proxy它接收数据包并将它们转发到正确的节点。
如果处理来自 `NodePort``LoadBalancer` 的流量的 Pod 没有在接收流量的工作节点上运行怎么办Kubernetes 有自己的内部代理,称为 kube-proxy用于接收数据包并将数据包转发到正确的节点。
## 原始客户端的源IP地址 {#source-ip-address-of-the-original-client}
## 原始客户端的源 IP 地址 {#source-ip-address-of-the-original-client}
如果数据包通过外部代理负载均衡器和/或 kube-proxy则客户端的原始源 IP 地址会丢失。 以下是一些保留原始客户端 IP 以用于日志记录或安全目的的策略。
如果数据包通过外部代理负载均衡器和/或 kube-proxy则客户端的原始源 IP 地址会丢失。以下是一些保留原始客户端 IP 以用于日志记录或安全目的的策略。
{{< tabset category-name="lb" >}}
{{< tab name="TCP/UDP Proxy Load Balancer" category-value="proxy" >}}
{{< tab name="TCP/UDP 代理负载均衡器" category-value="proxy" >}}
{{< warning >}}
Envoy 中发现了一个严重的 [bug](https://groups.google.com/g/envoy-security-announce/c/aqtBt5VUor0),即针对非 HTTP 连接错误地恢复了代理协议下游地址。
请不要在非 HTTP 连接上使用带有代理协议的 `remoteIpBlocks` 字段和 `remote_ip` 属性,直到发布具有适当修复的更新版本的 Istio。
请注意Istio 不支持代理协议,它只能通过 `EnvoyFilter` API 启用,使用风险自负。
{{< /warning >}}
如果您使用的是 TCP/UDP 代理外部负载均衡器AWS Classic ELB它可以使用 [代理协议](https://www.haproxy.com/blog/haproxy/proxy-protocol/) 嵌入原始 数据包数据中的客户端 IP 地址。 外部负载均衡器和 Istio 入口网关都必须支持代理协议才能工作。 在 Istio 中,您可以使用 `EnvoyFilter` 启用它,如下所示:
如果您使用的是 TCP/UDP 代理外部负载均衡器AWS Classic ELB它可以使用[代理协议](https://www.haproxy.com/blog/haproxy/proxy-protocol/)嵌入原始数据包数据中的客户端 IP 地址。外部负载均衡器和 Istio 入口网关都必须支持代理协议才能工作。在 Istio 中,您可以使用 `EnvoyFilter` 启用它,如下所示:
{{< text yaml >}}
apiVersion: networking.istio.io/v1alpha3
@ -94,7 +84,7 @@ spec:
istio: ingressgateway
{{< /text >}}
以下是`IstioOperator`示例,展示了如何在 AWS EKS 上配置 Istio 入口网关以支持代理协议:
以下是 `IstioOperator` 示例,展示了如何在 AWS EKS 上配置 Istio 入口网关以支持代理协议:
{{< text yaml >}}
apiVersion: install.istio.io/v1alpha1
@ -132,7 +122,9 @@ spec:
{{< tab name="Network Load Balancer" category-value="network" >}}
如果您使用的是保留客户端 IP 地址的 TCP/UDP 网络负载均衡器AWS 网络负载均衡器、GCP 外部网络负载均衡器、Azure 负载均衡器),或者您使用的是轮询模式的 DNS那么您还可以保留客户端 IP 在 Kubernetes 内部绕过 kube-proxy 并阻止它向其他节点发送流量。 **但是,您必须在每个节点上运行一个入口网关 pod。** 如果不这样做,那么任何接收流量但没有入口网关的节点都会丢弃流量。 有关更多信息,请参阅 [使用 `Type=NodePort` 的服务的源 IP](https://kubernetes.io/docs/tutorials/services/source-ip/#source-ip-for-services-with-type-nodeport)。 使用以下命令更新入口网关以设置 `externalTrafficPolicy: Local` 以保留入口网关上的原始客户端源 IP
如果您使用的是保留客户端 IP 地址的 TCP/UDP 网络负载均衡器AWS 网络负载均衡器、GCP 外部网络负载均衡器、Azure 负载均衡器),或者您使用的是轮询模式的 DNS那么您还可以保留客户端 IP 在 Kubernetes 内部绕过 kube-proxy 并阻止它向其他节点发送流量。**但是,您必须在每个节点上运行一个入口网关 Pod。**
如果不这样做,那么任何接收流量但没有入口网关的节点都会丢弃流量。有关更多信息,请参阅[使用 `Type=NodePort` 的服务的源 IP](https://kubernetes.io/zh-cn/docs/tutorials/services/source-ip/#source-ip-for-services-with-type-nodeport)。
使用以下命令更新入口网关以设置 `externalTrafficPolicy: Local` 以保留入口网关上的原始客户端源 IP
{{< text bash >}}
$ kubectl patch svc istio-ingressgateway -n istio-system -p '{"spec":{"externalTrafficPolicy":"Local"}}'
@ -142,7 +134,7 @@ $ kubectl patch svc istio-ingressgateway -n istio-system -p '{"spec":{"externalT
{{< tab name="HTTP/HTTPS Load Balancer" category-value="http" >}}
如果您使用的是 HTTP/HTTPS 外部负载均衡器AWS ALB、GCP它可以将原始客户端 IP 地址放在 X-Forwarded-For 标头中。 Istio 可以通过一些配置从此标头中提取客户端 IP 地址。 请参阅[配置网关网络拓扑](/zh/docs/ops/configuration/traffic-management/network-topologies/)。 如果在 Kubernetes 前面使用单个负载均衡器,快速示例:
如果您使用的是 HTTP/HTTPS 外部负载均衡器AWS ALB、GCP它可以将原始客户端 IP 地址放在 X-Forwarded-For 标头中。Istio 可以通过一些配置从此标头中提取客户端 IP 地址。请参阅[配置网关网络拓扑](/zh/docs/ops/configuration/traffic-management/network-topologies/)。如果在 Kubernetes 前面使用单个负载均衡器,请参考以下快速示例:
{{< text yaml >}}
apiVersion: install.istio.io/v1alpha1
@ -160,9 +152,9 @@ spec:
{{< /tabset >}}
作为参考,以下是 Istio 在流行的托管 Kubernetes 环境中使用`LoadBalancer`服务创建的负载均衡器类型:
作为参考,以下是 Istio 在流行的托管 Kubernetes 环境中使用 `LoadBalancer` 服务创建的负载均衡器类型:
|Cloud Provider | Load Balancer Name | Load Balancer Type
|云提供商 | 负载均衡器名称 | 负载均衡器类型
----------------|-------------------------------|-------------------
|AWS EKS | Classic Elastic Load Balancer | TCP Proxy
|GCP GKE | TCP/UDP Network Load Balancer | Network
@ -194,15 +186,16 @@ spec:
## 基于 IP 的允许列表和拒绝列表{#ip-based-allow-list-and-deny-list}
**何时使用 `ipBlocks``remoteIpBlocks`** 如果您使用 X-Forwarded-For HTTP 标头或代理协议来确定原始客户端 IP 地址,那么您应该在您的 `AuthorizationPolicy` 中使用 `remoteIpBlocks` . 如果您使用的是 `externalTrafficPolicy: Local`,那么您应该在 `AuthorizationPolicy` 中使用 `ipBlocks`
**何时使用 `ipBlocks``remoteIpBlocks`** 如果您使用 X-Forwarded-For HTTP 标头或代理协议来确定原始客户端 IP 地址,那么您应该在您的 `AuthorizationPolicy` 中使用 `remoteIpBlocks`
如果您使用的是 `externalTrafficPolicy: Local`,那么您应该在 `AuthorizationPolicy` 中使用 `ipBlocks`
|Load Balancer Type |Source of Client IP | `ipBlocks` vs. `remoteIpBlocks`
| 负载均衡器类型 | 客户端源 IP | `ipBlocks` `remoteIpBlocks`
--------------------|----------------------|---------------------------
| TCP Proxy | Proxy Protocol | `remoteIpBlocks`
| Network | packet source address| `ipBlocks`
| HTTP/HTTPS | X-Forwarded-For | `remoteIpBlocks`
* 以下命令为 Istio 入口网关创建授权策略`ingress-policy`。 以下策略将`action`字段设置为`ALLOW`,以允`ipBlocks`中指定的 IP 地址访问入口网关。 不在列表中的 IP 地址将被拒绝。 `ipBlocks` 支持单个 IP 地址和 CIDR 表示法。
* 以下命令为 Istio 入口网关创建授权策略 `ingress-policy`。以下策略将 `action` 字段设置为 `ALLOW`,以允 `ipBlocks` 中指定的 IP 地址访问入口网关。不在列表中的 IP 地址将被拒绝。`ipBlocks` 支持单个 IP 地址和 CIDR 表示法。
{{< tabset category-name="source" >}}
@ -407,13 +400,13 @@ EOF
## 清理 {#clean-up}
* 删除命名空间`foo`
* 移除命名空间 `foo`
{{< text bash >}}
$ kubectl delete namespace foo
{{< /text >}}
* 除授权策略:
* 除授权策略:
{{< text bash >}}
$ kubectl delete authorizationpolicy ingress-policy -n istio-system