Skip to content

BackendLBPolicy

The BackendLBPolicy CRD bundles three backend-level traffic management features into a single policy resource: session persistence, load balancing, and circuit breaking. It is a Gateway API local policy, which means it targets specific backends in the same namespace.

apiVersion: gateway.networking.k8s.io/v1alpha2
kind: BackendLBPolicy
metadata:
name: orders-lb-policy
namespace: nantian-demo
spec:
targetRefs:
- group: ""
kind: Service
name: orders-service
session_persistence:
sessionName: orders-session
type: Cookie
absoluteTimeout: 30m
idleTimeout: 10m
cookie:
lifetimeType: Session
loadBalancing:
type: ConsistentHash
consistentHash:
keyType: Header
headerName: x-tenant-id
circuitBreaker:
maxInflightRequests: 200

The targetRefs field specifies which backends the policy applies to. Each entry is a LocalPolicyTargetReference:

FieldDescription
groupAPI group of the target. Empty string for core Service.
kindMust be Service.
nameName of the Service in the same namespace as the policy.

The policy cannot target Services in other namespaces. A single policy can target multiple Services by listing multiple entries in targetRefs.

All three features (session persistence, load balancing, and circuit breaking) are optional. Omit a field to leave the gateway default in place for that feature. An empty BackendLBPolicy with all three fields absent has no effect.

Configures cookie-based session affinity. Requests from the same client are routed to the same backend for the duration of the session.

FieldTypeDescription
sessionNamestringName used to identify the session.
typestringSession persistence type. Currently Cookie.
absoluteTimeoutdurationMaximum session lifetime regardless of activity.
idleTimeoutdurationSession expires after this period of inactivity.
cookie.lifetimeTypestringSession (browser session) or Permanent (persistent cookie).

Overrides the default weighted round-robin strategy for the targeted backends.

FieldTypeDescription
typestringStrategy: RoundRobin, ConsistentHash, LeastRequest, or Random.
consistentHash.keyTypestringHash key source: SourceIP, Header, or Hostname. Required when type is ConsistentHash.
consistentHash.headerNamestringHeader name to hash. Required when keyType is Header.

When type is omitted, the backend uses weighted round-robin. The consistentHash block is only relevant for ConsistentHash; it is ignored for other strategies.

Limits concurrent inflight requests to protect the backend from overload.

FieldTypeDescription
maxInflightRequestsint32Maximum concurrent requests allowed. Omit or set to 0 to disable (gateway-wide default applies).

When the inflight request count reaches this limit, additional requests are rejected immediately with a 503 Service Unavailable response.

Multiple BackendLBPolicy resources may target the same backend. When this happens, the gateway resolves the conflict using a deterministic precedence order:

  1. Creation timestamp. The policy created first wins.
  2. Name. If timestamps are identical, the policy whose metadata.name comes first alphabetically wins.
  3. Namespace. If both timestamp and name match, the policy from the alphabetically smaller namespace wins.

This is a first-match-wins rule per backend. The gateway does not merge policies. Each backend gets exactly one winning policy, as determined by the PolicyPrecedes function.

The resolved policy appears in the data plane snapshot under BackendCluster.loadBalancing, BackendCluster.session_persistence, and BackendCluster.circuitBreaker. You can inspect these fields through the data plane admin API at the /snapshots endpoint.

The gateway reports policy resolution status in status.conditions:

Condition typeMeaning
AcceptedThe policy was parsed and applied successfully.
ConflictedAnother policy targeting the same backend took precedence.
InvalidThe policy contains an invalid configuration.
TargetNotFoundA targetRef names a Service that does not exist.

Check status.conditions to troubleshoot why a policy is not taking effect. A policy with condition Conflicted is valid but was overridden by an earlier-created policy; check which policy won and either delete the older one or adjust your targeting.

Query the data plane admin API at port 19080 to see which policies are active. The /snapshots endpoint returns the full IR snapshot. Look for the BackendCluster entry matching your service and inspect the session_persistence, loadBalancing, and circuitBreaker fields. These fields are present only when a BackendLBPolicy has been resolved for that backend.

Session Persistence with Multi-Replica Deployments

Section titled “Session Persistence with Multi-Replica Deployments”

Session persistence stores session state in cookies signed with a shared secret. For single-replica deployments, the data plane auto-generates an ephemeral key on startup. For multi-replica deployments, you must configure a shared secret so all replicas can validate session cookies:

# dataplane config
dataplane:
config:
session_persistence:
secret_key_file: /etc/nantian-gw/session-secret/key

Or via Helm chart values:

dataplane:
sessionPersistence:
sharedSecret: "your-cryptographically-random-secret"
# Or reference an existing Kubernetes Secret:
# existingSecret: "nantian-gw-session-secret"

Without a shared secret, each data plane replica generates its own ephemeral key. Session cookies signed by one replica are rejected by others, and all sessions are lost on pod restart. The data plane logs a warning on startup when using an auto-generated key:

session persistence using auto-generated key; configure sharedSecret or sharedSecretFile for multi-replica deployments

Generate a secure key:

Terminal window
openssl rand -hex 32