Skip to content

feat(ui): add a replace option to the component router - #9683

Open
djgould wants to merge 1 commit into
mainfrom
dg/router-replace-option
Open

feat(ui): add a replace option to the component router#9683
djgould wants to merge 1 commit into
mainfrom
dg/router-replace-option

Conversation

@djgould

@djgould djgould commented Sep 8, 2026

Copy link
Copy Markdown
Contributor

Description

Adds a replace option to the UI router's navigate / baseNavigate and to withRedirect.

Why. The router always pushes a history entry. When a guard redirects to another route in the same component (the sign-in index redirecting to /sign-in/tasks/… today, or the account switcher redirect in #9651), the route it left stays in history. Pressing Back goes to that route, the guard fires again, and the user is pushed forward again. Back never gets out of the component.

With replace: true the guard route is dropped from history, so Back goes to the previous page.

flowchart LR
  subgraph push["Before: push"]
    direction LR
    R1["/referrer"] --> S1["/sign-in (guard fires)"]
    S1 -- "push" --> C1["/sign-in/choose"]
    C1 -. "Back" .-> S1
  end
  subgraph rep["After: replace"]
    direction LR
    R2["/referrer"] --> S2["/sign-in (guard fires)"]
    S2 -- "replace" --> C2["/sign-in/choose"]
    C2 -. "Back" .-> R2
  end
Loading

Per routing mode

  • Path routing: passed through to clerk.navigate, which already supports replace.
  • Hash routing: uses window.location.replace for the fragment.
  • Virtual routing (modals): ignored, there is no browser history.

No existing guard changes behavior. The first caller is #9651.

Checklist

  • pnpm test runs as expected.
  • pnpm build runs as expected.
  • (If applicable) JSDoc comments have been added or updated for any package exports
  • (If applicable) Documentation has been updated

Type of change

  • 🐛 Bug fix
  • 🌟 New feature
  • 🔨 Breaking change
  • 📖 Refactoring / dependency upgrade / documentation
  • other:

🤖 Generated with Claude Code

@changeset-bot

changeset-bot Bot commented Sep 8, 2026

Copy link
Copy Markdown

🦋 Changeset detected

Latest commit: 23a75d3

The changes in this PR will be included in the next version bump.

This PR includes changesets to release 0 packages

When changesets are added to this PR, you'll see the packages that this PR includes changesets for and the associated semver types

Not sure what this means? Click here to learn what changesets are.

Click here if you're a maintainer who wants to add another changeset to this PR

@vercel

vercel Bot commented Sep 8, 2026

Copy link
Copy Markdown

The latest updates on your projects. Learn more about Vercel for GitHub.

Project Deployment Actions Updated
clerk-js-sandbox Ready Ready Preview Sep 9, 2026 2:30pm UTC
swingset Ready Ready Preview Sep 9, 2026 2:30pm UTC

Request Review

@coderabbitai

coderabbitai Bot commented Sep 8, 2026

Copy link
Copy Markdown
Contributor

Review Change StackReview Change Stack

No actionable comments were generated in the recent review. 🎉

ℹ️ Recent review info
⚙️ Run configuration

Configuration used: Repository YAML (base), Organization UI (inherited)

Review profile: ASSERTIVE

Plan: Team

Run ID: f51f2bf3-5432-4d03-a9d7-7e4c4e04d8cb

📥 Commits

Reviewing files that changed from the base of the PR and between 7731dc3 and 8f65a40.

📒 Files selected for processing (8)
  • .changeset/router-replace-option.md
  • packages/ui/src/common/__tests__/withRedirect.test.tsx
  • packages/ui/src/common/withRedirect.tsx
  • packages/ui/src/router/BaseRouter.tsx
  • packages/ui/src/router/HashRouter.tsx
  • packages/ui/src/router/Route.tsx
  • packages/ui/src/router/RouteContext.tsx
  • packages/ui/src/router/__tests__/HashRouter.test.tsx
🔗 Linked repositories identified

CodeRabbit considers these linked repositories for cross-repo context during reviews:

  • clerk/clerk_go (manual)
  • clerk/dashboard (manual)
  • clerk/accounts (manual)
  • clerk/backoffice (manual)
  • clerk/clerk (manual)

Included review availability: 9 reviews are currently available. Your included PR review attempts over the past 7 days set your current allowance at 10 reviews per hour.


📝 Walkthrough

Walkthrough

The change adds optional replace navigation support to withRedirect, route context navigation, base router navigation, and hash router navigation. External and internal router calls receive the option. Hash navigation uses window.location.replace when enabled. Tests cover option forwarding, non-redirect behavior, and query-parameter preservation.

Priority: ⬇️ Low

Estimated code review effort: 3 (Moderate) | ~20 minutes

Merge Risk: ⚪ Minimal · up to 23a75

This adds optional history-entry replacement to router navigation while retaining existing navigation behavior by default. The documented forwarding and hash-navigation coverage indicate no remaining merge-blocking risk.

🚥 Pre-merge checks | ✅ 4 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 0.00% which is insufficient. The required threshold is 80.00%. Docstring coverage is scoped to functions touched by this diff. Analyzed 2 functions across 7 files. (1 skipped: 1 … Write docstrings for the functions missing them to satisfy the coverage threshold.
✅ Passed checks (4 passed)
Check name Status Explanation
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.
Title check ✅ Passed The title clearly and concisely describes the main change: adding a replace option to the component router.
Description check ✅ Passed The description accurately explains the replace option, its routing-mode behavior, motivation, and test/build status.
Full details: Docstring Coverage

Explanation

Docstring coverage is 0.00% which is insufficient. The required threshold is 80.00%. Docstring coverage is scoped to functions touched by this diff. Analyzed 2 functions across 7 files. (1 skipped: 1 unsupported.)

  • Fix all pre-merge checks with AI

Warning

Linked repositories: Your configuration references 7 linked repositories, but your current plan allows 5. Analyzed clerk/clerk_go, clerk/dashboard, clerk/accounts, clerk/backoffice, clerk/clerk, skipped clerk/clerk-docs, clerk/cloudflare-workers.


Repository analysis: Could not refresh clerk/javascript because repository setup failed. Please try the review again.


Comment @coderabbitai help to get the list of available commands.

@pkg-pr-new

pkg-pr-new Bot commented Sep 8, 2026

Copy link
Copy Markdown

Open in StackBlitz

@clerk/astro

npm i https://pkg.pr.new/@clerk/astro@9683

@clerk/backend

npm i https://pkg.pr.new/@clerk/backend@9683

@clerk/chrome-extension

npm i https://pkg.pr.new/@clerk/chrome-extension@9683

@clerk/clerk-js

npm i https://pkg.pr.new/@clerk/clerk-js@9683

@clerk/electron

npm i https://pkg.pr.new/@clerk/electron@9683

@clerk/electron-passkeys

npm i https://pkg.pr.new/@clerk/electron-passkeys@9683

@clerk/eslint-plugin

npm i https://pkg.pr.new/@clerk/eslint-plugin@9683

@clerk/expo

npm i https://pkg.pr.new/@clerk/expo@9683

@clerk/expo-google-signin

npm i https://pkg.pr.new/@clerk/expo-google-signin@9683

@clerk/expo-passkeys

npm i https://pkg.pr.new/@clerk/expo-passkeys@9683

@clerk/express

npm i https://pkg.pr.new/@clerk/express@9683

@clerk/fastify

npm i https://pkg.pr.new/@clerk/fastify@9683

@clerk/hono

npm i https://pkg.pr.new/@clerk/hono@9683

@clerk/localizations

npm i https://pkg.pr.new/@clerk/localizations@9683

@clerk/nextjs

npm i https://pkg.pr.new/@clerk/nextjs@9683

@clerk/nuxt

npm i https://pkg.pr.new/@clerk/nuxt@9683

@clerk/react

npm i https://pkg.pr.new/@clerk/react@9683

@clerk/react-router

npm i https://pkg.pr.new/@clerk/react-router@9683

@clerk/shared

npm i https://pkg.pr.new/@clerk/shared@9683

@clerk/tanstack-react-start

npm i https://pkg.pr.new/@clerk/tanstack-react-start@9683

@clerk/testing

npm i https://pkg.pr.new/@clerk/testing@9683

@clerk/ui

npm i https://pkg.pr.new/@clerk/ui@9683

@clerk/upgrade

npm i https://pkg.pr.new/@clerk/upgrade@9683

@clerk/vue

npm i https://pkg.pr.new/@clerk/vue@9683

commit: 23a75d3

@github-actions

github-actions Bot commented Sep 8, 2026

Copy link
Copy Markdown
Contributor

API Changes Report

Generated by Break Check on 2026-09-09T14:32:09.398Z

Summary

Metric Count
Packages analyzed 19
Packages with changes 0
🔴 Breaking changes 0
🟡 Non-breaking changes 0
🟢 Additions 0

No API Changes Detected

All packages have stable APIs with no detected changes.


Report generated by Break Check

Last ran on 23a75d3.

Internal guards that redirect to a route inside the same component (task
guards, the upcoming account-switcher redirect) push a history entry, so
Back lands on the route that immediately redirects again. `navigate` and
`withRedirect` now accept `{ replace: true }`, threaded through PathRouter
(clerk.navigate already honors it), HashRouter (window.location.replace),
and VirtualRouter (no history, ignored).

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant