Supabase RPC Leak: The Real Lesson for Vibe Coders

A new CVE shows how a Supabase RPC function leaked org data — not because a key was public, but because the function logic was wrong. Here's the fix.

Barret4 min read

A new CVE this week is a clean example of the mistake AI-generated backends keep making. It has nothing to do with a leaked key. It's about what a database function does once someone calls it. If your app has a Supabase or Postgres backend that an AI builder wrote for you, this one is worth five minutes.

TL;DR

  • CVE-2026-56339 hit Capgo: a Supabase RPC function leaked whether an organization ID exists, using only the public API key.
  • The bug wasn't a key leak. Supabase anon keys and Firebase web configs are meant to be public. The bug was the function's own logic.
  • The function returned different error messages (NO_ORG vs NO_RIGHTS) for valid vs invalid org IDs — a classic enumeration flaw.
  • Separately, Vercel Connect is moving agents off long-lived GitHub tokens entirely, which is the direction this whole space needs to go.

What actually happened

Capgo, a service built on Supabase, shipped an RPC function called rescind_invitation. It's a SECURITY DEFINER function — meaning it runs with elevated database privileges regardless of who calls it. The flaw: it returned one error message when an organization didn't exist, and a different one when it existed but the caller lacked rights. Anyone with the app's publishable (anon) API key — which is public by design, visible in every network request — could call the function repeatedly and learn which organization IDs are real. That's an enumeration bug, and it hands attackers a list of real targets for phishing or social engineering. Details: CVE-2026-56339.

Why this is the pattern to watch

This is not about the anon key existing. Every Supabase project has one, and it's supposed to be in your frontend code. The actual risk lives one layer deeper: in the SQL functions and Row Level Security policies that decide what the anon key is allowed to do. AI builders like Lovable, Bolt, and Cursor generate these functions constantly, often as one-shot RPC calls to handle invites, permissions, or org lookups. A model writing that logic rarely thinks about what an error message reveals to an unauthenticated caller. If you have any SECURITY DEFINER function in your Supabase project, check what it returns on failure — not just whether it blocks the wrong user, but whether its error text tells them something they shouldn't know.

The other trend: fewer secrets to leak in the first place

On the infrastructure side, Vercel Connect now integrates with GitHub Tools so agents mint short-lived, scoped GitHub tokens at runtime instead of storing a long-lived personal access token. "There is no secret to store, rotate, or leak," as the changelog puts it. That's the right instinct for the AI-agent era: instead of asking developers to manage secrets carefully, remove the standing secret entirely. If your stack has any agent or CI step still holding a long-lived PAT, ask whether it can move to short-lived, scoped credentials instead.

FAQ

Is my Supabase anon key a security problem?

No. It's meant to be public and ships in every frontend bundle. The security problem, if there is one, is in your Row Level Security policies and any custom RPC functions — not the key itself.

How do I check if my app has this kind of enumeration bug?

Look at any database function marked SECURITY DEFINER in your Supabase project. Call it with bad input and good input and compare the error messages. If they differ in a way that reveals whether a record exists, that's the flaw this CVE describes.

Does using a long-lived GitHub token in my project put me at risk?

It's not automatically a breach, but it's a standing secret that can leak through logs, commits, or a compromised dependency. Vercel's move to short-lived, scoped tokens through Connect is a sign the industry sees standing tokens as a liability worth engineering away.

The bottom line

The headline risk in AI-coded backends is almost never a public key. It's the logic behind that key — the RLS policy or RPC function an AI wrote without thinking about what an error message gives away. Check your functions, not just your keys.

Find your gaps before an attacker does.

Is My Site Hackable? scans your deployed app for the exact issues in this article — exposed keys, missing RLS, open buckets — and tells you what's real and what's a false alarm.

Run a free scan →