Guides
Backups & restore
Astrodock keeps all its data on your box. One script captures the databases and the object store into a single timestamped tarball. Schedule it with cron, and copy the result off the box for real safety.
What data exists
Everything Astrodock stores lives in Docker volumes, so it survives container restarts and upgrades. The pieces worth backing up:
| Volume | What's in it |
|---|---|
pgdata | The Postgres data: the control-plane database plus every internal per-app database. |
objectdata | The bundled object store (files apps uploaded in internal-storage mode). |
static | Built static assets served for Node buildpack apps. |
apps / repos | Deployed app working directories and cloned source — rebuilt on deploy. |
pm2home | Process-manager state for running apps. |
caddy_data / caddy_config | Issued TLS certificates and the proxy's runtime config. |
The backup script focuses on the two that hold your irreplaceable data — the
databases (pgdata) and the object store (objectdata). The rest is
regenerated from your repo and .env on deploy; certificates re-issue themselves.
Don't forget .env
Your .env holds the secrets needed to read encrypted data back. It's gitignored, so
keep your own safe copy somewhere private — without it a restore is much harder.
Run a backup
From the repo root, with the stack running:
./scripts/backup.sh
By default the tarball lands in ./backups/. Pass a directory to put it elsewhere:
./scripts/backup.sh /mnt/backups
Under the hood the script:
- Runs
pg_dumpallthrough thepostgrescontainer, capturing the control-plane DB and every internal app DB (plus roles) in one SQL dump. - Snapshots the object store volume into a tar archive.
- Bundles both into
astrodock-backup-<UTC-timestamp>.tar.gz.
You'll see progress lines like [backup] dumping all databases… and a final
[backup] wrote … with the tarball path.
Schedule it with cron
Backups are only useful if they run on their own. Add a cron entry on the host. For a nightly backup at 3:15 AM:
# crontab -e
15 3 * * * cd /path/to/astrodock && ./scripts/backup.sh /mnt/backups >> /var/log/astrodock-backup.log 2>&1
Use a full path
Cron runs with a bare environment, so cd into the repo first (as above) and use an
absolute output directory. Logging to a file lets you confirm it actually ran.
Prune old tarballs periodically so they don't fill the disk — keep, say, the last 7–30 days depending on how much room you have.
Copy backups off the box
The script can push each tarball to an external S3 bucket. Set BACKUP_S3_BUCKET in the
environment (with AWS credentials available via the environment or your awscli config),
and it uploads after writing the local copy:
BACKUP_S3_BUCKET=my-astrodock-backups ./scripts/backup.sh /mnt/backups
When the variable is unset, the upload step is skipped entirely and you just get the local tarball. Any S3-compatible store with working credentials works here.
The single-box caveat
Local backups protect you from data corruption and fat-fingering — but if the whole box dies, the
backups die with it. Always keep at least one copy off the box (the
BACKUP_S3_BUCKET upload, or your own rsync/copy to another machine).
This off-box copy is the one place an external dependency genuinely earns its keep.
Restore
Restore is a deliberate, manual process — there's no one-click button, and that's on purpose, so you don't overwrite live data by accident. The outline:
-
Get the tarball onto the host
Copy your chosen
astrodock-backup-<timestamp>.tar.gzto the server and unpack it. Inside you'll findall-databases.sqlandobjectdata.tar.tar -xzf astrodock-backup-20260530T031500Z.tar.gz -
Bring the stack up enough to restore into
Start at least the
postgresandobjectstoreservices so there's a target to restore into. On a fresh box, rundocker compose up -dwith a matching.envfirst. -
Restore the databases
Feed the SQL dump back into Postgres through the container.
pg_dumpalloutput recreates every database and role:docker compose exec -T postgres psql -U astrodock < all-databases.sql -
Restore the object store
Untar
objectdata.tarback into the object store's data directory (inside its container / volume), then restart that service so it re-reads its data. -
Restart and verify
Run
docker compose up -d, then check the apps and the Health page in the dashboard. Confirm a known app loads and its data is present.
Practice before you need it
Restore touches your live databases. Do a dry run on a spare box at least once so the steps are familiar — the worst time to learn the procedure is during a real outage.
Related
- Do this before every upgrade: Upgrading
- Get alerted when an app goes down: Email notifications
- Set up your install: Install & run