From dd4259cc35ddb763b80b4652b19c18fbe0d5d36e Mon Sep 17 00:00:00 2001 From: wobsoriano Date: Sat, 8 Aug 2026 18:16:12 -0700 Subject: [PATCH 1/4] fix(web): redirect desktop auth to renderer root --- .../src/components/clerk/authRedirect.test.ts | 19 +++++++++++++++---- apps/web/src/components/clerk/authRedirect.ts | 13 ++++++++----- 2 files changed, 23 insertions(+), 9 deletions(-) diff --git a/apps/web/src/components/clerk/authRedirect.test.ts b/apps/web/src/components/clerk/authRedirect.test.ts index 4c4cd72d932..6d8b48cae1b 100644 --- a/apps/web/src/components/clerk/authRedirect.test.ts +++ b/apps/web/src/components/clerk/authRedirect.test.ts @@ -8,11 +8,22 @@ describe("resolveClerkSignInProps", () => { expect(resolveClerkSignInProps(href, false)).toEqual({ forceRedirectUrl: href }); }); - it("omits the redirect override on packaged desktop", () => { - expect(resolveClerkSignInProps("t3code://app/#/settings/general", true)).toEqual({}); + it("returns to the renderer root on packaged desktop", () => { + expect( + resolveClerkSignInProps( + "t3code://app/CLERK-ROUTER/VIRTUAL/sign-up#/settings/connections", + true, + ), + ).toEqual({ + forceRedirectUrl: "t3code://app/", + signUpForceRedirectUrl: "t3code://app/", + }); }); - it("omits the redirect override on development desktop", () => { - expect(resolveClerkSignInProps("t3code-dev://app/#/settings/general", true)).toEqual({}); + it("returns to the renderer root on development desktop", () => { + expect(resolveClerkSignInProps("t3code-dev://app/#/settings/general", true)).toEqual({ + forceRedirectUrl: "t3code-dev://app/", + signUpForceRedirectUrl: "t3code-dev://app/", + }); }); }); diff --git a/apps/web/src/components/clerk/authRedirect.ts b/apps/web/src/components/clerk/authRedirect.ts index 13331a27798..208d5b38c89 100644 --- a/apps/web/src/components/clerk/authRedirect.ts +++ b/apps/web/src/components/clerk/authRedirect.ts @@ -1,12 +1,15 @@ export interface ClerkSignInProps { forceRedirectUrl?: string; + signUpForceRedirectUrl?: string; } -// Clerk's native-app allowlist only authorizes the bare renderer root -// (t3code://app/), which @clerk/electron's OAuth transport already supplies, -// so any page-derived redirect override gets the whole sign-in request -// rejected. On Electron, omit the override and let Clerk use its defaults. export function resolveClerkSignInProps(href: string, isElectron: boolean): ClerkSignInProps { - if (isElectron) return {}; + if (isElectron) { + const redirectUrl = new URL("/", href).toString(); + return { + forceRedirectUrl: redirectUrl, + signUpForceRedirectUrl: redirectUrl, + }; + } return { forceRedirectUrl: href }; } From e99d783638e6433121b3218349131087799b6ccf Mon Sep 17 00:00:00 2001 From: wobsoriano Date: Sat, 8 Aug 2026 18:36:21 -0700 Subject: [PATCH 2/4] chore: add back comment --- apps/web/src/components/clerk/authRedirect.ts | 2 ++ 1 file changed, 2 insertions(+) diff --git a/apps/web/src/components/clerk/authRedirect.ts b/apps/web/src/components/clerk/authRedirect.ts index 208d5b38c89..8649143eee3 100644 --- a/apps/web/src/components/clerk/authRedirect.ts +++ b/apps/web/src/components/clerk/authRedirect.ts @@ -5,6 +5,8 @@ export interface ClerkSignInProps { export function resolveClerkSignInProps(href: string, isElectron: boolean): ClerkSignInProps { if (isElectron) { + // Match @clerk/electron's callback root for direct sign-in and sign-up transfers; + // otherwise Clerk's modal can submit its virtual route as the completion redirect. const redirectUrl = new URL("/", href).toString(); return { forceRedirectUrl: redirectUrl, From 3301d07019d8be0d44246629afb069d8296974da Mon Sep 17 00:00:00 2001 From: wobsoriano Date: Sat, 8 Aug 2026 18:45:04 -0700 Subject: [PATCH 3/4] chore: improve comment --- apps/web/src/components/clerk/authRedirect.ts | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/apps/web/src/components/clerk/authRedirect.ts b/apps/web/src/components/clerk/authRedirect.ts index 8649143eee3..d86a92a6885 100644 --- a/apps/web/src/components/clerk/authRedirect.ts +++ b/apps/web/src/components/clerk/authRedirect.ts @@ -5,8 +5,8 @@ export interface ClerkSignInProps { export function resolveClerkSignInProps(href: string, isElectron: boolean): ClerkSignInProps { if (isElectron) { - // Match @clerk/electron's callback root for direct sign-in and sign-up transfers; - // otherwise Clerk's modal can submit its virtual route as the completion redirect. + // @clerk/electron supplies the authorized renderer root for OAuth callbacks, but Clerk's + // modal can submit its virtual route as the completion redirect for sign-in or sign-up. const redirectUrl = new URL("/", href).toString(); return { forceRedirectUrl: redirectUrl, From a70cd1a66135bcb753230d28c727628e1c47547e Mon Sep 17 00:00:00 2001 From: wobsoriano Date: Sat, 8 Aug 2026 20:16:52 -0700 Subject: [PATCH 4/4] fix(web): preserve desktop route during Clerk auth --- apps/web/src/components/clerk/authRedirect.test.ts | 14 +++++++------- apps/web/src/components/clerk/authRedirect.ts | 12 +++++++----- 2 files changed, 14 insertions(+), 12 deletions(-) diff --git a/apps/web/src/components/clerk/authRedirect.test.ts b/apps/web/src/components/clerk/authRedirect.test.ts index 6d8b48cae1b..140474120cc 100644 --- a/apps/web/src/components/clerk/authRedirect.test.ts +++ b/apps/web/src/components/clerk/authRedirect.test.ts @@ -8,22 +8,22 @@ describe("resolveClerkSignInProps", () => { expect(resolveClerkSignInProps(href, false)).toEqual({ forceRedirectUrl: href }); }); - it("returns to the renderer root on packaged desktop", () => { + it("removes a Clerk virtual pathname and callback params while preserving the desktop route", () => { expect( resolveClerkSignInProps( - "t3code://app/CLERK-ROUTER/VIRTUAL/sign-up#/settings/connections", + "t3code://app/CLERK-ROUTER/VIRTUAL/sign-up?__clerk_status=complete#/settings/connections", true, ), ).toEqual({ - forceRedirectUrl: "t3code://app/", - signUpForceRedirectUrl: "t3code://app/", + forceRedirectUrl: "t3code://app/#/settings/connections", + signUpForceRedirectUrl: "t3code://app/#/settings/connections", }); }); - it("returns to the renderer root on development desktop", () => { + it("preserves a clean development desktop route", () => { expect(resolveClerkSignInProps("t3code-dev://app/#/settings/general", true)).toEqual({ - forceRedirectUrl: "t3code-dev://app/", - signUpForceRedirectUrl: "t3code-dev://app/", + forceRedirectUrl: "t3code-dev://app/#/settings/general", + signUpForceRedirectUrl: "t3code-dev://app/#/settings/general", }); }); }); diff --git a/apps/web/src/components/clerk/authRedirect.ts b/apps/web/src/components/clerk/authRedirect.ts index d86a92a6885..251c5ee3650 100644 --- a/apps/web/src/components/clerk/authRedirect.ts +++ b/apps/web/src/components/clerk/authRedirect.ts @@ -5,12 +5,14 @@ export interface ClerkSignInProps { export function resolveClerkSignInProps(href: string, isElectron: boolean): ClerkSignInProps { if (isElectron) { - // @clerk/electron supplies the authorized renderer root for OAuth callbacks, but Clerk's - // modal can submit its virtual route as the completion redirect for sign-in or sign-up. - const redirectUrl = new URL("/", href).toString(); + // Electron routes through the hash, so reset any Clerk virtual pathname without losing the T3 page. + const redirectUrl = new URL(href); + redirectUrl.pathname = "/"; + redirectUrl.search = ""; + return { - forceRedirectUrl: redirectUrl, - signUpForceRedirectUrl: redirectUrl, + forceRedirectUrl: redirectUrl.toString(), + signUpForceRedirectUrl: redirectUrl.toString(), }; } return { forceRedirectUrl: href };