fix: Don't fall through to catch-all when static child subtree doesn't match#90957
Merged
acdlite merged 1 commit intovercel:canaryfrom Mar 6, 2026
Merged
Conversation
Collaborator
Tests Passed |
…t match When matching a URL against the known route trie, if a URL part matches a static child but the remaining parts don't resolve within that child's subtree, the algorithm incorrectly falls back to a dynamic catch-all sibling at the same level. This causes the catch-all to consume the already-matched static part plus the remaining parts, producing a synthetic entry for the wrong route. For example, given routes /dashboard/settings/profile and /dashboard/[...catchall], navigating to /dashboard/settings/profile could incorrectly match the catch-all with params ["settings", "profile"] instead of the intended static route. The fix treats the static child match as authoritative: if a real (non-placeholder) static child exists but its subtree can't resolve the remaining URL parts, bail out to server resolution rather than trying the dynamic sibling. This is safe because it just means an extra network request for routes whose subtree hasn't been fully discovered.
fcd6656 to
592d5ab
Compare
ztanner
approved these changes
Mar 6, 2026
sokra
pushed a commit
that referenced
this pull request
Mar 6, 2026
…t match (#90957) When matching a URL against the known route trie, if a URL part matches a static child but the remaining parts don't resolve within that child's subtree, the algorithm incorrectly falls back to a dynamic catch-all sibling at the same level. This causes the catch-all to consume the already-matched static part plus the remaining parts, producing a synthetic entry for the wrong route. For example, given routes `/dashboard/settings/profile` and `/dashboard/[...catchall]`, navigating to `/dashboard/settings/profile` could incorrectly match the catch-all with params `["settings", "profile"]` instead of the intended static route. The fix treats the static child match as authoritative: if a real (non-placeholder) static child exists but its subtree can't resolve the remaining URL parts, bail out to server resolution rather than trying the dynamic sibling. This is safe because it just means an extra network request for routes whose subtree hasn't been fully discovered.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
When matching a URL against the known route trie, if a URL part matches a static child but the remaining parts don't resolve within that child's subtree, the algorithm incorrectly falls back to a dynamic catch-all sibling at the same level. This causes the catch-all to consume the already-matched static part plus the remaining parts, producing a synthetic entry for the wrong route.
For example, given routes
/dashboard/settings/profileand/dashboard/[...catchall], navigating to/dashboard/settings/profilecould incorrectly match the catch-all with params["settings", "profile"]instead of the intended static route.The fix treats the static child match as authoritative: if a real (non-placeholder) static child exists but its subtree can't resolve the remaining URL parts, bail out to server resolution rather than trying the dynamic sibling. This is safe because it just means an extra network request for routes whose subtree hasn't been fully discovered.