Free tool · Next.js · Vite · Expo
Paste your .env.
See what leaks.
AI agents love to “fix” a missing env var by adding NEXT_PUBLIC_. That ships your Stripe or OpenAI secret to every visitor. This finds it in a second, before you deploy.
› Checks Next.js, Vite, Expo, Nuxt, SvelteKit, Astro, CRA and Gatsby public prefixes. Values are masked in the results.
next: skip the next one
Skip the cleanup. The VibeBoot SaaS Starter ships with this already handled: only the app URL and app name are NEXT_PUBLIC_, every Stripe, auth and database secret stays server-side, and AGENTS.md and CLAUDE.md tell your agent to keep it that way. Plus auth, Stripe and a database on Next.js 16.4.3. $49, one-time.
14-day money-back guarantee · lifetime updates
- 17 secret key formats
- 7 framework prefixes
- nothing leaves your browser
- updated
01How a key ends up public
One prefix. Four steps. Zero warnings.
- 01The agent hits an errorA client component reads process.env.STRIPE_SECRET_KEY and gets undefined, because only prefixed vars reach the browser.
- 02It “fixes” itThe quickest change that makes the error go away: rename the variable to NEXT_PUBLIC_STRIPE_SECRET_KEY. It works.
- 03The build inlines itAt build time Next.js replaces process.env.NEXT_PUBLIC_… with the literal value inside your JavaScript files.
- 04Anyone can read itOpen DevTools, search the JS for sk_ and copy the key. Bots scan public sites and repos for exactly this.
npm run build && grep -rlE "sk_(live|test)_|rk_(live|test)_|whsec_|sk-(proj|ant)-|service_role|postgres(ql)?://[^\"]+:[^\"]+@" .next/staticNo output means none of those patterns are in the files Next.js sends to browsers. Vite builds go to dist/assets instead.
02What can be public
Some keys are built for the browser. Most aren't.
✓ fine with a public prefix
| Stripe publishable key | pk_live_ / pk_test_ |
| Supabase URL + anon or publishable key | protected by Row Level Security |
| Clerk publishable key | pk_live_ / pk_test_ |
| PostHog project key, Sentry DSN | write-only ingest keys |
| Firebase web config | lock it down with security rules |
| Your app URL, name, analytics IDs | not secrets at all |
✕ never with a public prefix
| Stripe secret / restricted key | sk_ / rk_ |
| Stripe webhook secret | whsec_ |
| OpenAI, Anthropic, xAI, Groq keys | anyone can run up your bill |
| Supabase service_role / secret key | skips Row Level Security |
| DATABASE_URL, SMTP / Redis URLs | contain a password |
| AUTH_SECRET, GitHub client secret | lets people forge sessions |
Audit this project for secrets exposed to the browser. List every env var with a public prefix (NEXT_PUBLIC_, VITE_, EXPO_PUBLIC_, PUBLIC_) and flag any that hold a secret: secret API keys, webhook secrets, service_role keys, database URLs, auth secrets. For each one: rename it without the prefix, read it only in server code (route handlers, server actions, server components) with import "server-only" in that module, and move any client usage behind a server route. Don't add a public prefix to fix an undefined env var. Tell me which keys I need to rotate.
03Start with secrets in the right place
A Next.js SaaS starter your agent can't talk into leaking keys.
Skip the cleanup. The VibeBoot SaaS Starter ships with this already handled: only the app URL and app name are NEXT_PUBLIC_, every Stripe, auth and database secret stays server-side, and AGENTS.md and CLAUDE.md tell your agent to keep it that way. Plus auth, Stripe and a database on Next.js 16.4.3. $49, one-time.
14-day money-back guarantee · lifetime updates
See everything that's inside →- 2 public vars · only the app URL and app name use NEXT_PUBLIC_
- Secrets stay server-side · Stripe, webhook, auth and database secrets have no public prefix in .env.example
- Agent rules · AGENTS.md, CLAUDE.md and .cursor/rules say: read secrets only on the server
- Hosted checkout · Stripe Checkout runs from a server route, so the browser needs no Stripe key
FAQ
Is it safe to paste my real .env here?
The checker is plain JavaScript in this page: nothing you paste is sent, logged or stored, and values are masked in the results. You can also paste only the variable names, or replace values with placeholders; name-based checks still work.
Are NEXT_PUBLIC_ variables secret if I only use them on the server?
No. Next.js inlines a NEXT_PUBLIC_ value into the client bundle wherever client code references it. Treat anything with the prefix as public, and keep secrets unprefixed so they stay on the server.
I already deployed a leaked key. Is renaming it enough?
No. Old builds and caches may still serve the JavaScript that contains it, and someone may already have copied it. Rotate (roll) the key with the provider first, then fix the name and redeploy.
Why do AI coding agents do this?
When a client component can't read a server-only variable, adding the public prefix is the shortest change that makes the error disappear. The real fix is moving the call to the server. A rule in AGENTS.md or .cursor/rules that says “never add NEXT_PUBLIC_ to a secret” stops most of it.
Does this work for Vite, Expo, SvelteKit and Astro?
Yes. It checks these public prefixes: NEXT_PUBLIC_ (Next.js), VITE_ (Vite), EXPO_PUBLIC_ (Expo), NUXT_PUBLIC_ (Nuxt), REACT_APP_ (Create React App), GATSBY_ (Gatsby), PUBLIC_ (SvelteKit / Astro).
Sources: Next.js docs on environment variables and data security, Vite's env and modes, Supabase's API keys guide and Stripe's API keys docs. Checked October 23, 2026. Spotted a mistake? Email [email protected].
$ fixed it? get the next one first
New fixes for what AI agents break, by email.
When we add a fix or a Cursor rule for a new Next.js, Auth.js, Prisma or Stripe break, it goes out in the VibeBoot newsletter. Free, occasional, unsubscribe in one click.
> More free tools
All tools →- VibeBoot DoctorNewPaste any error or your package.json: diagnosis, fix and the rule that prevents it.
- middleware.ts → proxy.tsNewConvert Next.js middleware to Next.js 16 proxy.ts, Auth.js v5 included.
- AGENTS.md checkerNewCheck AGENTS.md for the Next.js 16 managed block, commands and guardrails.
- Access control checkerPaste a route or server action, see what anyone can call.
- Prisma error fixerP2002, P1001, P2021, did not initialize yet: cause and fix.
- Next.js error fixerServer Component, Suspense and hydration errors: cause and fix.
- Stripe webhook fixerPaste a Stripe webhook error, get the cause and the fix.
- Auth.js error fixerMissingSecret, UntrustedHost, redirect_uri: cause and fix.
- AGENTS.md generatorA ready AGENTS.md and CLAUDE.md for your Next.js stack.
- Cursor Rules PackFree downloadScoped .mdc rules for Next.js, Stripe webhooks, access control and more.
- Cursor rules generatorBuild one project.mdc rule for your exact stack.
- AI chatbot cost calculatorCost per message, Pro margin and a safe free-tier cap.