I found it by accident.

I was looking for an old conversation with Claude. Searching through history, trying to recover context I had thrown away too quickly. Eventually I found it. But while I was looking, something else clicked.

All of these conversations are saved locally.

Every session. Every prompt. Every response. Sitting on disk, at predictable paths, no encryption, no access controls, no logging, no detection if something reads them.

And then the second thought arrived, the one I always get when I find something like this:

How many people have put credentials in here?


The way people actually use AI tools#

This is not theoretical.

Developers use Claude Code, Cursor, and Codex to ship real work. They paste in environment configs, ask the model to help debug authentication flows, hand it connection strings so it can actually run the code it writes. They share API keys to give the tool the context it needs. They treat the session like a trusted environment.

That trust is reasonable. It is also exactly what makes this interesting.

Because those sessions do not disappear. They accumulate. AWS keys, GitHub PATs, Stripe secrets, database connection strings, OpenAI tokens, Slack webhooks. Each one pasted in as context for a task and then forgotten about completely.

The conversations are still there. They are still readable. And on most machines, nothing is watching them.


The kill chain is short#

From an attacker’s perspective, this is almost boring in how simple it is.

Get local access to a developer’s machine. It does not matter how. Phishing, physical, supply chain, any initial foothold will do. Find the conversation files. Read them. Extract the credentials. Use them.

That is it. You do not break anything. You do not trigger anything. You log in.

The attacker is not exploiting a vulnerability in Claude or Cursor or Codex. They are exploiting the fact that those tools dutifully recorded everything the user asked them to do, and nobody thought to protect that record.

Think of it as an AI infostealer. Except instead of hooking a keylogger or intercepting clipboard data, you just read a file.

What surprised me most when I started looking at where these tools store their data was not that the files existed. It was that nothing protects them. No encryption. No ACLs beyond standard filesystem permissions. No canary mechanism. No detection. The assumption seems to be that if an attacker already has local access, it is already over.

Maybe. But that assumption is worth questioning when the files contain credentials that reach far outside the local machine.


What is actually on disk#

Claude Code CLI stores sessions in ~/.claude/projects/**/*.jsonl. Plaintext. One conversation per file. Human-readable. Every message, every tool call, every response. A GitHub issue filed against the Claude Code repo (#50014) documents a researcher finding five distinct secrets across 34 session files after 30 days of normal usage.

Cursor stores data in state.vscdb - a SQLite database, global and workspace-scoped. Ask yourself: how many developers using Cursor every day know that file exists? A detailed analysis found the global database alone can grow to over 1 GB, with additional conversation data stored across multiple locations most users never see.

Codex CLI keeps state in ~/.codex/state_5.sqlite plus plaintext JSONL rollout files under ~/.codex/sessions/. Both confirmed in open issues tracking unbounded storage growth.

ChatGPT Desktop encrypts its conversation files with a key stored in the system keychain - added after a July 2024 disclosure showed conversations were stored in plaintext. It is better than nothing. Against a credible attacker with local access who can also read the keychain - which many attack paths allow - it buys limited time.

Claude Desktop is on the roadmap. Path detected. Extraction in progress.

The common thread is that none of these were designed with forensic extraction in mind as a threat. They were designed to work well. They do. That is also why this matters.


Building ghosttype#

I built ghosttype in a few hours using Claude Code, which felt appropriately recursive.

The goal was simple: a local forensic scanner that reads conversation history from AI tools and extracts credentials. CLI because that is what red teams use. Python because it is the fastest path for me to build something real. Local-only because it is quieter, simpler, and the point is to stay off the network.

The detection engine has two layers.

The first is regex. Thirty-plus patterns for known credential formats: AWS access and secret keys, GitHub PATs in six formats, OpenAI tokens, Anthropic API keys, Stripe keys, Slack tokens, HashiCorp Vault tokens, GCP service accounts, JWT tokens, PEM private keys, database connection strings, and more. When a pattern matches, confidence is high.

The second layer is heuristic. Ten patterns using variable-name context signals - things like API_KEY=, JWT_SECRET=, password =. Lower confidence, but they catch the long tail of credentials that do not follow predictable formats.

False positives were the main problem to solve. The tool uses an entropy threshold of 3.0 bits per character, which filters out most placeholder values and documentation examples. It is not perfect. Getting there took a lot of back-and-forth with Claude Code and local testing. It will keep improving with real-world usage and feedback.

The output is a report. Every finding includes the source tool, credential type, severity, the value itself (or redacted if you prefer), the file path, confidence level, and 200 characters of context around the match. JSON and CSV by default. Pipeable to jq if you want to filter.

# Scan everything
ghosttype scan

# High-confidence findings only
ghosttype scan --min-confidence high

# Pipe to jq for critical only
ghosttype scan --format json --output - --quiet | jq '.[] | select(.severity == "critical")'

The red team case#

Post-exploitation on a developer machine. This is one of the first things I run now.

Not looking for vulnerabilities. Looking for keys that work. Cloud environments. Source code. CI/CD pipelines. Production databases. The developer already authenticated with all of those things. The record of that authentication is sitting in a file readable in under a second.

You do not break in. You log in.


The blue team case#

The value here is different but equally practical.

Run ghosttype and you get a map of what secrets have been exposed through AI tool usage on this machine. That tells you several things at once.

Which keys need to be rotated, and how urgently. Which users need to be educated about what they are putting into AI sessions. Which secrets management practices are not working, because the credentials are ending up in chat history instead of a vault. And it tells you where to build detections - because if you know this is a path attackers will use, you can start watching for it.

One more thing worth considering: deception. If you know attackers may be reading AI conversation history, you can plant things there on purpose. Canary tokens. Honeypot credentials. Keys that look real, alert on use, and lead nowhere useful. ghosttype tells you what is in those files. Nothing stops you from also controlling what is in those files.


The uncomfortable part#

There is an irony worth sitting with.

The tools people use to write more secure code, to move faster, to reduce bugs, to automate the tedious parts of development - those same tools are quietly accumulating a record of every credential the developer has ever handed them.

Nobody told you to rotate those keys after the session. Nobody warned you the history was there. Nobody built a detection for someone reading it.

That is not a failure of the AI tools specifically. It is a failure of the mental model we apply to them. We treat AI sessions like we treat a conversation with a colleague: we say what we need to say to get the work done, and then we move on. We do not think about the transcript.

The transcript exists.

As these tools get more capable - more connected, more agentic, more integrated into production environments - the amount of sensitive material flowing through those sessions will increase. More credentials. More context. More blast radius if that history gets read by someone who should not have access to it.

We need to stay on guard. We need detection. We need response plans. And we should probably start thinking about how we protect these files differently, before the problem gets larger than it already is.


What to do with this#

Run it on your own machine first.

ghosttype is open source, local-only, and built for authorized use: github.com/xFreed0m/ghosttype

If it finds nothing, that is useful to know. If it finds something, you have work to do.

Either way, now you know what is there.

That is always the better position to be in.

“Three may keep a secret, if two of them are dead.” - Benjamin Franklin

logo