From 9f794854106b32bf43f87b7dc042e4ef2dbc3113 Mon Sep 17 00:00:00 2001 From: Zai Shi Date: Fri, 27 Jun 2025 04:00:12 +0200 Subject: [PATCH] Fix redirect url (#703) ---- > [!IMPORTANT] > Adds redirect URL validation in sign-up process and updates test URL to localhost. > > - **Behavior**: > - Adds `validateRedirectUrl` check in `POST` handler in `route.tsx` to ensure `verificationCallbackUrl` is whitelisted. > - Throws `RedirectUrlNotWhitelisted` error if URL is not valid. > - **Tests**: > - Updates `verificationCallbackUrl` in `scaffoldProject` in `js-helpers.ts` to `http://localhost:3000`. > > This description was created by [Ellipsis](https://www.ellipsis.dev?ref=stack-auth%2Fstack-auth&utm_source=github&utm_medium=referral) for f25e26b9d3a388bc891e3cc85a33f11d5ce2169b. You can [customize](https://app.ellipsis.dev/stack-auth/settings/summaries) this summary. It will automatically update as commits are pushed. --------- Co-authored-by: Konsti Wohlwend --- .../latest/auth/password/sign-up/route.tsx | 9 + .../api/v1/auth/password/sign-up.test.ts | 29 + apps/e2e/tests/js/js-helpers.ts | 2 +- .../src/generated/quetzal-translations.ts | 5390 +++++++++-------- 4 files changed, 2825 insertions(+), 2605 deletions(-) diff --git a/apps/backend/src/app/api/latest/auth/password/sign-up/route.tsx b/apps/backend/src/app/api/latest/auth/password/sign-up/route.tsx index c3c5abc2f..ca954beb9 100644 --- a/apps/backend/src/app/api/latest/auth/password/sign-up/route.tsx +++ b/apps/backend/src/app/api/latest/auth/password/sign-up/route.tsx @@ -1,3 +1,4 @@ +import { validateRedirectUrl } from "@/lib/redirect-urls"; import { createAuthTokens } from "@/lib/tokens"; import { createSmartRouteHandler } from "@/route-handlers/smart-route-handler"; import { runAsynchronouslyAndWaitUntil } from "@/utils/vercel"; @@ -39,6 +40,14 @@ export const POST = createSmartRouteHandler({ throw new KnownErrors.PasswordAuthenticationNotEnabled(); } + if (!validateRedirectUrl( + verificationCallbackUrl, + tenancy.config.domains, + tenancy.config.allow_localhost, + )) { + throw new KnownErrors.RedirectUrlNotWhitelisted(); + } + const passwordError = getPasswordError(password); if (passwordError) { throw passwordError; diff --git a/apps/e2e/tests/backend/endpoints/api/v1/auth/password/sign-up.test.ts b/apps/e2e/tests/backend/endpoints/api/v1/auth/password/sign-up.test.ts index e1a4c6f34..9cd9967fc 100644 --- a/apps/e2e/tests/backend/endpoints/api/v1/auth/password/sign-up.test.ts +++ b/apps/e2e/tests/backend/endpoints/api/v1/auth/password/sign-up.test.ts @@ -56,6 +56,35 @@ it("should sign up new users", async ({ expect }) => { `); }); +it("should not sign up new users if verification callback url is not valid", async ({ expect }) => { + const mailbox = backendContext.value.mailbox; + const email = mailbox.emailAddress; + const password = generateSecureRandomString(); + const response = await niceBackendFetch("/api/v1/auth/password/sign-up", { + method: "POST", + accessType: "client", + body: { + email, + password, + verification_callback_url: "http://invalid-domain.com", + }, + }); + + expect(response).toMatchInlineSnapshot(` + NiceResponse { + "status": 400, + "body": { + "code": "REDIRECT_URL_NOT_WHITELISTED", + "error": "Redirect URL not whitelisted. Did you forget to add this domain to the trusted domains list on the Stack Auth dashboard?", + }, + "headers": Headers { + "x-stack-known-error": "REDIRECT_URL_NOT_WHITELISTED", +