Project: Traefik (Orchestration & Management / API Gateway)
File: kubernetes-ingress.md

title: "Kubernetes Ingress Routing Configuration" description: "Understand the routing configuration for the Kubernetes Ingress Controller and Traefik Proxy. Read the technical documentation." The Kubernetes Ingress Controller. {: .subtitle } The provider then watches for incoming ingresses events, such as the example below, and derives the corresponding dynamic configuration from it, which in turn will create the resulting routers, services, handlers, etc. ??? example "Configuring Kubernetes Ingress Controller" ```yaml tab="RBAC" apiVersion: rbac.authorization.k8s.io/v1 kind: ClusterRole metadata: name: traefik-ingress-controller rules: apiGroups: "" resources: services endpoints secrets verbs: get list watch apiGroups: extensions networking.k8s.io resources: ingresses ingressclasses verbs: get list watch apiGroups: extensions networking.k8s.io resources: ingresses/status verbs: update apiVersion: rbac.authorization.k8s.io/v1 kind: ClusterRoleBinding metadata: name: traefik-ingress-controller roleRef: apiGroup: rbac.authorization.k8s.io kind: ClusterRole name: traefik-ingress-controller subjects: kind: ServiceAccount name: traefik-ingress-controller namespace: default ``` ```yaml tab="Ingress" apiVersion: networking.k8s.io/v1 kind: Ingress metadata: name: myingress annotations: traefik.ingress.kubernetes.io/router.entrypoints: web spec: rules: host: example.com http: paths: path: /bar pathType: Exact backend: service: name: whoami port: number: 80 path: /foo pathType: Exact backend: service: name: whoami port: number: 80 ``` ```yaml tab="Traefik" apiVersion: v1 kind: ServiceAccount metadata: name: traefik-ingress-controller apiVersion: apps/v1 kind: Deployment metadata: name: traefik labels: app: traefik spec: replicas: 1 selector: matchLabels: app: traefik template: metadata: labels: app: traefik spec: serviceAccountName: traefik-ingress-controller containers: name: traefik image: traefik:v3.0 args: --entryPoints.web.address=:80 --providers.kubernetesingress ports: name: web containerPort: 80 apiVersion: v1 kind: Service metadata: name: traefik spec: type: LoadBalancer selector: app: traefik ports: protocol: TCP port: 80 name: web targetPort: 80 ``` ```yaml tab="Whoami" apiVersion: apps/v1 kind: Deployment metadata: name: whoami labels: app: traefiklabs name: whoami spec: replicas: 2 selector: matchLabels: app: traefiklabs task: whoami template: metadata: labels: app: traefiklabs task: whoami spec: containers: name: whoami image: traefik/whoami ports: containerPort: 80 apiVersion: v1 kind: Service metadata: name: whoami spec: ports: name: http port: 80 selector: app: traefiklabs task: whoami ``` !!! warning "Referencing resources in annotations" In an annotation, when referencing a resource defined by another provider, the must be used. ??? info "`traefik.ingress.kubernetes.io/router.entrypoints`" See for more information. ```yaml traefik.ingress.kubernetes.io/router.entrypoints: ep1,ep2 ``` ??? info "`traefik.ingress.kubernetes.io/router.middlewares`" See and for more information. ```yaml traefik.ingress.kubernetes.io/router.middlewares: auth@file,default-prefix@kubernetescrd ``` ??? info "`traefik.ingress.kubernetes.io/router.priority`" See for more information. ```yaml traefik.ingress.kubernetes.io/router.priority: "42" ``` ??? info "`traefik.ingress.kubernetes.io/router.pathmatcher`" Overrides the default router rule type used for a path. Only path-related matcher name can be specified: `Path`, `PathPrefix`. Default `PathPrefix` ```yaml traefik.ingress.kubernetes.io/router.pathmatcher: Path ``` ??? info "`traefik.ingress.kubernetes.io/router.tls`" See for more information. ```yaml traefik.ingress.kubernetes.io/router.tls: "true" ``` ??? info "`traefik.ingress.kubernetes.io/router.tls.certresolver`" See for more information. ```yaml traefik.ingress.kubernetes.io/router.tls.certresolver: myresolver ``` ??? info "`traefik.ingress.kubernetes.io/router.tls.domains.n.main`" See for more information. ```yaml traefik.ingress.kubernetes.io/router.tls.domains.0.main: example.org ``` ??? info "`traefik.ingress.kubernetes.io/router.tls.domains.n.sans`" See for more information. ```yaml traefik.ingress.kubernetes.io/router.tls.domains.0.sans: test.example.org,dev.example.org ``` ??? info "`traefik.ingress.kubernetes.io/router.tls.options`" See for more information. ```yaml traefik.ingress.kubernetes.io/router.tls.options: foobar@file ``` ??? info "`traefik.ingress.kubernetes.io/service.nativelb`" Controls, when creating the load-balancer, whether the LB's children are directly the pods IPs or if the only child is the Kubernetes Service clusterIP. The Kubernetes Service itself does load-balance to the pods. Please note that, by default, Traefik reuses the established connections to the backends for performance purposes. This can prevent the requests load balancing between the replicas from behaving as one would expect when the option is set. By default, NativeLB is false. ```yaml traefik.ingress.kubernetes.io/service.nativelb: "true" ``` ??? info "`traefik.ingress.kubernetes.io/service.nodeportlb`" Controls, when creating the load-balancer, whether the LB's children are directly the nodes internal IPs using the nodePort when the service type is NodePort. It allows services to be reachable when Traefik runs externally from the Kubernetes cluster but within the same network of the nodes. By default, NodePortLB is false. ```yaml traefik.ingress.kubernetes.io/service.nodeportlb: "true" ``` ??? info "`traefik.ingress.kubernetes.io/service.serversscheme`" Overrides the default

