F-01Critical
Row-level security disabled on profiles table
CWE-862 · A01:2021 Broken Access Control
What it is
The profiles table is readable with the anon key and has no row-level security policies. Any visitor can enumerate every user’s profile.
Why it matters
A curious user or scraper can dump names, emails, and roles for the entire tenant — the exact failure class behind recent vibe-code showcase breaches.
Evidence
supabase/migrations/001_init.sql — CREATE TABLE profiles …; RLS not enabled. Client uses NEXT_PUBLIC_SUPABASE_ANON_KEY=****ab12
How to fix
- Enable RLS: ALTER TABLE profiles ENABLE ROW LEVEL SECURITY;
- Add policies so users select/update only their own row (auth.uid() = id).
- Verify with the anon key that cross-user reads return empty.
Paste-back fix prompt
Enable Supabase RLS on the profiles table. Add policies so authenticated users can SELECT/UPDATE only rows where id = auth.uid(). Do not allow anon role to read other users’ profiles. Show the SQL migration.
F-02Critical
Service-role API key embedded in client bundle
CWE-798 · A07:2021 Identification and Authentication Failures
What it is
A Supabase service-role key is imported into a client component and ships in the browser JavaScript bundle.
Why it matters
Anyone who view-sources the app can impersonate the backend, bypass RLS, and read or modify the entire database — and rack up unlimited API spend.
Evidence
src/lib/supabase-admin.ts exported into src/app/dashboard/page.tsx; key redacted …x9f2
How to fix
- Remove service-role usage from any file imported by client components.
- Move privileged operations to a server-only route or Edge Function.
- Rotate the exposed key immediately.
Paste-back fix prompt
Find any Supabase service-role key usage in client-side code and move it to a server-only API route. Rotate the exposed key. Keep only the anon key in NEXT_PUBLIC_* env vars.
F-03High
Admin gate enforced only in React UI
CWE-602 · A01:2021 Broken Access Control
What it is
The /admin page hides controls when role !== "admin" in the browser, but the underlying /api/admin/users endpoint does not verify role server-side.
Why it matters
Changing a localStorage flag or calling the API directly grants admin actions to any logged-in user.
Evidence
src/app/admin/page.tsx (client check only); src/app/api/admin/users/route.ts — no role verification
How to fix
- Verify session and role on every admin API route before returning data.
- Treat UI checks as convenience only, never as authorization.
Paste-back fix prompt
Add server-side authorization to all /api/admin/* routes. Reject requests unless the authenticated user has role=admin in the database. Remove reliance on client-only role checks.
F-04High
Broken object-level authorization on order detail
CWE-639 · A01:2021 Broken Access Control
What it is
GET /api/orders/[id] returns any order by ID without checking that the order belongs to the current user.
Why it matters
Changing the ID in the URL or API call exposes other customers’ order contents and PII — classic BOLA/IDOR.
Evidence
src/app/api/orders/[id]/route.ts — select by id only, no owner filter
How to fix
- Filter by both id and owner_id = auth.uid() (or equivalent).
- Return 404 for unauthorized IDs (avoid confirming existence).
Paste-back fix prompt
Fix IDOR on the order detail API: only return an order if it belongs to the authenticated user. Use parameterized queries. Return 404 when unauthorized.
F-05Medium
.env committed and served from public folder
CWE-200 · A05:2021 Security Misconfiguration
What it is
A .env file with database and API credentials is present in public/ and is downloadable from the deployed origin.
Why it matters
Attackers routinely probe /.env. A successful hit hands over the full configuration without needing a vulnerability chain.
Evidence
public/.env.example renamed to public/.env in fixture; contains DATABASE_URL=…****4c1a
How to fix
- Delete secrets from public/; rotate every exposed credential.
- Ensure .env is gitignored and not copied into static output.
- Block /.env and /.git at the reverse proxy.
Paste-back fix prompt
Remove any .env files from public/ or static directories. Confirm .gitignore covers .env. Rotate all credentials that were exposed. Add server rules to return 404 for /.env and /.git.
F-06Low
Unauthenticated /debug/admin route
CWE-306 · A01:2021 Broken Access Control
What it is
A leftover debug route at /debug/admin lists users without authentication, intended for local development.
Why it matters
If deployed, anyone can enumerate accounts. Low severity only because the fixture marks it clearly — in production it would be High.
Evidence
src/app/debug/admin/page.tsx — no auth guard
How to fix
- Delete debug routes before deploy, or guard with auth and non-production env checks.
- Add a CI check that fails if /debug paths exist in production builds.
Paste-back fix prompt
Remove or hard-disable /debug/* routes in production builds. Gate any remaining diagnostics behind authentication and NODE_ENV !== production.