--- title: "Traefik Migration Documentation" description: "Learn the steps needed to migrate to new Traefik Proxy v3 versions. Read the technical documentation." --- # Migration: Steps needed between the versions This guide provides detailed migration steps for upgrading between different Traefik v3 versions. Each section covers breaking changes, deprecations, and configuration updates required for a smooth transition. --- ## v3.0 to v3.1 ### Kubernetes Provider RBACs Starting with v3.1, Traefik's Kubernetes Providers use the [EndpointSlices API](https://kubernetes.io/docs/concepts/services-networking/endpoint-slices/) (requires Kubernetes >=v1.21) for service endpoint discovery. This change also introduces NodePort load-balancing capabilities. The following RBAC updates are required for all Kubernetes providers: - Remove endpoints permissions and add endpointslices: ```yaml # Remove this section from your RBAC # - apiGroups: [""] # resources: ["endpoints"] # verbs: ["get", "list", "watch"] # Add this section instead - apiGroups: - discovery.k8s.io resources: - endpointslices verbs: - list - watch ``` - Add nodes permissions for NodePort support: ```yaml - apiGroups: - "" resources: - nodes verbs: - get - list - watch ``` !!! note "Affected Providers" These changes apply to: - [KubernetesIngress](../routing/providers/kubernetes-ingress.md#configuration-example) provider - [KubernetesCRD](../reference/dynamic-configuration/kubernetes-crd.md#rbac) provider - [KubernetesGateway](../reference/dynamic-configuration/kubernetes-gateway-rbac.yml) provider #### Gateway API: KubernetesGateway Provider The KubernetesGateway Provider is no longer experimental in v3.1 and can be enabled without the `experimental.kubernetesgateway` option. **Deprecated Configuration:** ??? example "Experimental kubernetesgateway option (deprecated)" ```yaml tab="File (YAML)" experimental: kubernetesgateway: true ``` ```toml tab="File (TOML)" [experimental] kubernetesgateway=true ``` ```bash tab="CLI" --experimental.kubernetesgateway=true ``` **Migration Steps:** 1. Remove the `kubernetesgateway` option from the experimental section 2. Configure the provider using the [KubernetesGateway Provider documentation](../providers/kubernetes-gateway.md) --- ## v3.1.0 to v3.1.1 ### IngressClass Lookup The `disableIngressClassLookup` option has been deprecated and will be removed in the next major version. **Migration Required:** - **Old:** `disableIngressClassLookup` - **New:** `disableClusterScopeResources` The new option provides broader control over cluster scope resources discovery, including both IngressClass and Nodes resources. --- ## v3.1 to v3.2 ### Kubernetes CRD Provider New optional fields have been added to several CRDs. These updates are backward compatible and only add new functionality. **Apply the latest CRDs:** ```shell kubectl apply -f https://raw.githubusercontent.com/traefik/traefik/v3.3/docs/content/reference/dynamic-configuration/kubernetes-crd-definition-v1.yml ``` **Updated Resources:** - [TraefikService](../../routing/services#mirroring-service) ([PR #11032](https://github.com/traefik/traefik/pull/11032)) - [RateLimit](../../middlewares/http/ratelimit) & [InFlightReq](../../middlewares/http/inflightreq) middlewares ([PR #9747](https://github.com/traefik/traefik/pull/9747)) - [Compress](../../middlewares/http/compress) middleware ([PR #10943](https://github.com/traefik/traefik/pull/10943)) ### Kubernetes Gateway Provider Standard Channel Starting with v3.2, the Kubernetes Gateway Provider now supports [GRPCRoute](https://gateway-api.sigs.k8s.io/api-types/grpcroute/) resources. Therefore, in the corresponding RBACs (see [KubernetesGateway](../reference/dynamic-configuration/kubernetes-gateway-rbac.yml) provider RBACs), the `grcroutes` and `grpcroutes/status` rights have to be added. **Required RBAC Updates:** ```yaml ... - apiGroups: - gateway.networking.k8s.io resources: - grpcroutes verbs: - get - list - watch - apiGroups: - gateway.networking.k8s.io resources: - grpcroutes/status verbs: - update ... ``` ### Kubernetes Gateway Provider Experimental Channel Due to breaking changes in Kubernetes Gateway [v1.2.0-rc1](https://github.com/kubernetes-sigs/gateway-api/releases/tag/v1.2.0-rc1), Traefik v3.3 only supports Kubernetes Gateway v1.2.x when experimental features are enabled. **New Feature: BackendTLSPolicy Support** The provider now supports [BackendTLSPolicy](https://gateway-api.sigs.k8s.io/api-types/backendtlspolicy/) resources. Therefore, in the corresponding RBACs (see [KubernetesGateway](../reference/dynamic-configuration/kubernetes-gateway-rbac.yml) provider RBACs), the `backendtlspolicies` and `backendtlspolicies/status` rights have to be added. **Required RBAC Updates:** ```yaml ... - apiGroups: - "" resources: - configmaps verbs: - get - list - watch - apiGroups: - gateway.networking.k8s.io resources: - backendtlspolicies verbs: - get - list - watch - apiGroups: - gateway.networking.k8s.io resources: - backendtlspolicies/status verbs: - update ... ``` --- ## v3.2.1 ### X-Forwarded-Prefix Header Changes In v3.2.1, the `X-Forwarded-Prefix` header is now handled like other `X-Forwarded-*` headers - Traefik removes it when sent from untrusted sources. This change improves security by preventing header spoofing from untrusted clients. Refer to the [Forwarded headers documentation](../routing/entrypoints.md#forwarded-headers) for configuration details. --- ## v3.2.2 ### Swarm Provider Label Updates In v3.2.2, Swarm-specific labels have been deprecated and will be removed in a future version. **Migration Required:** | Deprecated Label | New Label | |------------------|-----------| | `traefik.docker.network` | `traefik.swarm.network` | | `traefik.docker.lbswarm` | `traefik.swarm.lbswarm` | --- ## v3.2 to v3.3 ### ACME DNS Certificate Resolver In v3.3, DNS challenge configuration options have been reorganized for better clarity. **Migration Required:** | Deprecated Option | New Option | |-------------------|------------| | `acme.dnsChallenge.delaybeforecheck` | `acme.dnsChallenge.propagation.delayBeforeChecks` | | `acme.dnsChallenge.disablepropagationcheck` | `acme.dnsChallenge.propagation.disableChecks` | ### Tracing Global Attributes In v3.3, the tracing configuration has been clarified to better reflect its purpose. **Migration Required:** - **Old:** `tracing.globalAttributes` - **New:** `tracing.resourceAttributes` The old option name was misleading as it specifically adds resource attributes for the collector, not global span attributes. --- ## v3.3.4 ### OpenTelemetry Request Duration Metric In v3.3.4, the OpenTelemetry Request Duration metric unit has been standardized to match other providers and naming conventions. **Change Details:** - **Metric:** `traefik_(entrypoint|router|service)_request_duration_seconds` - **Old Unit:** Milliseconds - **New Unit:** Seconds This change ensures consistency across all metrics providers and follows standard naming conventions. --- ## v3.3.5 ### Compress Middleware Default Encodings In v3.3.5, the default compression algorithms have been reordered to favor gzip compression. **New Default:** `gzip, br, zstd` This change affects requests that either: - Don't specify preferred algorithms in the `Accept-Encoding` header - Have no order preference in their `Accept-Encoding` header The reordering helps ensure better compatibility with older clients that may not support newer compression algorithms. --- ## v3.3.6 ### Request Path Sanitization Starting with v3.3.6, incoming request paths are now automatically cleaned before processing for security and consistency. **What's Changed:** The following path segments are now interpreted and collapsed: - `/../` (parent directory references) - `/./` (current directory references) - Duplicate slash segments (`//`) **Disabling Sanitization:** ```yaml # EntryPoint HTTP configuration entryPoints: web: address: ":80" http: sanitizePath: false # Not recommended ``` !!! danger "Security Warning" Setting `sanitizePath: false` is not safe. This option should only be used with legacy clients that don't properly URL-encode data. Always ensure requests are properly URL-encoded instead of disabling this security feature. **Example Risk:** Base64 data containing "/" characters can lead to unsafe routing when path sanitization is disabled and the data isn't URL-encoded. --- ## v3.3 to v3.4 ### Kubernetes CRD Provider #### Load-Balancing Strategy Updates Starting with v3.4, HTTP service definitions now support additional load-balancing strategies for better traffic distribution. **Apply Updated CRDs:** ```shell kubectl apply -f https://raw.githubusercontent.com/traefik/traefik/v3.4/docs/content/reference/dynamic-configuration/kubernetes-crd-definition-v1.yml ``` **New Strategy Values:** - `wrr` (Weighted Round Robin) - `p2c` (Power of Two Choices) !!! warning "Deprecation" The `RoundRobin` strategy is deprecated but still supported (equivalent to `wrr`). It will be removed in the next major release. Refer to the [HTTP Services Load Balancing documentation](../../routing/services/#load-balancing-strategy) for detailed information. #### ServersTransport CA Certificate Configuration A new `rootCAs` option has been added to the `ServersTransport` and `ServersTransportTCP` CRDs. It supports both ConfigMaps and Secrets for CA certificates and replaces the `rootCAsSecrets` option. **Apply Updates:** ```shell # Update CRDs kubectl apply -f https://raw.githubusercontent.com/traefik/traefik/v3.4/docs/content/reference/dynamic-configuration/kubernetes-crd-definition-v1.yml # Update RBACs kubectl apply -f https://raw.githubusercontent.com/traefik/traefik/v3.4/docs/content/reference/dynamic-configuration/kubernetes-crd-rbac.yml ``` **New Configuration Format:** ```yaml --- apiVersion: traefik.io/v1alpha1 kind: ServersTransport metadata: name: foo namespace: bar spec: rootCAs: - configMap: ca-config-map - secret: ca-secret --- apiVersion: traefik.io/v1alpha1 kind: ServersTransportTCP metadata: name: foo namespace: bar spec: rootCAs: - configMap: ca-config-map - secret: ca-secret ``` !!! warning "Deprecation" The `rootCAsSecrets` option (Secrets only) is still supported but deprecated. It will be removed in the next major release. ### Rule Syntax Configuration In v3.4, rule syntax configuration options will be removed in the next major version. **Deprecated Options:** - `core.defaultRuleSyntax` (static configuration) - `ruleSyntax` (router option) These options were transitional helpers for migrating from v2 to v3 syntax. Please ensure all router rules use v3 syntax before the next major release. --- ## v3.4.1 ### Request Path Normalization Starting with v3.4.1, request paths are now normalized according to RFC 3986 standards for better consistency and security. **Normalization Process:** 1. **Unreserved Character Decoding:** Characters like `%2E` (.) are decoded to their literal form 2. **Case Normalization:** Percent-encoded characters are uppercased (`%2e` becomes `%2E`) This follows [RFC 3986 percent-encoding normalization](https://datatracker.ietf.org/doc/html/rfc3986#section-6.2.2.2) and [case normalization](https://datatracker.ietf.org/doc/html/rfc3986#section-6.2.2.1) standards. **Processing Order:** 1. Path normalization (cannot be disabled) 2. Path sanitization (if enabled) ### Reserved Character Handling in Routing Starting with v3.4.1, reserved characters (per [RFC 3986](https://datatracker.ietf.org/doc/html/rfc3986#section-2.2)) remain encoded during router rule matching to prevent routing ambiguity. **Why This Matters:** Reserved characters change the meaning of request paths when decoded. Keeping them encoded during routing prevents security vulnerabilities and ensures predictable routing behavior. ### Request Path Matching Examples The following table illustrates how path matching behavior has changed: | Request Path | Router Rule | Traefik v3.4.0 | Traefik v3.4.1 | Explanation | |-------------------|------------------------|----------------|----------------|-------------| | `/foo%2Fbar` | ```PathPrefix(`/foo/bar`)``` | Match | No match | `%2F` (/) stays encoded, preventing false matches | | `/foo/../bar` | ```PathPrefix(`/foo`)``` | No match | No match | Path traversal is sanitized away | | `/foo/../bar` | ```PathPrefix(`/bar`)``` | Match | Match | Resolves to `/bar` after sanitization | | `/foo/%2E%2E/bar` | ```PathPrefix(`/foo`)``` | Match | No match | Encoded dots normalized then sanitized | | `/foo/%2E%2E/bar` | ```PathPrefix(`/bar`)``` | No match | Match | Resolves to `/bar` after normalization + sanitization | ## v3.4.5 ### MultiPath TCP Since `v3.4.5`, the MultiPath TCP support introduced with `v3.4.2` has been removed. It appears that enabling MPTCP on some platforms can cause Traefik to stop with the following error logs message: - `set tcp X.X.X.X:X->X.X.X.X:X: setsockopt: operation not supported` However, it can be re-enabled by setting the `multipathtcp` variable in the GODEBUG environment variable, see the related [go documentation](https://go.dev/doc/godebug#go-124). ## v3.5.0 ### Observability #### TraceVerbosity on Routers and Entrypoints Starting with `v3.5.0`, a new `traceVerbosity` option is available for both entrypoints and routers. This option allows you to control the level of detail for tracing spans. Routers can override the value inherited from their entrypoint. **Impact:** - If you rely on tracing, review your configuration to explicitly set the desired verbosity level. - Existing configurations will default to `minimal` unless overridden, which will result in fewer spans being generated than before. Possible values are: - `minimal`: produces a single server span and one client span for each request processed by a router. - `detailed`: enables the creation of additional spans for each middleware executed for each request processed by a router. See the updated documentation for [entrypoints](../reference/install-configuration/entrypoints.md) and [dynamic routers](../reference/dynamic-configuration/file.md#observability-options). #### K8s Resource Attributes Since `v3.5.0`, the semconv attributes `k8s.pod.name` and `k8s.pod.uid` are injected automatically in OTel resource attributes when OTel tracing/logs/metrics are enabled. For that purpose, the following right has to be added to the Traefik Kubernetes RBACs: ```yaml ... - apiGroups: - "" resources: - pods verbs: - get ... ```