If your platform migrated its routing layer to Gateway API — and after ingress-nginx reached end-of-life on March 24, 2026, roughly half of all cloud-native environments had a reason to — you already own the API objects that a service mesh would use to manage traffic inside the cluster. That is the quiet consequence of GAMMA (Gateway API for Mesh Management and Administration): the same HTTPRoute and GRPCRoute resources your control plane provisions for tenant ingress can bind directly to Service resources and govern east-west traffic, and this has been GA in the Gateway API Standard Channel since v1.1.0 shipped in May 2024.
Here is the verdict up front, because it is the question the title asks: for most single-tenant-per-namespace PaaS workloads, GAMMA plus the ingress layer you already own covers the east-west features you would have stood up a mesh for — retries, timeouts, and traffic splitting — while the mesh's remaining exclusives (mTLS everywhere, authorization policy, uniform telemetry) carry a per-pod resource bill and a debugging surface that are worth deferring until a compliance requirement or a deep internal call graph actually demands them. The capability map looks like this:
| Capability | Gateway API (ingress only) | + GAMMA (mesh routes) | Full service mesh |
|---|---|---|---|
| North-south routing, TLS at the edge | ✅ | ✅ | ✅ |
| Per-route timeouts east-west | ❌ | ✅ | ✅ |
| Retries between internal services | ❌ | ✅ | ✅ |
| Canary / weighted splits east-west | ❌ | ✅ | ✅ |
| mTLS between all workloads | ❌ | ❌ | ✅ |
| Authorization policy (east-west) | ❌ | ❌ | ✅ |
| Uniform L7 telemetry for every hop | ❌ | ❌ | ✅ |
| Extra data-plane cost per pod | None | Mesh-dependent* | Sidecar or ztunnel overhead |
*GAMMA needs a conformant data plane (Linkerd, Istio, Kuma, Cilium), but you adopt only the routing semantics — and, as we will see, the route objects survive intact if you later turn on the rest.
The rest of this post walks through what GAMMA actually is, a worked example of what it buys a platform whose reconciler already writes HTTPRoute objects, the honest list of what it does not give you, what the full mesh costs in numbers, and a decision framework for a self-hosted PaaS.
What GAMMA Actually Is: The parentRef Flip
The GAMMA initiative started in 2022 as a vendor-neutral workstream inside the Gateway API subproject, asking how service mesh configuration should fit the same resource model as ingress. The answer it landed on is elegantly small. For ingress, an HTTPRoute attaches to a Gateway:
spec:
parentRefs:
- name: tenant-gateway
kind: GatewayFor mesh traffic, the same resource attaches to a Service instead:
spec:
parentRefs:
- name: api
kind: Service
group: ""
port: 8080That is the whole flip. Because a cluster typically runs exactly one mesh, GAMMA skips Gateway and GatewayClass entirely for east-west traffic — the route binds straight to the Service that receives the traffic. Mesh support reached Experimental status in Gateway API v0.8.0 (August 2023) and graduated to the Standard Channel in v1.1.0, alongside GRPCRoute. Conformant implementations today include Istio, Linkerd 2.14+, Kuma (the engine under Kong Mesh), and Cilium's GAMMA support.
Two scoping rules matter for a multi-tenant platform:
- Producer routes live in the same namespace as the parent
Serviceand apply to all traffic sent to it — the service owner's defaults. - Consumer routes live in the consuming workload's namespace and apply only to calls from that namespace — a caller's private overrides.
Consumer routes deliberately cannot reach across namespaces, so one tenant can never rewrite another tenant's traffic policy. For a single-tenant-per-namespace PaaS, that boundary lines up exactly with the isolation model the platform already enforces.
What GAMMA Buys a Platform That Already Speaks Gateway API
Consider the typical shape of a tenant app on a git-push platform: a web service and an api service in one namespace, deployed from the same repo. The tenant wants three things a plain ClusterIP Service cannot give them: a request timeout on calls from web to api, automatic retries on transient 5xx responses, and a canary split when they ship api-v2.
With a GAMMA-conformant data plane installed (Linkerd is the lightest-weight path), all three are one HTTPRoute bound to the api Service — using Linkerd's route annotations for retry and timeout policy, and weighted backendRefs for the split:
apiVersion: gateway.networking.k8s.io/v1
kind: HTTPRoute
metadata:
name: api-policy
namespace: tenant-a
annotations:
retry.linkerd.io/http: 5xx
retry.linkerd.io/limit: "2"
timeout.linkerd.io/request: 2s
spec:
parentRefs:
- name: api
kind: Service
group: ""
port: 8080
rules:
- backendRefs:
- name: api
port: 8080
weight: 90
- name: api-v2
port: 8080
weight: 10Ninety percent of traffic keeps hitting api, ten percent canaries to api-v2, every request gets a 2-second budget, and requests that fail with a 5xx are retried up to twice — since Linkerd 2.16, timeouts and retries compose, so a timed-out request is itself eligible for retry.
Now look at that YAML from the platform operator's chair. If your control plane already generates HTTPRoute objects for tenant ingress — which it does, if you migrated off ingress-nginx onto Gateway API — then east-west traffic policy is the same object type through the same reconciler code path. There is no second configuration language, no mesh-specific CRD your platform has to template, validate, and garbage-collect. A "canary deploy" feature in your dashboard becomes a weight field on an object you already own. That is the entire GAMMA value proposition for a PaaS: the marginal cost of exposing east-west routing to tenants drops to nearly zero, because the Gateway API for mesh deliberately reuses the north-south vocabulary.
What GAMMA Explicitly Does Not Give You
GAMMA is a routing specification, not a mesh replacement, and it is worth being precise about the gap — this is where "just use Gateway API" gets oversold.
- No mTLS. Workload-to-workload encryption and identity are entirely the mesh implementation's business. GAMMA says nothing about it; adopting GAMMA routes does not encrypt a single hop.
- No authorization policy. "Only
webmay callapi" is not expressible in a GAMMA route. Per GEP-1324, authorization policies are future GAMMA work, not shipped spec. - No uniform telemetry. The automatic golden-signal metrics, access logs, and distributed traces for every hop that make meshes attractive for debugging come from the mesh's proxies, not from the route objects.
- A real spec limitation: consumer routes are per-namespace, not per-workload. If two workloads in the same namespace call the same upstream
Service, they cannot set different timeouts for it via HTTPRoutes — the mesh overview docs call this out explicitly. For single-tenant namespaces this rarely bites, but it is a known edge.
So the honest framing is: GAMMA standardizes the traffic management third of the classic mesh triad (traffic, security, observability) into objects you already hold. The other two thirds still require buying the mesh — and the mesh has a price tag.
What the Full Mesh Costs: The Numbers
The canonical sidecar mesh attaches an Envoy proxy to every pod. A typical sidecar requests 100m CPU and 128Mi of memory — roughly a 20% resource increase per pod for a common workload profile — and the proxy image itself weighs in around 150–250MB. Small per-pod numbers compound at fleet scale: Solo.io's analysis of a 10,000-pod platform puts proxy memory overhead alone at roughly $127K per year at AWS on-demand pricing, before counting CPU.
Istio's ambient mode restructures the bill rather than eliminating it: L4 traffic moves to a per-node ztunnel DaemonSet (so the cost scales with nodes, not pods — benchmarks show around 4x lower memory use and about 25% less CPU than sidecars), but the L7 features GAMMA routes actually exercise require per-service-account waypoint proxies, which bring some of the per-workload cost back. Linkerd's micro-proxy sidecars are far lighter than Envoy, and in Defense Unicorns' testing averaged around 8 millicores and 40Mi each — but they are still one more container in every tenant pod the platform schedules, bills, and debugs.
And the operational cost is the bigger line item for a small platform team. With a mesh in the data path, an incident investigation now spans application logs, proxy logs, mTLS certificate state, routing rules, and control-plane sync status. Every Kubernetes upgrade gains a mesh-compatibility check. For a PaaS whose pitch is "push a git repo, get a running service," every one of those layers is invisible to tenants and fully owned by the operator.
The Decision Framework for a Self-Hosted PaaS
Put the three preceding sections together and the decision falls out along workload shape:
The mesh earns its keep when:
- A compliance regime (PCI-DSS, HIPAA, FedRAMP-style controls) mandates encryption in transit inside the cluster, not just at the edge — mTLS-by-default is the mesh's killer feature and nothing in Gateway API substitutes for it.
- Tenants run deep internal call graphs — five, ten, twenty services calling each other — where per-hop telemetry and circuit breaking stop being nice-to-haves.
- Multiple teams share namespaces or trust boundaries run through the cluster, and you need workload-identity-based authorization, not just NetworkPolicy's IP/label reachability.
The ingress layer plus GAMMA covers you when:
- Tenant apps are the PaaS-typical one-to-three services in their own namespace. TLS terminates at the platform's gateway, NetworkPolicy walls namespaces off from each other, and the east-west features tenants actually ask for — timeouts, retries, canaries — are GAMMA routes.
- Your platform team is small. The 20% per-pod overhead is arguably the cheap part; the always-on operational surface of a mesh control plane is the expensive part, and it lands on the same people running etcd backups and node upgrades.
The strategic point that makes this a low-regret call: GAMMA is the incremental path, not the opposite of the mesh. Because Istio, Linkerd, Kuma, and Cilium all implement the same GA spec, the HTTPRoute objects your platform writes today bind to Services identically under whichever mesh you may adopt in two years. Turning on mTLS later is additive — annotate, inject or enroll, done — and none of your routing configuration is stranded. Compare that with building tenant traffic features on a mesh-proprietary CRD today and owning a migration when you change meshes tomorrow.
The Platform Already Owns the Right Layer
The ingress-nginx retirement forced a generation of platforms onto Gateway API in early 2026, and GAMMA quietly turned that migration into a down payment on east-west traffic management. A self-hosted PaaS sitting on that foundation can ship retries, timeouts, and canary deploys as platform features — expressed in objects its reconciler already creates, scoped by the namespace boundaries it already enforces — and defer the service mesh until mTLS or authorization policy is a real requirement rather than an architecture-diagram aspiration. When that day comes, the routes come along unchanged.
That is the pattern worth internalizing: prefer the standard, reusable API surface over the heavier subsystem, and keep the upgrade path open instead of paying for capabilities before they are needed.
Bex.co is the open-source, AI-native Render alternative — push a git repo, get a running HTTPS service on machines you own, with the platform's Kubernetes and Cluster API machinery kept out of the tenant's way. Star the repo on GitHub or deploy your first app today.
Sources
- Gateway API v1.1: Service mesh, GRPCRoute, and a whole lot more — Kubernetes Blog
- Gateway API for Service Mesh — Gateway API docs
- GEP-1324: Service Mesh in Gateway API
- Gateway API v0.8.0: Introducing Service Mesh Support — Kubernetes Blog
- Retries and Timeouts — Linkerd docs
- Announcing Linkerd 2.16 — Linkerd Blog
- GAMMA Support — Cilium documentation
- Bringing Gateway API for Mesh to Kuma — Kong
- How Ambient Mesh Delivers Advanced Resource and Cost Savings — Solo.io
- Istio Ambient: Simplifying Service Mesh in UDS Core — Defense Unicorns
- Ingress NGINX: Statement from the Kubernetes Steering and Security Response Committees



