26,400 Live Keys in Public Code: Deleting a Secret Isn’t Revoking It
A researcher scanned 7.25 million public repositories and found 26,400 cloud and AI keys that still worked. The lesson isn’t “don’t commit secrets.” It’s that deleting one from your code doesn’t revoke it.
Every developer has done the nervous dance: you realize an API key slipped into a commit, so you delete the line, push the fix, and breathe out. Here’s the uncomfortable truth that just got measured at scale: that key is very likely still live, still sitting in your git history, and still usable by anyone who looks.
Independent researcher Ben Zimmermann, working with MongoDB’s Kingfisher team, scanned about 7.25 million public repositories on Gitee, China’s largest code-hosting platform, and found 26,400 unique credentials that actually authenticated when tested. Not 26,400 strings that looked like keys. 26,400 keys that still opened the door, to cloud accounts, AI APIs, and in at least one case an organization-admin account on a major enterprise AI platform.
The study is about Gitee specifically, but nothing about the lesson is regional. The same mistake lives in public repos on every platform, and this research is a clean, numbers-backed reminder of how long leaked secrets stay dangerous. Let’s look at what was found, the clever detail in how they found it, and what to actually do about your own keys.
What they found
The numbers come from Zimmermann’s write-up on MongoDB’s blog and reporting by The Hacker News. The scan covered 7,256,531 public Gitee repositories and, after deduplicating by token value, surfaced 26,400 unique credentials that were verified live, meaning each one was actually tested against the service that issued it and still authenticated.
The breakdown leans heavily toward cloud and AI services:
The heavy presence of Chinese cloud and AI providers (Alibaba, DeepSeek, Zhipu) makes sense given Gitee’s user base, but international services like OpenAI and the YouTube API show up in force too. The platform is a crossroads where regional developers wire up both local and global services, and the keys for all of them end up in the same public commits.
The single scariest find wasn’t a volume number. Zimmermann reported one live organization-admin credential for a major enterprise AI platform, which he chose not to name publicly. An org-admin key is not “someone can run up a small API bill”; it’s potentially control over an organization’s entire account on that platform. One leaked key like that can matter more than the other 26,399 combined.
Two honest limits on the data, which the researcher is upfront about. The scan ran for about a month and the exact test dates weren’t published, so “live” means live when tested, not necessarily today. And it covered 7.25 million repositories, a large sample but not all of Gitee, so the real exposure is plausibly larger, not smaller.
The clever part: one scanner isn’t enough
The methodology hides the most quietly important finding. Zimmermann ran two open-source secret scanners, TruffleHog and Kingfisher (MongoDB’s tool), against every repository’s full commit history, and validated each hit against the live service. The two tools barely agreed.
TruffleHog found 12,737 working credentials; Kingfisher found 14,664.
But only 1,001 were found by both.
Each scanner caught thousands the other completely missed. The clearest example: Kingfisher found all 1,489 Zhipu AI (BigModel) keys because TruffleHog has no detector for Zhipu’s key format at all.
That’s the lesson worth carrying beyond this story. Secret-scanning coverage varies a lot by provider, and the gaps are widest for regional cloud and AI services that the big Western-built scanners haven’t prioritized.
If you rely on a single tool, especially for keys from providers outside the usual US set, you’re likely blind to a meaningful share of your own exposure.
Why git history is the real trap
Here’s the mechanism behind the headline, and the part that catches careful developers. When you commit a secret, then “fix” it by deleting the line and committing again, the secret doesn’t vanish. Git keeps the whole history. The old commit still contains the key, and anyone can check out that commit, or just run a scanner over the history, and read it straight out. Your latest revision looks clean; your repository is not.
Get Wartelski.’s stories in your inbox
Join Medium for free to get updates from this writer.
That’s exactly why this scan found so much. The researchers inspected full commit histories, not just the current HEAD.
A key you thought you "removed" years ago is still sitting in commit
a3f9c2…, patiently authenticating.
And then there’s the second half, the one that turns a theoretical exposure into a measured one: live validation. The scanners didn’t just pattern-match strings that looked like keys. They tested each candidate against the issuing service to confirm it still worked. That’s why the number is so alarming. 26,400 isn’t “keys that were once committed”; it’s keys that were committed, possibly long ago, and still authenticate today because nobody ever revoked them.
Put those two facts together and you get the core message of the whole study, the thing worth tattooing on a sticky note:
Deleting a secret from your code is not the same as revoking it. Only the provider can revoke it. Until you do that, it’s live.
This is also why the usual advice to “scrub it from history with git filter-repo or BFG" is necessary but not sufficient. Rewriting history makes the key harder to find going forward, but if the repo was ever public, assume someone already has the key. Rewriting history is cleanup; rotating the key at the provider is the actual fix.
What a leaked AI or cloud key actually buys an attacker
AI API keys are a direct line to your bill. A leaked OpenAI, DeepSeek or Zhipu key lets someone run models on your account and your credit card. This has a name now, LLMjacking, and it’s a booming niche precisely because AI compute is expensive and the keys are easy to find. Victims often discover it as a sudden, eye-watering usage charge. Beyond cost, depending on the key’s scope, an attacker may reach fine-tuned models, stored files or conversation data tied to the account.
Cloud keys are worse. The single largest category here was Alibaba Cloud, at 9,473 keys. A cloud access key, depending on its IAM permissions, can mean reading or deleting storage buckets, spinning up expensive compute (classic for crypto mining), reaching databases, or pivoting deeper into an account’s infrastructure. A cloud key is rarely “just one service”; it’s a foothold.
And the org-admin key is the nightmare tier. That single unnamed enterprise-AI-platform admin credential could, in the wrong hands, mean control over an entire organization’s account: other users, their keys, their data, their billing. It’s the difference between a break-in and getting the master key to the building.
This also slots into a pattern that’s run through this year’s security news: AI infrastructure is both a target and a prize. We’ve seen poisoned packages harvest cloud keys to run models on someone else’s account, and attackers specifically hunting credentials to resell or to power their own AI workloads. A public repo full of live keys is the low-effort version of the same goal, no exploit required, just a scanner and some patience.
The one piece of good news: the researchers found no confirmed malicious use of these specific credentials, and they notified the major affected providers. The bad news is that notification isn’t revocation. At publication, it wasn’t confirmed that the keys had actually been revoked, and individual developers who leaked them were never contacted. So many of these may still be live as you read this.
What to do, today and going forward
Split this into two jobs: find what’s already leaked, and stop the next leak.
If you’ve ever pushed to a public repo
Rotate, don’t just delete. This is the whole point of the article. For any secret that has ever been in a public repository, go to the provider and revoke or rotate it. Deleting the commit, or even the whole repo, does not make an exposed key safe. Zimmermann’s own advice is blunt: treat any key that’s ever been in a public repo as exposed, and revoke it at the source.
Scan your own history. Run a secret scanner over your full git history, not just the working tree, and ideally run more than one, given how little the two tools overlapped. TruffleHog and Kingfisher are both free; using both catches far more than either alone, especially for non-US providers. GitHub, GitLab and others also offer secret scanning for repos you host there.
Check provider usage logs. For any key you find exposed, look at the account’s recent activity and billing for anything unexpected before and after you rotate. Unusual model usage or compute spend is the tell for LLMjacking or cloud abuse.
So it doesn’t happen again
Keep secrets out of code entirely. Use environment variables, a secrets manager (cloud KMS, Vault, or your platform’s secret store), and a committed .env.sample with placeholders so nobody is tempted to hard-code the real thing. Add .env and friends to .gitignore on day one.
Scan before the commit lands. A pre-commit hook (via pre-commit, Husky, or a scanner's own hook) that blocks a commit containing a secret stops the leak at the source. Pair it with server-side scanning (push protection) so a missing local hook isn't a single point of failure.
Prefer short-lived, least-privilege credentials. A key that expires in an hour is far less dangerous leaked than one that lives forever. Scope keys to exactly what they need, read-only where possible, and avoid org-admin keys in anything a developer might touch. The blast radius of a leak is set long before the leak happens, by how much that key could do.
Make rotation routine, not an emergency. If rotating a key is a painful, rare event, it won’t happen when it matters. Build it into your normal operations so that “rotate everything that touched that repo” is a button, not a project.
The takeaway
The durable lesson is a mindset shift. Treat a leaked secret the way you’d treat a lost physical key to your house: you don’t feel better because you can’t see it anymore; you change the lock. For credentials, changing the lock means revoking at the provider, every time, no exceptions. And because scanner coverage is so uneven, especially for regional and AI providers, assume your tooling is missing some of your exposure and lean toward short-lived, least-privilege keys so that the leaks you don’t catch hurt less.
If you enjoyed this article, feel free to give it some claps 👏 — it helps more people discover this content. To stay updated with my latest posts, hit the Follow button! You can also consider subscribing to get notified about new articles.








