使用NGINX Ingress Controller增强TCP/UDP负载均衡和WAF配置

NGINX | 2021年3月31日

标准Kubernetes Ingress资源非常适合预置和配置基本的Ingress负载均衡,但不具备实现Kubernetes生产级部署所需的自定义功能。因此,非NGINX用户只能使用注解、ConfigMap和自定义模板,而这些方式容易出错、难以使用、不安全,并且缺乏精细的作用域控制。NGINX Ingress资源正是我们为解决这一问题提供的方案。

NGINX Ingress资源适用于基于NGINX Open Source和NGINX Plus的两个版本的NGINX Ingress Controller。它们提供原生、类型安全且采用缩进格式的配置方式,可简化Ingress负载均衡的实施。在本博客中,我们将重点介绍NGINX Ingress Controller 1.11.0中引入的两项功能,帮助您更轻松地配置WAF和负载均衡策略:

  • TransportServer资源:TransportServer资源用于定义TCP、UDP和TLS直通负载均衡的配置。我们新增了运行状况检查、状态报告和配置片段,以增强TCP/UDP负载均衡。
  • NGINX Ingress WAF策略:将NGINX App Protect 3.0与NGINX Ingress Controller结合部署后,可以利用NGINX Ingress资源将WAF策略应用于特定的Kubernetes服务。

TransportServer资源增强功能

NGINX Ingress Controller 1.11.0在以下方面扩展了TransportServer(TS)资源:

注意:版本 1.11.0 中新增的 TransportServer 资源功能属于技术预览版,目前仍在积极开发中。未来版本将把这些功能提升至稳定且可用于生产环境的质量标准。

TransportServer 代码片段

在NGINX Ingress Controller中,我们为VirtualServer和VirtualServerRoute(VS和VSR)资源引入了配置片段,以便原生扩展面向HTTP客户端的NGINX Ingress配置。1.11.0版本为TS资源引入了配置片段,让您可以轻松利用NGINX和NGINX Plus的各项功能来交付基于TCP/UDP的服务。例如,可以使用配置片段添加deny和allow指令,通过IP地址和地址范围来指定哪些客户端可以访问服务

apiVersion: k8s.nginx.org/v1alpha1kind: TransportServer
metadata:
  name: cafe
spec:
  host: cafe.example.com
  serverSnippets: |
    deny  192.168.1.1;
    allow 192.168.1.0/24;
  upstreams:
  - name: tea
    service: tea-svc
    port: 80

健康检查

为监控Kubernetes集群的运行状况,NGINX Ingress Controller不仅会考虑应用Pod本地的Kubernetes探针,还会持续监控基于TCP/UDP的上游服务之间的网络状态。被动健康检查用于评估进行中事务的运行状况,主动健康检查(NGINX Plus专属)则通过合成连接请求定期探测端点。

运行状况检查对于熔断和处理应用程序错误非常有用。可以使用TS资源中“healthCheck”字段内的参数来自定义运行状况检查,包括设置探测间隔、探测超时时间、探测延迟时间等。

此外,还可以设置NGINX Ingress Controller发出的健康探测所针对的上游服务和目标端口。如果由另一个进程或子系统监控应用的多个下游组件,并通过其他侦听器公开上游应用的运行状况,此设置会很有用。

使用ingressClassName 支持多个 TransportServer 资源

更新并应用TS资源时,建议验证配置是否有效,以及是否已成功应用于相应的Ingress Controller部署。版本1.11.0为TS资源引入了ingressClassName字段和状态报告功能。在存在多个部署的环境中,ingressClassName字段可确保TS资源由指定的Ingress Controller部署处理。

要显示一个或所有TS资源的状态,请运行kubectl get transportserver命令;输出内容包括状态(Valid或Invalid)、最近一次更新的原因,以及(对于单个TS)自定义消息。

$ kubectl get transportserver  NAME      STATE   REASON           AGE
  dns-tcp   Valid   AddedOrUpdated   47m

$ kubectl describe transportserver dns-tcp
. . .
Status:
  Message:  Configuration for default/dns-tcp was added or updated
  Reason:   AddedOrUpdated
  State:    Valid

如果多个TS资源争用同一主机或侦听器,NGINX Ingress Controller会选择时间戳最早的TS资源,从而确保在这种情况下获得确定性结果。

