ANT-2026-EFRBDRNP · supabase/supabase
open-redirect low
Severity Claude low · Security research firm - · Maintainer -
Discovered by Claude Mythos Preview
Anthropic's analysis of this finding, sealed at approval.
ANT-2026-EFRBDRNP: Unvalidated returnTo redirect after organisation creation
In Supabase Studio's NewOrgForm component, after a user successfully creates an organisation the code reads returnTo from router.query and calls router.push(returnTo) with no validation. Because Next.js router.push accepts absolute URLs and performs a full-page navigation for external origins, an attacker who gets an authenticated Studio user to open a link like /dashboard/new?returnTo=https://evil.tld will have the victim redirected to the attacker's site immediately after completing the legitimate org-creation flow. This can be used to stage a convincing phishing page that mimics Studio and harvests credentials or PATs.
Target
Project: supabase/supabase
Location: apps/studio/components/interfaces/Organization/NewOrg/NewOrgForm.tsx:303
Discovery: static analysis — not yet dynamically reproduced
Technical Details
The root cause is a missing allow-list / relative-path check on the user-controlled returnTo value before it is handed to router.push. router.push will happily navigate to an absolute external URL, so any value the attacker places in the query string becomes the post-action destination.
Reproduction
- Attacker crafts a URL to the legitimate Studio new-org page with
?returnTo=https://evil.tld/dashboard. - Attacker distributes the link (e.g. in a community channel) as a helpful quick-start link.
- Victim authenticates (if needed) and submits the new-organisation form on the real dashboard.
- On success,
router.push(returnTo)navigates the victim's browser tohttps://evil.tld/dashboard. - Attacker's page mimics Studio and prompts for re-authentication or a personal access token.
[No reproducer or sanitizer output attached — request from security-cvd@anthropic.com if needed.]
Suggested Fix
Only honour returnTo values that are relative paths beginning with a single / (and not //); otherwise fall back to the default dashboard route.
Acknowledgement
This vulnerability was discovered by Claude, Anthropic's AI assistant, and triaged by the Anthropic security team in collaboration with Anthropic Research. Please direct questions to security-cvd@anthropic.com and reference ANT-2026-EFRBDRNP.
Reference: ANT-2026-EFRBDRNP
Anthropic CVD Policy: https://www.anthropic.com/coordinated-vulnerability-disclosure
The change that resolved this finding.
diff --git a/apps/studio/components/interfaces/Organization/NewOrg/NewOrgForm.tsx b/apps/studio/components/interfaces/Organization/NewOrg/NewOrgForm.tsx
index dd67eda9d45ff..d88e6280a1936 100644
--- a/apps/studio/components/interfaces/Organization/NewOrg/NewOrgForm.tsx
+++ b/apps/studio/components/interfaces/Organization/NewOrg/NewOrgForm.tsx
@@ -57,6 +57,7 @@ import { useConfirmPendingSubscriptionCreateMutation } from '@/data/subscription
import { useIsFeatureEnabled } from '@/hooks/misc/useIsFeatureEnabled'
import { useLocalStorageQuery } from '@/hooks/misc/useLocalStorage'
import { PRICING_TIER_LABELS_ORG, STRIPE_PUBLIC_KEY } from '@/lib/constants'
+import { validateReturnTo } from '@/lib/gotrue'
import { useProfile } from '@/lib/profile'
interface NewOrgFormProps {
@@ -279,7 +280,7 @@ export const NewOrgForm = ({
: 'My Project'
if (searchParams.returnTo) {
- const url = new URL(searchParams.returnTo, window.location.origin)
+ const url = new URL(validateReturnTo(searchParams.returnTo, '/'), window.location.origin)
if (searchParams.auth_id) {
url.searchParams.set('auth_id', searchParams.auth_id)
}https://github.com/supabase/supabase/commit/a59b797216d6459ef466a209ee90b404826f9b9b
Dates from discovery through public reveal.
- 2026-05-14 Reported to tracker
- 2026-05-14 Maintainer acknowledged
- 2026-05-15 Sent to maintainer
- 2026-06-11 Patch released
- 2026-08-18 Publicly revealed
SHA-3-512 hash:
9c08f381eb7b115269163418ec693ce3fdd7c32e96993ae2429967b16ed4d93f4451bfaf7c9fb7f659b486dbb11d9eae68d20cc82ff45113bef8714e6c5e1f17
Committed 2026-05-17 17:54 PT
Revealed 2026-08-18 07:12 PT
Verify (download preimage.json)
Show preimage JSON
{
"ant_id": "ANT-2026-EFRBDRNP",
"bug_class": "open-redirect",
"claude_severity": "low",
"commit_sha": null,
"created_at": "2026-05-14T22:04:17+00:00",
"description": "In Supabase Studio's NewOrgForm component, after a user successfully creates an organisation the code reads `returnTo` from `router.query` and calls `router.push(returnTo)` with no validation. Because Next.js `router.push` accepts absolute URLs and performs a full-page navigation for external origins, an attacker who gets an authenticated Studio user to open a link like `/dashboard/new?returnTo=https://evil.tld` will have the victim redirected to the attacker's site immediately after completing the legitimate org-creation flow. This can be used to stage a convincing phishing page that mimics Studio and harvests credentials or PATs.",
"discovered_at": "2026-05-10T00:00:00+00:00",
"location": "apps/studio/components/interfaces/Organization/NewOrg/NewOrgForm.tsx:303",
"poc_sha256": null,
"preimage_version": 1,
"project": "supabase/supabase",
"reproduction": [
"1. Attacker crafts a URL to the legitimate Studio new-org page with `?returnTo=https://evil.tld/dashboard`.",
"2. Attacker distributes the link (e.g. in a community channel) as a helpful quick-start link.",
"3. Victim authenticates (if needed) and submits the new-organisation form on the real dashboard.",
"4. On success, `router.push(returnTo)` navigates the victim's browser to `https://evil.tld/dashboard`.",
"5. Attacker's page mimics Studio and prompts for re-authentication or a personal access token."
],
"technical_details": "The root cause is a missing allow-list / relative-path check on the user-controlled `returnTo` value before it is handed to `router.push`. `router.push` will happily navigate to an absolute external URL, so any value the attacker places in the query string becomes the post-action destination.",
"title": "Unvalidated returnTo redirect after organisation creation",
"vendor_severity": null
}