```yaml traefik.ingress.kubernetes.io/service.serversscheme: h2c ``` ??? info "`traefik.ingress.kubernetes.io/service.serverstransport`" See for more information. ```yaml traefik.ingress.kubernetes.io/service.serverstransport: foobar@file ``` ??? info "`traefik.ingress.kubernetes.io/service.passhostheader`" See for more information. ```yaml traefik.ingress.kubernetes.io/service.passhostheader: "true" ``` ??? info "`traefik.ingress.kubernetes.io/service.sticky.cookie`" See for more information. ```yaml traefik.ingress.kubernetes.io/service.sticky.cookie: "true" ``` ??? info "`traefik.ingress.kubernetes.io/service.sticky.cookie.name`" See for more information. ```yaml traefik.ingress.kubernetes.io/service.sticky.cookie.name: foobar ``` ??? info "`traefik.ingress.kubernetes.io/service.sticky.cookie.secure`" See for more information. ```yaml traefik.ingress.kubernetes.io/service.sticky.cookie.secure: "true" ``` ??? info "`traefik.ingress.kubernetes.io/service.sticky.cookie.samesite`" See for more information. ```yaml traefik.ingress.kubernetes.io/service.sticky.cookie.samesite: "none" ``` ??? info "`traefik.ingress.kubernetes.io/service.sticky.cookie.httponly`" See for more information. ```yaml traefik.ingress.kubernetes.io/service.sticky.cookie.httponly: "true" ``` ??? info "`traefik.ingress.kubernetes.io/service.sticky.cookie.maxage`" See for more information. ```yaml traefik.ingress.kubernetes.io/service.sticky.cookie.maxage: 42 ``` If the Kubernetes cluster version is 1.18+, the new `pathType` property can be leveraged to define the rules matchers: `Exact`: This path type forces the rule matcher to `Path` `Prefix`: This path type forces the rule matcher to `PathPrefix` Please see for more information. !!! warning "Multiple Matches" In the case of multiple matches, Traefik will not ensure the priority of a Path matcher over a PathPrefix matcher, as stated in . TLS can be enabled through the of an Entrypoint: ```bash tab="CLI" --entryPoints.websecure.address=:443 --entryPoints.websecure.http.tls ``` ```yaml tab="File (YAML)" entryPoints: websecure: address: ':443' http: tls: {} ``` ```toml tab="File (TOML)" [entryPoints.websecure] address = ":443" [entryPoints.websecure.http.tls] ``` This way, any Ingress attached to this Entrypoint will have TLS termination by default. ??? example "Configuring Kubernetes Ingress Controller with TLS on Entrypoint" ```yaml tab="RBAC" apiVersion: rbac.authorization.k8s.io/v1 kind: ClusterRole metadata: name: traefik-ingress-controller rules: apiGroups: "" resources: services endpoints secrets verbs: get list watch apiGroups: extensions networking.k8s.io resources: ingresses ingressclasses verbs: get list watch apiGroups: extensions networking.k8s.io resources: ingresses/status verbs: update apiVersion: rbac.authorization.k8s.io/v1 kind: ClusterRoleBinding metadata: name: traefik-ingress-controller roleRef: apiGroup: rbac.authorization.k8s.io kind: ClusterRole name: traefik-ingress-controller subjects: kind: ServiceAccount name: traefik-ingress-controller namespace: default ``` ```yaml tab="Ingress" apiVersion: networking.k8s.io/v1 kind: Ingress metadata: name: myingress annotations: traefik.ingress.kubernetes.io/router.entrypoints: websecure spec: rules: host: example.com http: paths: path: /bar pathType: Exact backend: service: name: whoami port: number: 80 path: /foo pathType: Exact backend: service: name: whoami port: number: 80 ``` ```yaml tab="Traefik" apiVersion: v1 kind: ServiceAccount metadata: name: traefik-ingress-controller apiVersion: apps/v1 kind: Deployment metadata: name: traefik labels: app: traefik spec: replicas: 1 selector: matchLabels: app: traefik template: metadata: labels: app: traefik spec: serviceAccountName: traefik-ingress-controller containers: name: traefik image: traefik:v3.0 args: --entryPoints.websecure.address=:443 --entryPoints.websecure.http.tls --providers.kubernetesingress ports: name: websecure containerPort: 443 apiVersion: v1 kind: Service metadata: name: traefik spec: type: LoadBalancer selector: app: traefik ports: protocol: TCP port: 443 name: websecure targetPort: 443 ``` ```yaml tab="Whoami" apiVersion: apps/v1 kind: Deployment metadata: name: whoami labels: app: traefiklabs name: whoami spec: replicas: 2 selector: matchLabels: app: traefiklabs task: whoami template: metadata: labels: app: traefiklabs task: whoami spec: containers: name: whoami image: traefik/whoami ports: containerPort: 80 apiVersion: v1 kind: Service metadata: name: whoami spec: ports: name: http port: 80 selector: app: traefiklabs task: whoami ``` To enable TLS on the underlying router created from an Ingress, one should configure it through annotations: ```yaml traefik.ingress.kubernetes.io/router.tls: "true" ``` For more options, please refer to the available . ??? example "Configuring Kubernetes Ingress Controller with TLS" ```yaml tab="RBAC" apiVersion: rbac.authorization.k8s.io/v1 kind: ClusterRole metadata: name: traefik-ingress-controller rules: apiGroups: "" resources: services endpoints secrets verbs: get list watch apiGroups: extensions networking.k8s.io resources: ingresses ingressclasses verbs: get list watch apiGroups: extensions networking.k8s.io resources: ingresses/status verbs: update apiVersion: rbac.authorization.k8s.io/v1 kind: ClusterRoleBinding metadata: name: traefik-ingress-controller roleRef: apiGroup: rbac.authorization.k8s.io kind: ClusterRole name: traefik-ingress-controller subjects: kind: ServiceAccount name: traefik-ingress-controller namespace: default ``` ```yaml tab="Ingress" apiVersion: networking.k8s.io/v1 kind: Ingress metadata: name: myingress annotations: traefik.ingress.kubernetes.io/router.entrypoints: websecure traefik.ingress.kubernetes.io/router.tls: true spec: rules: host:

http: paths: path: /bar pathType: Exact backend: service: name: whoami port: number: 80 path: /foo pathType: Exact backend: service: name: whoami port: number: 80 ``` ```yaml tab="Traefik" apiVersion: v1 kind: ServiceAccount metadata: name: traefik-ingress-controller apiVersion: apps/v1 kind: Deployment metadata: name: traefik labels: app: traefik spec: replicas: 1 selector: matchLabels: app: traefik template: metadata: labels: app: traefik spec: serviceAccountName: traefik-ingress-controller containers: name: traefik image: traefik:v3.0 args: --entryPoints.websecure.address=:443 --providers.kubernetesingress ports: name: websecure containerPort: 443 apiVersion: v1 kind: Service metadata: name: traefik spec: type: LoadBalancer selector: app: traefik ports: protocol: TCP port: 443 name: websecure targetPort: 443 ``` ```yaml tab="Whoami" apiVersion: apps/v1 kind: Deployment metadata: name: whoami labels: app: traefiklabs name: whoami spec: replicas: 2 selector: matchLabels: app: traefiklabs task: whoami template: metadata: labels: app: traefiklabs task: whoami spec: containers: name: whoami image: traefik/whoami ports: containerPort: 80 apiVersion: v1 kind: Service metadata: name: whoami spec: ports: name: http port: 80 selector: app: traefiklabs task: whoami ``` ??? example "Using a secret" ```yaml tab="Ingress" apiVersion: networking.k8s.io/v1 kind: Ingress metadata: name: foo namespace: production spec: rules: host: example.net http: paths: path: /bar pathType: Exact backend: service: name: service1 port: number: 80 tls: secretName: supersecret ``` ```yaml tab="Secret" apiVersion: v1 kind: Secret metadata: name: supersecret data: tls.crt: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCi0tLS0tRU5EIENFUlRJRklDQVRFLS0tLS0= tls.key: LS0tLS1CRUdJTiBQUklWQVRFIEtFWS0tLS0tCi0tLS0tRU5EIFBSSVZBVEUgS0VZLS0tLS0= ``` TLS certificates can be managed in Secrets objects. !!! info Only TLS certificates provided by users can be stored in Kubernetes Secrets. certificates cannot be managed in Kubernetes Secrets yet. !!! info "Routing directly to " To route directly to the Kubernetes service, one can use the `traefik.ingress.kubernetes.io/service.nativelb` annotation on the Kubernetes service. It controls, when creating the load-balancer, whether the LB's children are directly the pods IPs or if the only child is the Kubernetes Service clusterIP. One alternative is to use an `ExternalName` service to forward requests to the Kubernetes service through DNS. To do so, one must . Traefik automatically requests endpoint information based on the service provided in the ingress spec. Although Traefik will connect directly to the endpoints (pods), it still checks the service port to see if TLS communication is required. There are 3 ways to configure Traefik to use HTTPS to communicate with pods: If the service port defined in the ingress spec is `443` (note that you can still use `targetPort` to use a different port on your pod). If the service port defined in the ingress spec has a name that starts with `https` (such as `https-api`, `https-web` or just `https`). If the service spec includes the annotation `traefik.ingress.kubernetes.io/service.serversscheme: https`. If either of those configuration options exist, then the backend communication protocol is assumed to be TLS, and will connect via TLS automatically. !!! info Please note that by enabling TLS communication between traefik and your pods, you will have to have trusted certificates that have the proper trust chain and IP subject name. If this is not an option, you may need to skip TLS certificate verification. See the setting for more details. Ingresses can be created that look like the following: ```yaml tab="Ingress" apiVersion: networking.k8s.io/v1 kind: Ingress metadata: name: cheese spec: defaultBackend: service: name: stilton port: number: 80 ``` This ingress follows the Global Default Backend property of ingresses. This will allow users to create a "default router" that will match all unmatched requests. !!! info Due to Traefik's use of priorities, you may have to set this ingress priority lower than other ingresses in your environment, to avoid this global ingress from satisfying requests that could match other ingresses. To do this, use the `traefik.ingress.kubernetes.io/router.priority` annotation (as seen in ) on your ingresses accordingly. {!traefik-for-business-applications.md!}