The key never expired
Truffle Security spent four years pulling AWS keys out of git history, Hugging Face datasets, Docker images and CI logs. Of the ones they could re-verify, 88% still authenticate. The median live key is five years old, 2,505 users never rotated theirs, and 929 of them wear the quarantine policy AWS attaches when it spots a key in public. Nobody failed to detect anything. Bromure Agentic Coding keeps the half of the key that signs out of the VM, so what an agent leaks is dead the day it leaves.
Finding leaked credentials is a solved problem. Truffle Security has been at it for four years and has 431,875 AWS findings to show for it. The unsolved half is the step after, where someone has to log in and delete the key. That happens one time in seven.
Truffle Security published a census this week, and BleepingComputer picked it up on Thursday. Since August 2022 the company has collected AWS access keys from the places they surface in public: git history, Hugging Face datasets, Docker images, package registries, CI logs. Then it checked whether they still work.
The report counts 431,875 verified AWS findings, deduplicated to 64,024 unique access keys across 50,654 distinct accounts. Of those, 10,616 pairs carried enough material to re-test. Eighty-eight percent of them still authenticate. That is 9,308 keys, live today, that anybody could have picked up off a public surface at some point in the last four years.
They kept the verification narrow, using read-only metadata calls: sts:GetCallerIdentity,
iam:ListAccessKeys, policy-name enumeration, a budget read, one Cost Explorer call per
account. They read no data and changed nothing, and they told 10,260 of the 10,616 owners
before publishing.
Then look at how old the keys are.
Five years, and counting
The median still-working key is 1,831 days old. The oldest is 17.4 years. Only 25 keys in the set, nine tenths of one percent, date from the last thirty days.
That distribution describes sediment rather than a stream of fresh accidents getting caught and cleaned. A key leaks and stays leaked, because an AWS static access key has no expiry: no clock, no renewal, no certificate going stale in eighteen months. It works until someone opens the console and deletes it. Truffle measured how often that someone shows up. Of the users whose keys the researchers could enumerate, 398 out of 2,903 have a newer key sitting alongside the leaked one, which is 13.7%. The remaining 2,505 never rotated it.
You cannot pin that on the discovery step either, because Amazon had already done the
discovering. When AWS spots one of its own keys in public it attaches a policy called
AWSCompromisedKeyQuarantine to the user, clamps down what the key can do, and emails the
account. Nobody has to ask it to. Truffle found 929 IAM users, 12% of the 7,590 active
ones, wearing that policy right now. A hundred and twelve of them wear the original
version of it, so AWS flagged those at least three years ago and they still answer.
Detection worked, the email went out, and three years later the key is still good.
The leak surface moved somewhere with no delete button
The single largest source in the whole census is Hugging Face: 8,482 unique live keys across 3,394 datasets, and a 17.9% root-key rate, well above the rest of the population.
Truffle had already measured the far end of that pipe. In June the team cloned every public dataset on Hugging Face: 186.9 million unique files, 7.6 petabytes, around 815,000 dataset repositories. They flattened Parquet, Arrow, JSONL and archives into scannable text and verified everything they found. The result was 221,303 live, unique credentials sitting in 6,003 datasets: 11,496 AI-provider keys, 8,557 Google Cloud service-account keys across 3,811 projects, 8,594 working database logins, 3,343 AWS keys that pass an STS identity check, 349 GitHub personal access tokens of which 223 can push code and 130 can rewrite CI workflows.
Two of their examples show how far one mistake travels. Somebody pasted a Brazilian fintech's AWS key into a chatbot, and it now turns up mirrored about eighteen times across different corpora. An Infura key captured the same way ended up in 1,131 datasets and 10,162 separate file locations. Forty-four percent of the unique live secrets Truffle found appear in more than one dataset.
Then people train on those datasets. StarCoder's documented training data contains 25,217 of these keys; Swallow, 22,484; OLMo 3, 21,278. The large proprietary models keep their corpora private, so nobody outside knows.
Truffle draws the blunt conclusion: rotation is still the only fix, because nobody can go back and clean training data. Treat any key that ever hit a public repo, a web page, or a chatbot as burned.
Every source on that list is something an agent writes
Look again at where Truffle went shopping: git history, Docker images, package registries, CI logs, dataset uploads. Those are build outputs, and they are the artifacts a coding agent now produces unattended, overnight, at a rate no team could review.
An agent that runs a backlog while you sleep writes commits, rewrites lockfiles, builds
images, pushes branches, and fills logs. Every one of those is a publication surface, and
the agent has your ~/.aws/credentials in reach the whole time, because that is how the
SDK is designed to find it.
Coding agents now write those artifacts faster than any tool before them, and the 13.7% has not moved.
The half that signs stays on your Mac
Bromure Agentic Coding runs the agent in a disposable Ubuntu VM on Apple's Virtualization framework, with a host-side proxy as its only route out. AWS needs its own handling in that design. SigV4 never puts the secret on the wire, since the SDK consumes it in-process to compute an HMAC, so a proxy has nothing to swap in transit. Bromure moves the signing instead.
Inside the VM, ~/.aws/config names a credential_process helper. When the SDK asks for
credentials, the helper returns the real access key ID paired with a forty-character fake
secret, minted fresh per session. The access key ID is an identifier, not a secret, and
it is the half that identifies which IAM user is calling. The secret access key is the
half that signs, and it never enters the VM's address space at all. Bromure does not even
export AWS_ACCESS_KEY_ID or AWS_SECRET_ACCESS_KEY into the guest environment, on the
grounds that environment variables leak through /proc, ps -E and shell history. The
VM gets a region string and nothing else.
The SDK signs a request whose signature cannot be right. On the way out, the host strips
that signature and recomputes SigV4 with the real material. aws, boto3 and terraform all
work as usual. Anything that routes around the proxy gets InvalidSignatureException back
from Amazon, which is the failure you want.
Now run a Bromure workspace through Truffle's methodology. Their bar for counting a key is
a signed sts:GetCallerIdentity that comes back valid. Suppose a compromised dependency
harvests the credentials file out of that guest, or the agent gets talked into cat-ing
it, or a build inlines it into a public bundle. What leaves is an identifier and forty
characters that were never the secret. It fails on the day it leaks, so it never joins the
sediment layer and there is no five-year tail behind it.
That also removes the rotation step that waits on a human. The real secret lives in one place, on your Mac, in the profile's Credentials pane. Change it there and the next session picks it up. Nobody has to work out which of ninety overnight runs wrote which artifact.
A signed request narrower than the key that signs it
The other headline in the census is reach. Of 817 keys tied to a business, 768 gave full
control of the account: 526 root keys and 242 IAM users holding AdministratorAccess.
One hundred and thirty of those root keys sit on organization management accounts, the
account that governs every member account in the org. Across the users the researchers
could enumerate, 976 of them held AdministratorAccess, or 84%.
Those are keys minted for convenience, years ago, for a task that needed three permissions.
Bromure's Guardrails setting narrows the credential at the point of use, so you never have
to remember to narrow it at the source. It is a host-side policy engine in the proxy. For
AWS it reads the action name out of the X-Amz-Target header for JSON-protocol services
like DynamoDB and Lambda, or out of the Action= parameter for query-protocol services
like EC2, IAM and SQS, and falls back to HTTP method for S3. Delete*, Terminate*,
Remove*, Purge* and Destroy* classify as destructive; Get*, List* and Describe*
classify as reads. Set the profile to Read-only and a mutation comes back as a hard 403
that the agent reads as an ordinary API failure. Set it to Block destructive and creates
and updates go through while deletes do not.
Your Mac enforces this, not the VM, so an agent that has been talked into something cannot argue its way past it. The credential your host signs with ends up narrower than the credential itself, which is worth having in a population where 84% of the enumerable users carried admin.
The record shows up before the invoice
One more number from the report. Of the 2,754 accounts whose budgets the researchers could read, 262 have a budget alert configured at all, which is 9.5%, at a median limit of eight dollars. That same set spent $420,631 in July, with fifty accounts over $1,000 and nine over $10,000. Most of those owners will meet their intruder on an invoice.
Bromure writes the record while the work happens. Every request the host signs emits a
credential.aws_sign row into Window → Security Timeline carrying the service, method,
host, region and the masked access key ID, alongside the package fetches, the firewall
verdicts and the credential swaps. Bromure keeps that log on the Mac, where nothing inside
the VM can edit it. For the stricter version, AWS → Require approval to use turns each
signing call into a consent prompt with a time-bounded grant, so an afternoon of real work
asks once.
Bromure applies the same idea one step earlier, when you first bring a profile up. It runs
your imported agent configuration through a redaction pass: structured JSON, TOML and YAML
filtered by key name, matching token, secret, password, apikey, credential,
authorization, private_key and access_key, and prose filtered by token shape, matching
AKIA, ASIA, sk-ant-, ghp_, glpat-, AIza and npm_. Whatever real secrets sit in
the dotfiles on your Mac, they do not ride into the VM with the rest of the setup.
What the census proves
Truffle Security ran this well: read-only calls, no data touched, 10,260 of 10,616 owners told before publication. AWS comes out of it better than the headline suggests, since the quarantine policy is Amazon finding its own leaked keys and warning the owner without being prompted. Both halves of the detection pipeline did their job.
The result was still 9,308 live keys with a median age of five years, and a rotation rate of 13.7%.
The failing control asks a person to complete a chore months or years after the mistake, on a system they may not own any more, for a key that gives no sign of being a problem. Controls shaped like that fail at scale, and they were failing before anything started writing commits overnight.
So stop asking the chore to carry the weight. Put a credential in the workspace that was never the credential, and the census has nothing to count, the corpus has nothing to mirror, and the five-year tail belongs to somebody else.
Sources: Truffle Security, "Leaked Corporate AWS Keys Held Full Admin Rights" (Aug 19, 2026) · Truffle Security, "Scanning 7.6 Petabytes of HuggingFace Training Data for Secrets" (Jun 1, 2026) · Truffle Security, "Introducing TruffleHog AWS Analyze" (Aug 20, 2026) · BleepingComputer, "Hundreds of leaked AWS keys give full control over corporate accounts" (Aug 21, 2026) · Cybernews, "Massive exposure: researchers test leaked AWS keys, 9 out of 10 still authenticate" (Aug 21, 2026)