diff --git a/.changeset/kind-paws-swim.md b/.changeset/kind-paws-swim.md
new file mode 100644
index 00000000000..95025976244
--- /dev/null
+++ b/.changeset/kind-paws-swim.md
@@ -0,0 +1,5 @@
+---
+'@clerk/clerk-js': patch
+---
+
+Detect when a user already has an active session in multi-session app and redirect to /choose subroute
diff --git a/integration/tests/session-tasks-multi-session.test.ts b/integration/tests/session-tasks-multi-session.test.ts
index 7e923f6f957..3235d99fec1 100644
--- a/integration/tests/session-tasks-multi-session.test.ts
+++ b/integration/tests/session-tasks-multi-session.test.ts
@@ -61,6 +61,11 @@ testAgainstRunningApps({ withEnv: [appConfigs.envs.withSessionTasks] })(
       // Create second user, to initiate a pending session
       // Don't resolve task and switch to active session afterwards
       await u.po.signIn.goTo();
+      await u.page.waitForURL(/sign-in\/choose/);
+      await u.page.getByText('Add account').click();
+      await u.page.waitForURL(/sign-in$/);
+      await u.po.signIn.waitForMounted();
+      await u.po.signIn.getIdentifierInput().waitFor({ state: 'visible' });
       await u.po.signIn.setIdentifier(user2.email);
       await u.po.signIn.continue();
       await u.po.signIn.setPassword(user2.password);
@@ -68,6 +73,11 @@ testAgainstRunningApps({ withEnv: [appConfigs.envs.withSessionTasks] })(
 
       // Sign-in again back with active session
       await u.po.signIn.goTo();
+      await u.page.waitForURL(/sign-in\/choose/);
+      await u.page.getByText('Add account').click();
+      await u.page.waitForURL(/sign-in$/);
+      await u.po.signIn.waitForMounted();
+      await u.po.signIn.getIdentifierInput().waitFor({ state: 'visible' });
       await u.po.signIn.setIdentifier(user1.email);
       await u.po.signIn.continue();
       await u.po.signIn.setPassword(user1.password);
diff --git a/integration/tests/sign-in-active-session-redirect.test.ts b/integration/tests/sign-in-active-session-redirect.test.ts
new file mode 100644
index 00000000000..f65a7853a56
--- /dev/null
+++ b/integration/tests/sign-in-active-session-redirect.test.ts
@@ -0,0 +1,94 @@
+import { test } from '@playwright/test';
+
+import { appConfigs } from '../presets';
+import type { FakeUser } from '../testUtils';
+import { createTestUtils, testAgainstRunningApps } from '../testUtils';
+
+testAgainstRunningApps({ withEnv: [appConfigs.envs.withEmailCodes] })(
+  'sign in redirect with active session @generic @nextjs',
+  ({ app }) => {
+    test.describe.configure({ mode: 'serial' });
+
+    let fakeUser: FakeUser;
+    let fakeUser2: FakeUser;
+
+    test.beforeAll(async () => {
+      const u = createTestUtils({ app });
+      fakeUser = u.services.users.createFakeUser({
+        withPhoneNumber: true,
+        withUsername: true,
+      });
+      await u.services.users.createBapiUser(fakeUser);
+
+      fakeUser2 = u.services.users.createFakeUser({
+        withPhoneNumber: true,
+        withUsername: true,
+      });
+      await u.services.users.createBapiUser(fakeUser2);
+    });
+
+    test.afterAll(async () => {
+      await fakeUser.deleteIfExists();
+      await fakeUser2.deleteIfExists();
+    });
+
+    test('redirects to /sign-in/choose when visiting /sign-in with active session in multi-session mode', async ({
+      page,
+      context,
+    }) => {
+      const u = createTestUtils({ app, page, context });
+
+      await u.po.signIn.goTo();
+      await u.po.signIn.signInWithEmailAndInstantPassword({ email: fakeUser.email, password: fakeUser.password });
+      await u.po.expect.toBeSignedIn();
+
+      await u.page.goToAppHome();
+      await u.po.signIn.goTo();
+      await u.page.waitForURL(/sign-in\/choose/);
+      await u.page.waitForSelector('text=Choose an account');
+    });
+
+    test('shows active session in account switcher with option to add account', async ({ page, context }) => {
+      const u = createTestUtils({ app, page, context });
+
+      await u.po.signIn.goTo();
+      await u.po.signIn.signInWithEmailAndInstantPassword({ email: fakeUser.email, password: fakeUser.password });
+      await u.po.expect.toBeSignedIn();
+
+      await u.po.signIn.goTo();
+      await u.page.waitForURL(/sign-in\/choose/);
+      await u.po.signIn.waitForMounted();
+      await u.page.getByText('Add account').waitFor({ state: 'visible' });
+      await u.page.getByText('Choose an account').waitFor({ state: 'visible' });
+    });
+
+    test('shows sign-in form when no active sessions exist', async ({ page, context }) => {
+      const u = createTestUtils({ app, page, context });
+
+      await u.page.context().clearCookies();
+      await u.po.signIn.goTo();
+      await u.po.signIn.waitForMounted();
+      await u.page.waitForSelector('text=/email address|username|phone/i');
+      await u.page.waitForURL(/sign-in$/);
+    });
+
+    test('can sign in to second account after clicking "Add account" from /choose', async ({ page, context }) => {
+      const u = createTestUtils({ app, page, context });
+
+      await u.po.signIn.goTo();
+      await u.po.signIn.signInWithEmailAndInstantPassword({ email: fakeUser.email, password: fakeUser.password });
+      await u.po.expect.toBeSignedIn();
+
+      await u.po.signIn.goTo();
+      await u.page.waitForURL(/sign-in\/choose/);
+      await u.po.signIn.waitForMounted();
+
+      await u.page.getByText('Add account').click();
+      await u.page.waitForURL(/sign-in$/);
+      await u.po.signIn.waitForMounted();
+
+      await u.po.signIn.signInWithEmailAndInstantPassword({ email: fakeUser2.email, password: fakeUser2.password });
+      await u.po.expect.toBeSignedIn();
+    });
+  },
+);
diff --git a/integration/tests/sign-in-single-session-mode.test.ts b/integration/tests/sign-in-single-session-mode.test.ts
new file mode 100644
index 00000000000..821027d021d
--- /dev/null
+++ b/integration/tests/sign-in-single-session-mode.test.ts
@@ -0,0 +1,79 @@
+import type { FakeUser } from '@clerk/testing/playwright';
+import { test } from '@playwright/test';
+
+import type { Application } from '../models/application';
+import { appConfigs } from '../presets';
+import { createTestUtils, testAgainstRunningApps } from '../testUtils';
+
+/**
+ * Tests for single-session mode behavior using the withBilling environment
+ * which is configured for single-session mode in the Clerk Dashboard.
+ */
+testAgainstRunningApps({ withEnv: [appConfigs.envs.withBilling] })(
+  'sign in with active session in single-session mode @generic @nextjs',
+  ({ app }) => {
+    test.describe.configure({ mode: 'serial' });
+
+    let fakeUser: FakeUser;
+
+    test.beforeAll(async () => {
+      const u = createTestUtils({ app });
+      fakeUser = u.services.users.createFakeUser({
+        withPhoneNumber: true,
+        withUsername: true,
+      });
+      await u.services.users.createBapiUser(fakeUser);
+    });
+
+    test.afterAll(async () => {
+      await fakeUser.deleteIfExists();
+    });
+
+    test('redirects to afterSignIn URL when visiting /sign-in with active session in single-session mode', async ({
+      page,
+      context,
+    }) => {
+      const u = createTestUtils({ app, page, context });
+
+      await u.po.signIn.goTo();
+      await u.po.signIn.signInWithEmailAndInstantPassword({ email: fakeUser.email, password: fakeUser.password });
+      await u.po.expect.toBeSignedIn();
+      await u.page.waitForAppUrl('/');
+
+      await u.po.signIn.goTo();
+      await u.page.waitForAppUrl('/');
+      await u.po.expect.toBeSignedIn();
+    });
+
+    test('does NOT show account switcher in single-session mode', async ({ page, context }) => {
+      const u = createTestUtils({ app, page, context });
+
+      await u.po.signIn.goTo();
+      await u.po.signIn.signInWithEmailAndInstantPassword({ email: fakeUser.email, password: fakeUser.password });
+      await u.po.expect.toBeSignedIn();
+
+      await u.page.goToRelative('/sign-in/choose');
+      await u.page.waitForAppUrl('/');
+    });
+
+    test('shows sign-in form when no active session in single-session mode', async ({ page, context }) => {
+      const u = createTestUtils({ app, page, context });
+
+      await u.page.context().clearCookies();
+      await u.po.signIn.goTo();
+      await u.po.signIn.waitForMounted();
+      await u.page.waitForSelector('text=/email address|username|phone/i');
+      await u.page.waitForURL(/sign-in$/);
+    });
+
+    test('can sign in normally when not already authenticated in single-session mode', async ({ page, context }) => {
+      const u = createTestUtils({ app, page, context });
+
+      await u.page.context().clearCookies();
+      await u.po.signIn.goTo();
+      await u.po.signIn.signInWithEmailAndInstantPassword({ email: fakeUser.email, password: fakeUser.password });
+      await u.po.expect.toBeSignedIn();
+      await u.page.waitForAppUrl('/');
+    });
+  },
+);
diff --git a/packages/clerk-js/src/ui/components/SignIn/SignInStart.tsx b/packages/clerk-js/src/ui/components/SignIn/SignInStart.tsx
index 6b0dd0cc8a9..69f574829b1 100644
--- a/packages/clerk-js/src/ui/components/SignIn/SignInStart.tsx
+++ b/packages/clerk-js/src/ui/components/SignIn/SignInStart.tsx
@@ -109,6 +109,7 @@ function SignInStartInternal(): JSX.Element {
     shouldStartWithPhoneNumberIdentifier ? 'phone_number' : identifierAttributes[0] || '',
   );
   const [hasSwitchedByAutofill, setHasSwitchedByAutofill] = useState(false);
+  const hasInitializedRef = useRef(false);
 
   const organizationTicket = getClerkQueryParam('__clerk_ticket') || '';
   const clerkStatus = getClerkQueryParam('__clerk_status') || '';
@@ -181,6 +182,35 @@ function SignInStartInternal(): JSX.Element {
     setShouldAutofocus(true);
   };
 
+  /**
+   * Redirect to account switcher if user already has active sessions in multi-session mode
+   */
+  useEffect(() => {
+    if (organizationTicket || hasInitializedRef.current) {
+      return;
+    }
+
+    hasInitializedRef.current = true;
+
+    const urlParams = new URLSearchParams(window.location.search);
+    const isAddingAccount = urlParams.has('__clerk_add_account');
+
+    if (isAddingAccount) {
+      urlParams.delete('__clerk_add_account');
+      const newSearch = urlParams.toString();
+      const newUrl = window.location.pathname + (newSearch ? `?${newSearch}` : '');
+      window.history.replaceState({}, '', newUrl);
+      return;
+    }
+
+    const hasActiveSessions = (clerk.client?.signedInSessions?.length ?? 0) > 0;
+    const isMultiSessionMode = !authConfig.singleSessionMode;
+
+    if (hasActiveSessions && isMultiSessionMode) {
+      void navigate('choose');
+    }
+  }, [clerk.client?.signedInSessions, authConfig.singleSessionMode, navigate, organizationTicket]);
+
   // switch to the phone input (if available) if a "+" is entered
   // (either by the browser or the user)
   // this does not work in chrome as it does not fire the change event and the value is
diff --git a/packages/clerk-js/src/ui/components/SignIn/__tests__/SignInStart.test.tsx b/packages/clerk-js/src/ui/components/SignIn/__tests__/SignInStart.test.tsx
index 5d6aad7857f..dc438b5f1d9 100644
--- a/packages/clerk-js/src/ui/components/SignIn/__tests__/SignInStart.test.tsx
+++ b/packages/clerk-js/src/ui/components/SignIn/__tests__/SignInStart.test.tsx
@@ -590,4 +590,114 @@ describe('SignInStart', () => {
       );
     });
   });