使用原生NGINX App Protect支持定义WAF策略

NGINX Ingress资源不仅让配置更简单、更灵活,还支持将流量控制委派给不同团队,并对VirtualServerRoute(VSR)资源中定义的应用子路由所属用户实施更严格的权限限制。通过为适当的团队授予适当Kubernetes资源的访问权限,NGINX Ingress资源可帮助您精细控制网络资源,并在用户账户遭入侵或攻击时减少应用可能受到的损害。

1.11.0版引入了原生Web应用防火墙(WAF)Policy对象,将这些优势扩展到Kubernetes部署中的NGINX App Protect配置。该策略利用了APLogConf和APPolicy对象(在1.8.0版中引入),并可附加到VirtualServer(VS)和VSR资源。这意味着,安全管理员可以通过VS资源管理Ingress配置的全部范围,同时通过引用VSR资源将安全职责委派给其他团队。

在以下示例中,系统会对路由到上游服务waf-prod的用户应用webapp-prod策略。为了将/v2路由的安全职责委派给不同团队所拥有的命名空间,突出显示的route指令引用了一个VSR资源。

apiVersion: k8s.nginx.org/v1kind: VirtualServer
metadata:
  name: webapp
spec:
  host: webapp.example.com
  policies:
  - name: waf-prod 
  tls:
    secret: app-secret
  upstreams:
  - name: webapp-prod
    service: webapp-svc
    port: 80
  routes:
  - path: /v2
    route: test/test
  - path: /v1
    action:
      pass: webapp-prod

负责管理test命名空间的团队可以使用该命名空间中的VSR资源设置自己的参数和WAF策略。

apiVersion: k8s.nginx.org/v1kind: VirtualServerRoute
metadata:
  name: test 
  namespace: test
spec:
  host: webapp.example.com
  upstreams:
  - name: webapp 
    service: webapp-test-svc
    port: 80
  subroutes:
  - path: /v2
    policies:
    - name: waf-test
    action:
      pass: webapp

此示例按命名空间隔离租户,并为webapp-test-svc服务在test命名空间中应用不同的WAF策略。它说明了如何通过将资源委派给不同团队并使用对象进行封装,简化新功能测试,同时不影响生产环境中的应用。

1.11.0版本还有哪些新功能?

NGINX Ingress Controller 1.11.0延续了我们提供生产级Ingress控制器的承诺,兼具灵活性、强大功能和易用性。除了WAF和TS方面的改进外,1.11.0版本还包括以下增强功能:

更多注解的验证

在版本1.10.0中引入的注解验证改进基础上,我们现在还会验证以下注解:

注解验证nginx.org/client-max-body-size 必须是有效的偏移量nginx.org/fail-timeout 必须是有效的时间值nginx.org/max-conns 必须是有效的非负整数nginx.org/max-fails 必须是有效的非负整数nginx.org/proxy-buffer-size 必须是有效的大小值nginx.org/proxy-buffers 必须是有效的代理缓冲区规范nginx.org/proxy-connect-timeout 必须是有效的时间值nginx.org/proxy-max-temp-file-size 必须是有效的大小值nginx.org/proxy-read-timeout 必须是有效的时间值nginx.org/proxy-send-timeout 必须是有效的时间值nginx.org/upstream-zone-size 必须是有效的大小值

如果应用 Ingress 资源时注解值无效,Ingress Controller 将拒绝该资源,并从 NGINX 中移除相应配置。

策略状态信息

现在,kubectl get policy 命令会报告策略状态(Valid 或 Invalid);对于单个TS,还会报告自定义消息以及最近一次更新的原因。

$ kubectl get policy  NAME              STATE   AGE
  webapp-policy     Valid   30s

$ kubectl describe policy webapp-policy
. . .
Status:
  Message:  Configuration for default/webapp-policy was added or updated
  Reason:   AddedOrUpdated
  State:    Valid

与 Istio 的兼容性

NGINX Ingress Controller现在可用作Istio服务网格内运行的应用的Ingress控制器。这样,无需采用变通方法,即可继续在基于Istio的环境中使用NGINX Ingress Controller提供的高级功能。此集成有两项要求:

  • 将Istio边车注入NGINX Ingress Controller部署
  • 仅向后端发送一个HTTP Host标头

