Skip to main content
Back to Journal
user@argobox:~/journal/2026-03-27-thirty-credentials-in-the-clear
$ cat entry.md

Thirty Credentials in the Clear

○ NOT REVIEWED

Thirty Credentials in the Clear

Date: 2026-03-27 Agents Used: 14 Explore agents, parallel Scope: Full codebase audit of /mnt/homes/galileo/argo/Development/argobox/ Files Scanned: 87,478 total (45,489 excluding dependencies) Result: Worse than I expected


The Numbers

  • 1,824 TypeScript files + 892 Astro source files audited
  • 372 API endpoints reviewed
  • 38 packages + 66 modules evaluated
  • 2,052 git commits analyzed
  • 15 audit categories scored

The Big One: 30+ Leaked Credentials

Passwords, API keys, tokens. Real ones. Committed to git history.

GitHub tokens. Cloudflare API keys. Keys for 6 different AI providers. Twilio credentials. Resend API key. Infrastructure tokens. All sitting in the repository.

The primary offender: content/docs/admin/environment-variables.md. A documentation page. The page that's supposed to explain what environment variables the project uses. Instead of placeholder values, it has the actual values. The real secrets. In a markdown file. In git.

A docs page became the single biggest credential leak in the entire codebase. That's almost impressive in a terrible way.


XSS Vulnerabilities

Two of them.

Email HTML regex sanitizer — the sanitization is bypassable. Regex-based HTML sanitization has been known to be insufficient for years. Attack vectors exist that slip past pattern matching.

Markdown preview without DOMPurify — markdown content renders to HTML without proper sanitization. No DOMPurify. No allowlist. Raw HTML injection is possible through crafted markdown input.

Neither is currently exploitable by anonymous users since the affected surfaces are behind auth. But "behind auth" means "any authenticated user can exploit them," which is not the same as "safe."


API Security Issues

Six of them. Each one different.

  1. Debug endpoint leaks key lengths — not the keys themselves, but enough metadata to narrow an attack.
  2. Command endpoint skips auth on GET — POST requires authentication, GET does not. The GET handler returns data that should be protected.
  3. File API path traversal — insufficient path validation allows reading files outside the intended directory.
  4. SSRF in api-proxy — the proxy endpoint can be used to make requests to internal services, potentially accessing metadata endpoints or internal APIs.
  5. Demo mode auth bypass — demo mode disables authentication checks in ways that could be exploited if the mode is accidentally enabled in production.
  6. Unsigned JWT extraction — JWT tokens are read without proper signature verification in at least one code path.

Docker Containers Running as Root

Three of them: lab-engine, audiobook-engine, argonaut. No USER directives in their Dockerfiles. Default root. Container breakout risk is low with modern Docker, but running as root inside the container means any vulnerability in the application has maximum privilege.


PII in Git

known_devices.json — contains MAC addresses and personal device names. My devices. Named with my naming convention.

identity_map.json — maps real names to sanitized names. The file that's supposed to protect privacy literally contains the mapping that defeats the anonymization. In git. Where anyone with repo access can read it.


The Rest

  • 67 root-level .md files (should be about 17)
  • 441 personal journal backups tracked in git
  • Dual lock files — both package-lock.json and pnpm-lock.yaml
  • 300 MB of git history bloat from embeddings-index.json
  • 22 stale remote branches
  • 86 console.log statements in production code
  • 301 as any type assertions

Not all bad news though. Auth system graded A-minus — strong multi-layer defense with CF Access, JWT validation, and KV role checks. Test suite has 65+ files with 2,713+ test cases and zero skipped. The bones are solid. The hygiene is not.


What Gets Fixed

15-item checklist. None started yet.

  1. Revoke and rotate all 30+ leaked credentials
  2. Replace real values in environment-variables.md with placeholders
  3. Fix the 2 XSS vulnerabilities
  4. Fix API auth bypasses
  5. Add USER directives to 3 Dockerfiles
  6. Gitignore sensitive data files
  7. git rm --cached the 9 tracked log/txt files + package-lock.json
  8. Purge git history of secrets
  9. Fix CORS wildcards
  10. Reduce root .md files from 67 to ~17
  11. Prune 22 stale remote branches
  12. Add Docker health checks
  13. Standardize dependency versions
  14. Remove 441 journal backups from repo
  15. Dedup recovered-content/

The credential rotation alone is going to be a full session. 30+ keys across GitHub, Cloudflare, Twilio, Resend, 6 AI providers. Each one needs to be revoked in the provider dashboard, regenerated, and stored properly.


The Decision

I chose not to revoke credentials immediately. Document now, rotate later. The reasoning: these credentials have been in git for a while already. A few more days of planned rotation is safer than emergency revocation that might break production services.

The credential vault is stored at /Vaults/argobox/ops/private/ with a Claude-only access policy. 48 API keys, tokens, and passwords inventoried. 27-item rotation checklist created.


The Audit Trail

15 detailed audit reports generated:

  • Master report with scorecard at CODEBASE-HEALTH-AUDIT-2026-03-27.md
  • Individual reports from audit-01-secrets-deep.md through audit-15-data-content.md

All stored in /mnt/homes/galileo/argo/Vaults/argobox/.

87,478 files. 14 agents. 30+ credentials in the clear. And a docs page that was doing the opposite of its job.

At least I know now.