In this post we’re going to use a Gateway and HTTPRoutes to create a global load balancer and configure routes as an alternative to using the traditional ingress approach.
Cheat Sheet:
kubectl get gateways
kubectl describe gateways <name>
kubectl get httproutes
kubectl describe httproutes <route name>
References:
https://gateway-api.sigs.k8s.io/guides/multiple-ns/
https://cloud.google.com/kubernetes-engine/docs/how-to/deploying-gateways#external-gateway
https://cloud.google.com/kubernetes-engine/docs/concepts/gateway-api
What you’ll need:
Kubernetes cluster (we’re using Autopilot)
Working installs of gcloud and helm
Install Sample Applications:
For this example we’re going to install pgadmin and phpmyadmin via helm charts.
- pgadmin chart is available at https://artifacthub.io/packages/helm/runix/pgadmin4
- phpmyadmin chart available from https://bitnami.com/stack/phpmyadmin/helm
This example assumes that pgadmin, phpmyadmin, and the following yamls are in the same namespace, ie, default. Review the multiple-ns link the references if needed.
Configure gateway.yaml:
Create a gateway.yaml file and add the following contents:
kind: Gateway
apiVersion: gateway.networking.k8s.io/v1beta1
metadata:
name: external-http
# annotations:
# networking.gke.io/certmap: store-example-com-map
spec:
gatewayClassName: gke-l7-global-external-managed
listeners:
- name: http
protocol: HTTP
port: 80
Configure routes.yaml:
Next, create a routes.yaml file and put the following contents inside of it.
Pro Tip: Note the RequestHeaderModifier below — this tells pgAdmin to update its internal base paths. Hat tip to Joey for finding that nugget here!
kind: HTTPRoute
apiVersion: gateway.networking.k8s.io/v1beta1
metadata:
name: pgadmin-external
spec:
parentRefs:
- kind: Gateway
name: external-http
rules:
- backendRefs:
- name: phpmyadmin
port: 80
- matches:
- path:
value: /pga
filters:
- type: RequestHeaderModifier
requestHeaderModifier:
add:
- name: X-Script-Name
value: /pga
backendRefs:
- name: pgadmin-pgadmin4
port: 80
Create a Health Check Policy for pgAdmin:
During our testing we needed to create a healthcheck policy for pgAdmin because the default one created by using the gateway and route was generating an http healthcheck that was marking the pods as bad. The following will create a TCP healthcheck that will work. Note — we did not try the http healthcheck AFTER we modified the headers in the route.yaml for pgAdmin.
apiVersion: networking.gke.io/v1
kind: HealthCheckPolicy
metadata:
name: pgadmin-healthcheck
# namespace: default
spec:
default:
checkIntervalSec: 5
timeoutSec: 5
healthyThreshold: 5
unhealthyThreshold: 2
logConfig:
enabled: true
config:
type: TCP
httpHealthCheck:
portSpecification: USE_SERVING_PORT
proxyHeader: NONE
targetRef:
group: ""
kind: Service
name: pgadmin-pgadmin4
Deploy:
Now we need to deploy each of the yamls as follows:
kubectl apply -f gateway.yaml
kubectl apply -f routes.yaml
kubectl apply -f pgadmin-healthcheck.yaml
Check the Status:
You can check the status of the gateway, etc by doing the following:
kubectl:
kubectl get gateways
kubectl describe gateways <name>
kubectl get httproutes
kubectl describe httproutes <route name>
Via Portal:
You can visit the load balancer section in portal to see the newly created loadbalancer, backends, and routes.
Acknowledgements:
Many thanks to Joey for working tirelessly with me as we figured this out!