+
+  describe('Active session redirect', () => {
+    describe('multi-session mode', () => {
+      it('redirects to /choose when user has active sessions', async () => {
+        const { wrapper, fixtures } = await createFixtures(f => {
+          f.withEmailAddress();
+          f.withMultiSessionMode();
+          f.withUser({
+            email_addresses: ['user@clerk.com'],
+          });
+        });
+
+        // Mock active sessions using spyOn
+        vi.spyOn(fixtures.clerk.client, 'signedInSessions', 'get').mockReturnValue([
+          {
+            id: 'sess_123',
+            user: fixtures.clerk.user,
+            status: 'active',
+          } as any,
+        ]);
+
+        render(, { wrapper });
+
+        await waitFor(() => {
+          expect(fixtures.router.navigate).toHaveBeenCalledWith('choose');
+        });
+      });
+
+      it('redirects to /choose when user has multiple active sessions', async () => {
+        const { wrapper, fixtures } = await createFixtures(f => {
+          f.withEmailAddress();
+          f.withMultiSessionMode();
+          f.withUser({
+            email_addresses: ['user@clerk.com'],
+          });
+        });
+
+        // Mock multiple active sessions using spyOn
+        vi.spyOn(fixtures.clerk.client, 'signedInSessions', 'get').mockReturnValue([
+          {
+            id: 'sess_123',
+            user: fixtures.clerk.user,
+            status: 'active',
+          } as any,
+          {
+            id: 'sess_456',
+            user: { id: 'user_456' },
+            status: 'active',
+          } as any,
+        ]);
+
+        render(, { wrapper });
+
+        await waitFor(() => {
+          expect(fixtures.router.navigate).toHaveBeenCalledWith('choose');
+        });
+      });
+
+      it('does NOT redirect when user has no active sessions', async () => {
+        const { wrapper, fixtures } = await createFixtures(f => {
+          f.withEmailAddress();
+          f.withMultiSessionMode();
+        });
+
+        // No active sessions using spyOn
+        vi.spyOn(fixtures.clerk.client, 'signedInSessions', 'get').mockReturnValue([]);
+
+        render(, { wrapper });
+
+        await waitFor(
+          () => {
+            expect(fixtures.router.navigate).not.toHaveBeenCalledWith('choose');
+          },
+          { timeout: 100 },
+        );
+
+        screen.getByText(/email address/i);
+      });
+    });
+
+    describe('single-session mode', () => {
+      it('does NOT redirect to /choose when user has active session in single-session mode', async () => {
+        const { wrapper, fixtures } = await createFixtures(f => {
+          f.withEmailAddress();
+          f.withUser({
+            email_addresses: ['user@clerk.com'],
+          });
+        });
+
+        vi.spyOn(fixtures.clerk.client, 'signedInSessions', 'get').mockReturnValue([
+          {
+            id: 'sess_123',
+            user: fixtures.clerk.user,
+            status: 'active',
+          } as any,
+        ]);
+
+        fixtures.environment.authConfig.singleSessionMode = true;
+
+        render(, { wrapper });
+
+        await waitFor(
+          () => {
+            expect(fixtures.router.navigate).not.toHaveBeenCalledWith('choose');
+          },
+          { timeout: 100 },
+        );
+      });
+    });
+  });
 });
diff --git a/packages/clerk-js/src/ui/components/UserButton/useMultisessionActions.tsx b/packages/clerk-js/src/ui/components/UserButton/useMultisessionActions.tsx
index dd3d37e9c1f..af63b10f6cd 100644
--- a/packages/clerk-js/src/ui/components/UserButton/useMultisessionActions.tsx
+++ b/packages/clerk-js/src/ui/components/UserButton/useMultisessionActions.tsx
@@ -99,7 +99,9 @@ export const useMultisessionActions = (opts: UseMultisessionActionsParams) => {
   };
 
   const handleAddAccountClicked = () => {
-    windowNavigate(opts.signInUrl || window.location.href);
+    const url = new URL(opts.signInUrl || window.location.href, window.location.origin);
+    url.searchParams.set('__clerk_add_account', '1');
+    windowNavigate(url.toString());
     return sleep(2000);
   };