All posts
Threat6 min read

Fake AI crawlers are hunting your .env files. Here's how to check yours

Line of friendly-looking robots walking past server racks while one shines a light on a locked folder with a key

If you've looked at your access logs lately and seen a lot of "ClaudeBot" or "ChatGPT" traffic, you might have assumed it was AI companies indexing your site. Some of it probably was. But a growing share isn't: it's credential scanners wearing an AI crawler's name tag, and they're asking for one file in particular. Your .env.

This week, bot-management vendor Cequence published research on a single actor that rotated through about 32 AI bot identities, including names belonging to OpenAI, Anthropic, Meta and Perplexity. On one day in October it reached 48% of the Cequence-protected organizations that saw any AI bot traffic at all. It wasn't crawling content. It was requesting roughly 90 file paths where secrets tend to live: .env files, cloud credential files, private SSH keys and server environment data.

Nearly all of those requests were blocked or failed, and no breach has been reported. That's good news for Cequence's customers. The question for you is simpler: if one of these bots hit your app today, would it get a 404 or your Stripe key?

What's going on

Three separate reports from the last few months point the same way.

  • Cequence (published Oct 28): one scanner, ~32 fake AI identities, active from at least late September through late October. Each cloud address fired a burst of 50 to 190 requests in about eight seconds and then moved on. It used more than 300 addresses in a single day, and none of the late-September addresses showed up again a month later. CSO Online's write-up notes that this kind of rotation makes static IP blocklists far less useful.
  • GreyNoise (August): a different cluster impersonated 13 AI crawlers from 824 addresses, none of which sat inside the companies' published IP ranges. The most-requested paths read like a checklist of every place a framework might leave secrets: /.env, /app/.env, /api/.env, /backend/.env, /.env.local, /.env.production, /.env.bak, /.aws/credentials. The fake bots never once asked for /robots.txt. Anthropic's real crawler did, and never requested a credential file.
  • Symantec, via Help Net Security (Oct 23): a honeypot posing as an unprotected AI service caught an attacker's autonomous agent at work. Its jailbreak prompt told the model that reading .env files, API keys and database schemas was ordinary development work. Most of the 127,000+ requests the honeypot logged were recon, stolen-key attempts and probes for exposed config files.

The pattern is clear. Attackers know that site owners have started allowlisting AI crawlers, so they borrow those names. And they know that AI keys are worth real money: a leaked OpenAI, Anthropic or Gemini key can run up a large bill before you notice.

Why builders who ship fast should care

The user agent string is just a header the visitor writes about itself. It proves nothing. If your hosting setup, CDN rule or WAF lets "known AI bots" through, you may have opened a door for exactly this traffic.

More importantly, the thing being hunted is a classic mistake in quickly shipped apps. A .env file ends up in the web root because the build copied the whole project folder. A .env.production.bak gets left behind after a late-night fix. A Docker image serves /app as static files. None of this needs a clever exploit. It's a GET request, and the bot doesn't care whether it's the first request it makes or the ninetieth.

Exposed .env files: why this file is so valuable to attackers

How to check your app

Start with the paths the scanners actually request. Run the loop below from a terminal, with your own domain.

What you want to see is 404 or 403 for every line. A 200 is a problem, but check the body before you panic: many single-page apps return index.html with a 200 for any unknown path. Run curl -s https://yourapp.com/.env | head -5 and look at what comes back. If you see KEY=value lines, treat every secret in that file as compromised.

for p in .env .env.local .env.production .env.bak .env.old \
         app/.env api/.env backend/.env .aws/credentials .git/config; do
  code=$(curl -s -o /dev/null -w "%{http_code}" "https://yourapp.com/$p")
  echo "$code  /$p"
done

While you're at it, check the related leaks that give away the same secrets by another route:

  • A reachable .git directory lets anyone rebuild your source, including any .env that was ever committed.
  • Keys in your JavaScript bundle don't need a scanner at all. Open DevTools and search the bundle for sk-, AIza or key.
  • Source maps in production can ship your original source, comments and all.
Exposed .git directory: how attackers rebuild your source

Then check your logs. Search for requests to /.env or /.aws/credentials. If any of them returned a 200, that's your incident start time.

How to fix it

1. Get secrets out of the web root. The real fix is that the file simply isn't there to serve. Environment variables belong in your host's settings (Vercel, Netlify, Railway, Fly and the rest all have them), not in a file that gets deployed alongside your static assets. Make sure .env* is in both .gitignore and .dockerignore.

2. Block dotfiles at the server as a backstop. For nginx:

# Deny all hidden files except the ACME challenge path
location ~ /\.(?!well-known) {
    deny all;
    return 404;
}

For Apache (.htaccess):

<FilesMatch "^\.">
    Require all denied
</FilesMatch>

For an Express app serving static files, express.static ignores dotfiles by default. Don't override it with dotfiles: 'allow'.

3. Rotate anything that was exposed. Deleting the file doesn't un-leak the keys. Rotate every secret that was ever reachable, starting with payment, database and AI provider keys. Our post on the Railway breach walks through how to rotate your app's secrets without downtime.

4. Stop trusting the user agent. If you allow AI crawlers through a firewall or rate limit, verify them against the IP ranges the companies publish instead of matching on the name. GreyNoise lists the official JSON files for Anthropic, OpenAI, Google and Perplexity in its report. Cequence's advice is the same: verify through signed requests, published address ranges or direct integrations.

5. Patch your dev tooling if it's exposed. GreyNoise also saw these scanners attempting the Vite file-read bug CVE-2025-30208. If a Vite dev server is ever reachable from the internet, upgrade to 6.2.3, 6.1.2, 6.0.12, 5.4.15 or 4.5.10 or later, and don't expose dev servers publicly in the first place.

6. Set spend limits on AI keys. Most AI providers let you cap monthly spend or scope keys to specific projects. It won't stop a leak, but it turns a four-figure surprise into a small one.

Quick checklist

Before you close the terminal, make sure that:

  • Every path in the curl loop above returns 404/403, not your file.
  • .env* is in .gitignore and .dockerignore.
  • Your server or host denies dotfiles.
  • No secret keys are in the JS bundle or source maps.
  • Any key that was ever reachable has been rotated.
  • AI crawler allowlists check IP ranges, not just the user agent.
  • Spend limits are set on AI provider keys.

Check it before the bots do

These scanners rotate through hundreds of addresses and spend about eight seconds on each burst. You won't win by watching logs. You win by making sure there's nothing there when they knock.

AppSafe checks for exactly the leaks these bots go looking for, including reachable .env files, exposed .git directories, database dumps and API keys in your frontend bundle, and every finding comes with a copy-paste fix prompt for your AI coding tool. If you're still in pre-launch mode, our checklist for AI-built apps is a good companion read. Run a free scan of your app and see what a bot would see.

Run this checklist automatically

One free scan checks your app for all of these issues and gives you an AI fix prompt for each finding.

Scan my app free