前段时间,Kubernetes SIG-Network[1] 发布了备受期待的 Gateway API 0.5.0 版。主要组件的 Api 正在升级到 beta (v1beta1),这意味着我们很快就会看到更多使用这些原语的项目。
让我们回顾一下 Gateway API 的基础知识,它旨在解决什么,它有什么好处。
Gateway API 是新的官方 Kubernetes 资源的集合,它们定义了由供应商实现的规范,类似于 Ingress 由 Google、Amazon 等实现的方式。
它引入的新资源有:
SIG-Network 所述的新Gateway API[2]的目标是:
header
的匹配、流量加权和其他核心功能,这些功能只能通过自定义注释在 Ingress 中实现。Gateway 和 GatewayClass 是基础设施级别的组件,它们是 XRoute 组件的底层(这就是这个版本令人兴奋的原因)。
让我们看看这个层次结构实际上是什么样子的:
Gateway API 的第一个直接好处是它可以更好地分离关注点。
Ingress 对象很棒,是 Devops 和 App 工程师通常需要一起弄清楚配置的微妙对象,应用程序开发人员知道应用程序的路由,但通常不知道诸如 TLS 证书之类的细节,这些细节通常在 Devops 域,在同一个 Ingress 对象中发生的这个和其他配置正在阻止双方的自治,并为错误配置留出更多空间。
在新的 Gateway API 中,Gateway API 将这些和其他配置解耦为 Gateway 和 Route 对象,允许应用程序工程师和 Devops 工程师/集群操作员自由安全地行动,如下所示:
新 API 的另一个主要好处是,更多功能在 Gateway API 对象定义中表达,而不是让供应商通过自定义注释来定义。 此增强提供了几个好处:
让我们举个例子,这里是您如何使用 Ingress 对象和 AWS alb 定义流量拆分。
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
name: "groundcover-app"
namespace: "app"
annotations:
kubernetes.io/ingress.class: alb
alb.ingress.kubernetes.io/scheme: internet-facing
alb.ingress.kubernetes.io/target-type: ip
alb.ingress.kubernetes.io/actions.blue-green: |
{
"type":"forward",
"forwardConfig":{
"targetGroups":[
{
"serviceName":"groundcover-app-v1",
"servicePort":"80",
"weight":80
},
{
"serviceName":"groundcover-app-v2",
"servicePort":"80",
"weight":20
}
]
}
}
labels:
app: groundcover-app
spec:
rules:
- http:
paths:
- path: /
pathType: Prefix
backend:
service:
name: blue-green
port:
name: use-annotation
正如您所看到的,这里有很多供应商特定的定义,大量使用注释,但是,使用新的 Gateway API,等效的将是
apiVersion: gateway.networking.k8s.io/v1beta1
kind: Gateway
metadata:
name: prod-web
spec:
gatewayClassName: acme-lb
listeners:
- protocol: HTTP
port: 80
name: prod-web-gw
allowedRoutes:
namespaces:
from: Same
apiVersion: gateway.networking.k8s.io/v1beta1
kind: HTTPRoute
metadata:
name: "hello-kubernetes"
labels:
gateway: prod-web-gw
spec:
hostnames:
- app.groundcover.com
rules:
- backendRefs:
- name: groundcover-app-v1
port: 80
weight: 90
- name: groundcover-app-v2
port: 80
weight: 10
如您所见,这里的配置要简洁很多,并且定义是完全可移植的!
作为理解的一部分,在 Kubernetes 集群中有不同的角色操作不同的组件,因此需要支持跨命名空间引用,因为这些不同的组织单元通常在不同的命名空间中运行,同时仍然使用通用的基础设施组件,例如 TLS 证书,主机名等等。
为了实现上述功能,Gateway API 支持在一个集群中建立 Gateway 对象,并在引用它的每个应用程序/组织单元命名空间中创建 Route 对象。
以下是此类设置的说明:
基础设施运营商还可以明确限制谁可以将 Route 对象注册到网关,在我们的示例中,网关定义如下:
apiVersion: gateway.networking.k8s.io/v1beta1
kind: Gateway
metadata:
name: shared-gateway
namespace: infra-ns
spec:
gatewayClassName: shared-gateway-class
listeners:
- name: https
hostname: "foo.example.com"
protocol: HTTPS
port: 443
allowedRoutes:
namespaces:
from: Selector
selector:
matchLabels:
shared-gateway-access: "true"
tls:
certificateRefs:
- name: foo-example-com
网关将只允许带有 shared-gateway-access: "true" 标签的命名空间使用共享网关,因此在我们的示例中,命名空间对象必须定义如下:
apiVersion: v1
kind: Namespace
metadata:
name: infra-ns
labels:
shared-gateway-access: "true"
---
apiVersion: v1
kind: Namespace
metadata:
name: site-ns
labels:
shared-gateway-access: "true"
---
apiVersion: v1
kind: Namespace
metadata:
name: store-ns
labels:
shared-gateway-access: "true"
一旦部署了这些层,应用程序开发人员就可以注册他们的 Route 对象,引用共享网关。
在我们的示例中,store Route 对象将如下所示:
apiVersion: gateway.networking.k8s.io/v1beta1
kind: HTTPRoute
metadata:
name: store
namespace: store-ns
spec:
parentRefs:
- name: shared-gateway
namespace: infra-ns
rules:
- matches:
- path:
value: /store
backendRefs:
- name: store
port: 8080
本文严重依赖 Kubernetes SIG-Network,他们在记录[3]新 API 方面做得非常出色,如果您现在有兴趣尝试 Gateway API,他们在此处[4]列出了可用的实现。
Kubernetes 正在迅速变化,尽管适应这些变化很困难,有时令人沮丧。但这绝对值得。
在我看来,社区在收集案例研究并以负责任的方式统一它们方面做得非常出色。
让 Kubernetes 用户能够在通用 API 方面建立专业知识,而不是成为特定于供应商的专家,这将有助于构建更成熟的产品,专注于创造价值并更轻松地在不同环境中应用我们的技能。
原文:https://www.groundcover.com/blog/k8s-gateway-api
[1]
Kubernetes SIG-Network: https://github.com/kubernetes/community/tree/master/sig-network
[2]
Gateway API: https://gateway-api.sigs.k8s.io/
[3]
记录: https://gateway-api.sigs.k8s.io/
[4]
在此处: https://gateway-api.sigs.k8s.io/implementations/
- END -