DEV Community

LayerZero
LayerZero

Posted on

3,800 GitHub repos got breached by one VSCode extension. Here's the 5-minute audit that saves yours.

GitHub just confirmed it: one malicious VSCode extension exfiltrated tokens from 3,800 repositories. Not 38. Not 380. Three thousand eight hundred.

If you're a vibe coder who installs extensions to make your editor look cool or speed up boilerplate, this is the moment to read the rest of this post.

Because the worst part isn't that it happened. It's how boring the attack was.

What actually went down

The extension shipped as a normal productivity tool, passed marketplace review, and racked up installs. Then it shipped a quiet update. That update did three things:

  1. Walked the user's filesystem looking for .env, .npmrc, .git/config, and ~/.aws/credentials
  2. Read VSCode's own secret storage (where GITHUB_TOKEN, OPENAI_API_KEY, and friends often live)
  3. POSTed everything to a server the attacker controlled

No zero-day. No exploit chain. No CVE. Just a published extension doing exactly what extensions are allowed to do — read your files.

That's the thing nobody tells you when you click Install: a VSCode extension has the same filesystem permissions you do.

Why this hits vibe coders harder than anyone

If you're building with AI, your laptop is a treasure chest:

  • Anthropic API key
  • OpenAI API key
  • Supabase service role key
  • A GitHub PAT with repo scope
  • Maybe a Stripe secret if you've shipped

All of it sits in .env files, all of it readable by any process running as you. Including the cute little "AI commit message generator" extension you installed last Tuesday.

The 3,800 breached repos weren't enterprise targets. They were side projects, indie SaaS, vibe-coded MVPs. The exact stuff this audience builds.

The 5-minute audit, in order

Stop reading and do these in your terminal. Right now.

1. List every extension you have installed

code --list-extensions --show-versions
Enter fullscreen mode Exit fullscreen mode

Look for anything you don't remember installing. Anything with a publisher you can't immediately identify. Anything with under ~50k installs that you grabbed because a tweet recommended it.

Uninstall anything you can't justify in 5 seconds:

code --uninstall-extension some.suspicious-extension
Enter fullscreen mode Exit fullscreen mode

2. Check what your extensions can see

VSCode extensions don't have a permission model. They get everything your user account has access to. There's no manifest.json listing which folders an extension can read. It can read all of them.

This is not a bug. This is the design.

The only mitigation is: don't install extensions you don't need, from publishers you don't know.

3. Rotate every secret in every .env on this machine

find ~/Desktop ~/Projects ~/code -name ".env*" -not -path "*/node_modules/*" 2>/dev/null
Enter fullscreen mode Exit fullscreen mode

For every file that comes back, assume the contents leaked. Go to each provider's dashboard and rotate:

  • GitHub: Settings → Developer settings → Personal access tokens → revoke + reissue
  • Anthropic / OpenAI: revoke the keys, generate new ones, update .env
  • Supabase: rotate the service role key (this one is bad — it bypasses RLS)
  • AWS: rotate IAM access keys, audit CloudTrail for the last 30 days

Is this annoying? Yes. Is it cheaper than waking up to a $40k OpenAI bill from a crypto miner? Also yes.

4. Audit your GitHub for the actual breach signature

gh auth status
gh api /user/repos --paginate -q '.[] | select(.pushed_at > "2026-05-01") | .full_name'
Enter fullscreen mode Exit fullscreen mode

Look at every repo pushed to recently. Check the commits. Are any of them yours that you don't remember? Any new collaborators? Any new deploy keys under Settings → Deploy keys?

This is the actual breach signature. Stolen tokens get used to add backdoors to private repos, then those backdoors siphon from production.

5. Set up a guardrail so this doesn't happen again

Move your secrets out of .env and into a secret manager — even a free one. direnv + 1Password CLI is the cheapest setup that doesn't leave plaintext on disk:

# .envrc (committed, no secrets in it)
export ANTHROPIC_API_KEY=$(op read "op://Personal/Anthropic/credential")
export GITHUB_TOKEN=$(op read "op://Personal/GitHub PAT/credential")
Enter fullscreen mode Exit fullscreen mode

Now a malicious extension reading .env finds nothing useful. The secret lives encrypted in your vault and only decrypts in your shell session.

The non-obvious takeaway

The VSCode marketplace is not curated the way the iOS App Store is. The bar to publish is a free Microsoft account. Review is mostly automated. The trust model is "we'll catch the bad ones eventually" — and "eventually" was apparently 3,800 repos this time.

Every extension you install is a supply-chain dependency with full read access to your machine. Treat them like you'd treat a random npm package with one maintainer: install only what you need, prefer the ones with millions of downloads from publishers you can name, and audit periodically.

The "AI-everything" gold rush makes this worse, not better. Every week there's a new extension that promises to 10x your coding with some Claude or GPT-powered magic. Most of them are fine. Some of them are not. You won't be able to tell the difference until your bill arrives.

What to do tonight

  1. Run the audit above. All 5 steps. Don't skip step 3.
  2. Pick one project and move it from .env to op or aws-vault or doppler. Just one.
  3. Set a calendar reminder for 30 days from now to do this audit again.

Following LayerZero — we break down the infrastructure that ships AI products without getting them breached. Next up: why .env was never meant for production secrets, and the 3-line setup that fixes it for vibe coders.

Top comments (0)