Gateway API is the next-generation service networking API from the Kubernetes community. Cloud-native API Gateway supports the Kubernetes Gateway API standard, which allows you to use declarative Gateway and HTTPRoute resources to configure gateway routes and expose services in your cluster to external users.
Background
Gateway API is the next-generation service networking API from the Kubernetes community. It provides more expressive, extensible, and role-oriented routing and load balancing interfaces than the traditional Ingress API. Gateway API introduces a clearer resource model hierarchy, including GatewayClass, Gateway, and HTTPRoute, and supports richer traffic management capabilities.
Prerequisites
You have a Cloud-native API Gateway instance with engine version 2.1.16 or later. If your instance is running an earlier version, upgrade it first.
You have a Kubernetes cluster (ACK cluster) running version 1.24 or later.
You have installed the Gateway API CRDs, version v1.3.0 or earlier. The current gateway supports the Gateway API protocol up to v1.3.0, so we recommend installing v1.3.0. If you use an Alibaba Cloud ACK cluster, we recommend that you install the Gateway API CRDs using component management. On the ACK console, go to Applications > Helm, select gateway-api, and click Update to change the version.
Configure Gateway API listening
Enable Gateway API listening
Log on to the Cloud-native API Gateway console, select the target gateway instance, go to the API page, and click Create API.
Under HTTP API, click Import Gateway API.
In the creation panel, enter an API name and description, and select the source ACK cluster. In the Custom Configuration area, configure the namespace and GatewayClass to monitor. By default, the gateway listens for Gateway API resources in all namespaces in the cluster. After you complete the configuration, click OK.
Select the newly created API. If Gateway API resources already exist in the ACK cluster and are within the configured listening scope, the corresponding route entries appear in the route list, indicating that the gateway is successfully monitoring Gateway API resources.
For compatibility with open-source Higress, Cloud-native API Gateway listens by default for resources whose GatewayClass is higress, regardless of the filter configurations.
Modify Gateway API listening
Log on to the Cloud-native API Gateway console, select the target gateway instance, go to the API page, and then click the Gateway API that you want to modify.
In the upper-right corner, click Edit. Adjust the monitored GatewayClass and namespace, and then click Confirm. The configuration takes effect immediately. If you leave a configuration field empty, all resources of that type are monitored.
Example
After meeting the prerequisites and configuring listening for Gateway API, you can follow this example to route services using Gateway API resources.
Deploy a sample application
Create a file named
httpbin.yamlwith the following content:apiVersion: apps/v1 kind: Deployment metadata: name: httpbin namespace: default spec: replicas: 1 selector: matchLabels: app: httpbin template: metadata: labels: app: httpbin version: v1 spec: containers: - image: registry.cn-hangzhou.aliyuncs.com/mse-ingress/go-httpbin args: - "--port=8080" - "--version=v1" imagePullPolicy: Always name: httpbin ports: - containerPort: 8080 --- apiVersion: v1 kind: Service metadata: name: httpbin namespace: default spec: type: ClusterIP ports: - port: 80 targetPort: 8080 protocol: TCP selector: app: httpbinDeploy the application:
kubectl apply -f httpbin.yamlVerify that the application is running:
kubectl get pods -l app=httpbinExpected output:
NAME READY STATUS RESTARTS AGE httpbin-5d4f8b6c7f-xxxxx 1/1 Running 0 30s
Deploy a gateway and routes
Once listening is enabled, Cloud-native API Gateway creates a GatewayClass named higress by default. You can also create your own GatewayClass resource as needed.
(Optional) To use a custom GatewayClass, create a file named
gatewayclass.yaml:apiVersion: gateway.networking.k8s.io/v1 kind: GatewayClass metadata: name: apig # You can customize the name. spec: controllerName: higress.io/gateway-controllerkubectl apply -f gatewayclass.yamlCreate a file named
gateway.yamlwith the following content:apiVersion: gateway.networking.k8s.io/v1 kind: Gateway metadata: name: apig-gateway namespace: default spec: gatewayClassName: apig listeners: - name: http protocol: HTTP port: 80 hostname: "*.example.com" allowedRoutes: namespaces: from: Same --- apiVersion: gateway.networking.k8s.io/v1 kind: HTTPRoute metadata: name: httpbin-route namespace: default spec: parentRefs: - name: apig-gateway hostnames: - "demo.example.com" rules: - matches: - path: type: PathPrefix value: / backendRefs: - kind: Service name: httpbin port: 80Deploy the Gateway and routing rules:
kubectl apply -f gateway.yamlVerify that the Gateway is ready. Wait about 2 minutes, and then run the following command:
kubectl get gateway apig-gatewayExpected output:
NAME CLASS ADDRESS PROGRAMMED AGE apig-gateway apig nlb-xxxx True 2mThe Gateway is ready when the
PROGRAMMEDstatus isTrue.Verify that the route is monitored correctly. Log on to the Cloud-native API Gateway console, go to the target gateway instance, click API, find the API of type Gateway API, and then click it to view the route list. If the Gateway API route created in the cluster appears in the list, the route is monitored correctly.
Test application access
Log on to the Cloud-native API Gateway console, select the target gateway instance, and on the Overview > Basic Information page, find the gateway endpoint address.
Access the application. Replace
<gateway-endpoint-address>with the address that you obtained in the previous step.curl -H "Host: demo.example.com" http://<gateway-endpoint-address>/versionExpected output:
version: v1 hostname: httpbin-5d4f8b6c7f-xxxxx
Use cases
The following examples are based on the official Gateway API documentation. For more scenarios, see the Gateway API official user guide.
Use case 1: Modify request headers with a filter
HTTPRoute filters allow you to apply additional processing during the request or response phase. The following example shows how to use a filter to add a custom request header to requests that are sent to the backend.
Create a file named
httproute-filter.yaml:apiVersion: gateway.networking.k8s.io/v1 kind: HTTPRoute metadata: name: demo-filter spec: parentRefs: - name: apig-gateway hostnames: - "filter.example.com" rules: - matches: - path: type: PathPrefix value: / filters: - type: RequestHeaderModifier requestHeaderModifier: add: - name: my-header value: foo backendRefs: - kind: Service name: httpbin port: 80This configuration creates an HTTPRoute resource named
demo-filter. After deployment, the request headermy-header: foois automatically added to requests that access thefilter.example.comdomain.Deploy the routing rule:
kubectl apply -f httproute-filter.yamlAccess the application:
curl -H "Host: filter.example.com" http://<gateway-endpoint-address>/headerThe output includes the automatically added request header:
headers: { ... "My-Header": [ "foo" ], ... }
Use case 2: Weight-based traffic splitting
By setting weights for multiple backend services, you can distribute requests proportionally. This is a common practice for canary releases.
Create a file named
nginx.yamlto deploy two NGINX applications. Theold-nginxservice returns the stringold, and thenew-nginxservice returns the stringnew.apiVersion: apps/v1 kind: Deployment metadata: name: old-nginx spec: replicas: 1 selector: matchLabels: run: old-nginx template: metadata: labels: run: old-nginx spec: containers: - image: registry.cn-hangzhou.aliyuncs.com/acs-sample/old-nginx imagePullPolicy: Always name: old-nginx ports: - containerPort: 80 protocol: TCP restartPolicy: Always --- apiVersion: v1 kind: Service metadata: name: old-nginx spec: type: ClusterIP ports: - port: 80 protocol: TCP targetPort: 80 selector: run: old-nginx --- apiVersion: apps/v1 kind: Deployment metadata: name: new-nginx spec: replicas: 1 selector: matchLabels: run: new-nginx template: metadata: labels: run: new-nginx spec: containers: - image: registry.cn-hangzhou.aliyuncs.com/acs-sample/new-nginx imagePullPolicy: Always name: new-nginx ports: - containerPort: 80 protocol: TCP restartPolicy: Always --- apiVersion: v1 kind: Service metadata: name: new-nginx spec: type: ClusterIP ports: - port: 80 protocol: TCP targetPort: 80 selector: run: new-nginxCreate a file named
httproute-weight.yaml:apiVersion: gateway.networking.k8s.io/v1 kind: HTTPRoute metadata: name: demo-weight spec: parentRefs: - name: apig-gateway hostnames: - "weight.example.com" rules: - matches: - path: type: PathPrefix value: / backendRefs: - kind: Service name: old-nginx port: 80 weight: 90 - kind: Service name: new-nginx port: 80 weight: 10NoteThe
weightfield is a relative value and does not need to sum to 100. In this configuration, the 90:10 ratio means that approximately 90% of the traffic is routed toold-nginxand 10% is routed tonew-nginx.Deploy the applications and routing rules:
kubectl apply -f nginx.yaml kubectl apply -f httproute-weight.yamlAccess the application multiple times to verify the traffic distribution:
for i in {1..10}; do curl -s -H "Host: weight.example.com" http://<gateway-endpoint-address>/; echo; doneIn the expected output, most responses return
oldand a few returnnew, at a ratio of approximately 9:1.
Use case 3: Header-based canary routing
By using header-matching rules, you can route traffic with a specific request header to a canary service, while routing all other traffic to a stable version. This method is often used to verify a canary version without affecting production users.
Based on the previous example, deploy a canary version of the httpbin service. Create a file named
httpbin-canary.yaml:apiVersion: apps/v1 kind: Deployment metadata: name: httpbin-canary namespace: default spec: replicas: 1 selector: matchLabels: app: httpbin-canary template: metadata: labels: app: httpbin-canary version: v2 spec: containers: - image: registry.cn-hangzhou.aliyuncs.com/mse-ingress/go-httpbin args: - "--port=8080" - "--version=v2" imagePullPolicy: Always name: httpbin ports: - containerPort: 8080 --- apiVersion: v1 kind: Service metadata: name: httpbin-canary namespace: default spec: type: ClusterIP ports: - port: 80 targetPort: 8080 protocol: TCP selector: app: httpbin-canarykubectl apply -f httpbin-canary.yamlCreate a file named
httproute-canary.yamlto configure header-based canary routing rules:apiVersion: gateway.networking.k8s.io/v1 kind: HTTPRoute metadata: name: demo-canary spec: parentRefs: - name: apig-gateway hostnames: - "canary.example.com" rules: - matches: - headers: - type: Exact name: env value: canary backendRefs: - kind: Service name: httpbin-canary port: 80 - backendRefs: - kind: Service name: httpbin port: 80This configuration defines two routing rules: traffic with the request header
env: canaryis routed to the canary servicehttpbin-canary, while all other traffic is routed to the stable versionhttpbin.Deploy the routing rule:
kubectl apply -f httproute-canary.yamlVerify the canary route by accessing the stable version without the header:
curl -H "Host: canary.example.com" http://<gateway-endpoint-address>/versionExpected output:
version: v1 hostname: httpbin-f4c58d59c-xxxxxAccess the canary version with the
env: canaryrequest header:curl -H "Host: canary.example.com" -H "env: canary" http://<gateway-endpoint-address>/versionExpected output:
version: v2 hostname: httpbin-canary-585859f9b6-xxxxx