fix: path-based routing broken due to key collisions in sanitize() #211

Closed
opened 2026-04-05 17:02:41 +02:00 by MrUnknownDE · 0 comments
Owner

Originally created by @shreyaspapi on 2/23/2026

Community Contribution License Agreement

By creating this pull request, I grant the project maintainers an unlimited,
perpetual license to use, modify, and redistribute these contributions under any terms they
choose, including both the AGPLv3 and the Fossorial Commercial license terms. I
represent that I have the right to grant this license for all contributed content.

Description

Fixes #2294

What this fixes

The sanitize() function used to generate internal map keys for grouping targets in getTraefikConfig can cause path collisions. It replaces all non-alphanumeric characters (including /, ., _) with dashes and collapses them, so structurally different paths can produce the same key:

  • sanitize("/a/b") = "a-b"
  • sanitize("/a-b") = "a-b" (same!)

When two targets get the same key, they're grouped into one loadbalancer service and Traefik round-robins between them instead of routing by path.

Note: this specific collision doesn't affect the / vs /api scenario reported in the issue (those already produce different keys), but it would affect setups with paths like /api/v1 vs /api-v1 or /app.v2 vs /app/v2.

How to test?

  1. Create two resources with paths that would collide under old sanitization (e.g., /api/v1 and /api-v1)
  2. Verify they route to their correct backends independently (no round-robin)
  3. Verify existing resources with simple paths still work with the same router names
*Originally created by @shreyaspapi on 2/23/2026* ## Community Contribution License Agreement By creating this pull request, I grant the project maintainers an unlimited, perpetual license to use, modify, and redistribute these contributions under any terms they choose, including both the AGPLv3 and the Fossorial Commercial license terms. I represent that I have the right to grant this license for all contributed content. ## Description Fixes #2294 ## What this fixes The `sanitize()` function used to generate internal map keys for grouping targets in `getTraefikConfig` can cause path collisions. It replaces all non-alphanumeric characters (including `/`, `.`, `_`) with dashes and collapses them, so structurally different paths can produce the same key: - `sanitize("/a/b")` = `"a-b"` - `sanitize("/a-b")` = `"a-b"` (same!) When two targets get the same key, they're grouped into one loadbalancer service and Traefik round-robins between them instead of routing by path. Note: this specific collision doesn't affect the `/` vs `/api` scenario reported in the issue (those already produce different keys), but it would affect setups with paths like `/api/v1` vs `/api-v1` or `/app.v2` vs `/app/v2`. ## How to test? 1. Create two resources with paths that would collide under old sanitization (e.g., `/api/v1` and `/api-v1`) 2. Verify they route to their correct backends independently (no round-robin) 3. Verify existing resources with simple paths still work with the same router names
Sign in to join this conversation.
No Label
1 Participants
Notifications
Due Date
No due date set.
Dependencies

No dependencies set.

Reference: github/pangolin#211