Coldkey: Paper Backup for Post-Quantum Age Keys
July 22, 2026 · 3 min read
I use age and SOPS for all my secrets management. Every .env file in my homelab is encrypted in git, decrypted in memory at deploy time. It works well -- but it creates a single point of failure: the age private key. Lose that key and every encrypted file becomes unrecoverable.
I needed a paper backup. Not a digital backup (that's the same failure domain), not a password manager export (tied to a cloud account), but something I could print, laminate, and put in a fireproof safe. Something that would survive a house fire, a stolen laptop, and a cloud provider going under.
I built coldkey.
What it does
coldkey generate creates a post-quantum age key pair (ML-KEM-768 + X25519 hybrid) and produces a single-page HTML document with:
- The raw key text in monospace for manual transcription
- QR code(s) encoding the full key file
- A SHA-256 checksum for verification
- Step-by-step recovery instructions
The QR encoding is the interesting part. A post-quantum age key stores only the 32-byte seed (not the expanded ML-KEM-768 private key), so the full keys.txt is about 2,089 bytes -- fitting in a single version-40 QR code. If a key file exceeds that, coldkey splits across multiple QR codes with a framing protocol (COLDKEY:part/total:data) and a checksum.
Security model
The key generation itself is hardened:
mlockall(MCL_CURRENT | MCL_FUTURE)prevents key material from being swapped to disk- Files written with mode
0600and fsynced; temporaries shredded with 3-pass overwrite - Secrets passed via stdin or files only, never in process arguments
There's also a Docker hardened mode using distroless/static:nonroot with --network none --read-only --cap-drop ALL --security-opt no-new-privileges:true. The container has no shell, no network, and a read-only root filesystem. Key material exists only in RAM and the host-mounted output directory.
The paper backup problem
Most key management advice says "back up your keys" but doesn't specify how. A digital backup to S3 or Backblaze is in the same trust domain as the original -- if an attacker gets your cloud credentials, they get both the ciphertexts and the key. A paper backup breaks that chain. The key lives in a different physical and digital domain from the secrets it protects.
The recovery procedure is straightforward: scan the QR codes, strip the framing prefix, concatenate, verify the SHA-256 checksum, and you have your keys.txt back. I tested it by generating a key, printing the backup, shredding the digital copy, and recovering from the printout. It works.
Install
brew install --cask pike00/tap/coldkey
# or
go install github.com/pike00/coldkey/cmd/coldkey@latestThe repo is at github.com/pike00/coldkey with a Homebrew tap, Docker image, and CI. 64 stars so far -- more people than I expected have the same failure mode.