为满足第一项要求,请在NGINX Ingress Deployment文件的annotations字段中添加以下内容。

annotations:   traffic.sidecar.istio.io/includeInboundPorts: "" 
  traffic.sidecar.istio.io/excludeInboundPorts: "80,443"         
  traffic.sidecar.istio.io/excludeOutboundIPRanges: "10.90.0.0/16,10.45.0.0/16"     sidecar.istio.io/inject: 'true'

第二项要求通过更改requestHeaders字段的行为来实现。在以前的版本中,使用以下配置时,会向后端发送两个Host标头:$host和指定值bar.example.com。

apiVersion: k8s.nginx.org/v1kind: VirtualServer
metadata:
  name: foo 
spec:
  host: foo.example.com
  upstreams:
  - name: foo
    port: 8080
    service: backend-svc
    use-cluster-ip: true
  routes:
  - path: "/"
    action:
      proxy:
        upstream: foo
        requestHeaders: set: - name: Host value: bar.example.com

在1.11.0及更高版本中,仅发送指定的值。要发送$host,请完全省略requestHeaders字段。

上游端点的集群IP地址

现在,NGINX Ingress Controller配置中的上游端点可以使用服务的Cluster-IP地址填充,而不再使用各个Pod端点的IP地址。要让NGINX Ingress Controller将流量路由到Cluster-IP服务,请在VS或VSR配置的use-cluster-ip: true字段添加到upstreams部分:

upstreams:  - name: tea
    service: tea-svc
    port: 80
    use-cluster-ip: true
  - name: coffee
    service: coffee-svc
    port: 80
    use-cluster-ip: true

资源

有关1.11.0版本的完整变更日志,请参阅《发行说明》。

要试用搭配NGINX Plus和NGINX App Protect的NGINX Ingress Controller for Kubernetes,请立即开始30天免费试用,或联系我们,讨论您的用例。

要试用搭配NGINX Open Source的NGINX Ingress Controller,可以获取发布版源代码,也可以从DockerHub下载预构建容器。

如需了解不同Ingress控制器之间的差异,请参阅我们博客中的文章“等等,我使用的是哪款适用于Kubernetes的NGINX Ingress Controller?”。


分享

关于作者

相关博客文章

NGINX Plus R26 正式发布
NGINX | 2022/02/15

NGINX Plus R26 正式发布

NGINX Plus R26通过缓存JSON Web密钥集加快JWT验证,并强化TLS握手,从而提升安全性。NGINX JavaScript的新功能包括增强对异步函数的支持,以及实现WebCrypto API。

使用NGINX App Protect DoS保护gRPC应用,抵御严重的DoS攻击
NGINX | 2022/02/10

使用NGINX App Protect DoS保护gRPC应用,抵御严重的DoS攻击

gRPC具备开发人员设计和部署现代应用所需的速度与灵活性,但其开放性也使其极易受到第7层DoS攻击。NGINX App Protect DoS可保护gRPC应用免受此类破坏性攻击。

Ingress Controller 选型指南(第 2 部分):风险与面向未来的规划
NGINX | 2021/09/13

Ingress Controller 选型指南(第 2 部分):风险与面向未来的规划

了解选择错误的Ingress控制器可能带来的风险,以及如何从关键方面着手,让您的选择更好地适应未来需求。

NGINX Plus R19 正式发布
NGINX | 2019/09/03

NGINX Plus R19 正式发布

NGINX Plus R19扩展了监控功能,不仅提供更多指标,还新增了指标分析方式;增加试运行模式,用于测试限速效果;增强键值存储,以支持IP地址范围;并使限速更加动态。

NGINX现已正式加入F5
NGINX | 2019/05/09

NGINX现已正式加入F5

NGINX现已正式成为F5的一部分。Gus Robertson现任F5 NGINX业务部门负责人。他阐述了两家公司在人才、文化和愿景方面融合的价值,以及双方将如何携手增强NGINX的开源产品和商业产品。

使用NGINX和NGINX Plus实现高性能缓存
NGINX | 2016/08/24

使用NGINX和NGINX Plus实现高性能缓存

我将介绍NGINX在内容缓存和性能方面的工作原理,并分享一些控制NGINX内容缓存方式的技巧。