~/blog $ cat three-recipes-in-a-docker-volume.md

Three recipes in a Docker volume

Every homelab has a junk drawer. Mine turned out to be named b47a8c7e0ec8f100142a2c0dd323f9f374a4c979646c3f40680d0e437a0eeb79.

There are three new recipes in the recipes section: a five-star chocolate mousse, sourdough-discard coconut biscuits, and a dairy-free coconut mousse. None of them is actually new. They're from early 2025, back before this became a bread blog. For most of the eighteen months since, the only copy of them was a 1.4 MB SQLite file that no backup knew existed.

Moving house

My self-hosted stuff (Immich, Jellyfin, Paperless and friends) lived on a VMware virtual machine called, with tremendous imagination, vmware. This week all of it moved to Hendrix: a real Fedora box, a real SSD, everything in Docker Compose, the photos and films on an SMB share.

The migration was thorough in a way I would never be at midnight. SHA-256 manifests. A Postgres restore in a single transaction. A 5.4 GB tarball of ~/Selfhosted. An inventory of every running container: six apps running, so six apps moved. Then the VM was switched off.

Clean. Done. Suspiciously done.

The route to nowhere

Nginx Proxy Manager still had a route for mealie.farcas.local, pointing at the switched-off VM. Mealie wasn't in the inventory, because Mealie wasn't running. And its folder in the backup was empty. 8 KB. Three directories. Zero files.

The compose file had mounted the data at ${PWD}/../volumes/mealie-data. ${PWD} is wherever you happened to be standing when you typed docker compose up — and wherever I'd been standing in February 2025, the recipes never landed there. Docker put them in an anonymous volume instead, named after its own hash, tucked under /var/lib/docker/volumes/ where no folder-based backup ever looks.

The recipes weren't lost. They were just somewhere nobody had written down. Which, for a backup, is the same thing.

Getting them out

The VM came back up for one last look, with its Immich stopped first so two servers wouldn't start rearranging the same photo library. No passwordless sudo, so /var/lib/docker stayed locked. But anyone in the docker group can start containers, and containers can mount volumes.

So every volume on the machine went into a throwaway Redis container, read-only, because Redis happened to be the only image on disk with a shell in it. One find for anything ending in .db, one tar over SSH, and mealie.db was home.

Inside: three recipes, one user, a five-star rating I don't remember giving, and a last_made date proving I actually baked the biscuits on February 28, 2025. Past me had a good week.

The same sweep turned up other orphans: a change-detection datastore, a Postgres cluster, half an ERPNext install I have no memory of. I am choosing not to think about the ERPNext install.

Where recipes belong

Mealie runs on Hendrix now, with all its old data. I still can't see the recipes in its UI.

I've decided I don't care. They're Markdown files in a git repo now, next to the crêpes, which is where they belonged all along. Plain text doesn't need a container to be readable, and it's never once been lost because I forgot which directory I was standing in.

$ docker volume ls -q | grep -cE '^[0-9a-f]{64}$'
25
$ # cool. cool cool cool.
$ █

— EOF —

cd .. →