Skip to main content

Sticky Sessions (IngressRoute)

Pin a user to the same backend pod using cookie-based session affinity, configured directly on the IngressRoute service reference. Useful when running multiple replicas and your app maintains in-memory session state.

Prerequisites​

base/base-values.yaml

image:
registry: docker.io
repository: traefik/whoami
tag: latest
port: 80

Configuration​

envs/prod/values.yaml

deployment:
enabled: true
replicas: 2

service:
enabled: true

customResources:
- |
apiVersion: traefik.io/v1alpha1
kind: IngressRoute
metadata:
name: my-app-sticky
annotations:
kubernetes.io/ingress.class: public-traefik
external-dns.alpha.kubernetes.io/target: public-v2.{{ .Values.captain_domain }}
spec:
entryPoints:
- web
- websecure
routes:
- match: Host(`{{ include "app.name" . }}.apps.{{ .Values.captain_domain }}`)
kind: Rule
services:
- name: '{{ include "app.name" . }}'
namespace: '{{ include "app.namespace" . }}'
port: 80
sticky:
cookie:
name: my-sticky-cookie
maxAge: 3600
secure: true
httpOnly: true
sameSite: none

What Gets Created​

ResourceNamePurpose
Deploymentmy-app-prodRuns 2 replicas of the application
Servicemy-app-prodClusterIP service for internal routing
IngressRoutemy-app-stickyRoutes traffic with cookie-based pod affinity

Verify​

# First request — check for the sticky cookie in the response
curl -v https://my-app-prod.apps.nonprod.antoniostacos.onglueops.com 2>&1 | grep -i set-cookie
# Output should include: Set-Cookie: my-sticky-cookie=<hash>; ... Secure; HttpOnly; SameSite=None

# Subsequent requests with the cookie go to the same pod
curl -b "my-sticky-cookie=<hash>" https://my-app-prod.apps.nonprod.antoniostacos.onglueops.com
# The "Hostname:" line in the whoami response should be the same across multiple requests
note

The -prod suffix matches your environment folder name (envs/prod/). If you deploy to a different environment like envs/uat/, the suffix changes accordingly (e.g., my-app-uat).

Key Points​

  • Sticky sessions are configured on the service reference inside the IngressRoute routes[].services[] block — not via annotations
  • Requires replicas > 1 to observe the effect (with a single replica, all requests go to the same pod regardless)
  • Traefik manages the sticky cookie entirely — your application does not need to set or read it
  • secure: true ensures the cookie is only sent over HTTPS
  • httpOnly: true prevents JavaScript from accessing the cookie
  • sameSite: none allows the cookie to be sent on cross-origin requests (requires secure: true)
  • This is the IngressRoute CRD equivalent of the annotation-based sticky sessions approach used with standard Kubernetes Ingress
info

Choosing a cookie name: The name field sets the cookie name. Use a descriptive name to avoid collisions if your app sets its own cookies. Traefik generates the cookie value automatically — it's a hash of the backend pod.