Skip to content

Back up and restore

The postgres_data Docker volume contains the Bearicorn database, including stored attachments. Back it up with PostgreSQL tools instead of copying a live volume directory.

Infrastructure snapshots are useful as a second layer, but a logical PostgreSQL archive is more portable and can be validated before an incident. PostgreSQL documents custom archives in pg_dump and the matching restore options in pg_restore.

INFO

This is a baseline for the current single-host stack, not a complete high-availability backup design. Set the schedule, retention, monitoring, and restore-test frequency for your recovery objectives.

Create a backup

Run from /opt/bearicorn/monorepo/deploy/compose. Set the Compose file used by your installation:

bash
export BEARICORN_COMPOSE_FILE=docker-compose.caddy.yml

docker compose --env-file .env -f "$BEARICORN_COMPOSE_FILE" exec -T postgres \
  sh -c 'pg_dump --username="$POSTGRES_USER" --dbname="$POSTGRES_DB" --format=custom' \
  > bearicorn-postgres.dump

Use docker-compose.yml for Direct HTTP or docker-compose.traefik.yml for Traefik.

The custom archive includes the database contents needed by the current stack. Confirm that the file is non-empty and readable:

bash
test -s bearicorn-postgres.dump
docker compose --env-file .env -f "$BEARICORN_COMPOSE_FILE" exec -T postgres \
  pg_restore --list < bearicorn-postgres.dump | head

Store it safely

A backup contains encrypted user content as well as service information such as accounts, membership, and timestamps. Move it off the Docker host, encrypt the destination, restrict access, and apply a retention policy.

Keep at least one copy in a separate failure domain. Periodically restore into a disposable environment; an untested backup is not a recovery plan.

Restore a backup

Destructive operation

The following procedure replaces the current database. Confirm the target host, preserve the current .env, and take a fresh backup before continuing.

Stop the application so it cannot write during restore:

bash
docker compose --env-file .env -f "$BEARICORN_COMPOSE_FILE" stop hub-app

Restore the archive through the PostgreSQL container:

bash
docker compose --env-file .env -f "$BEARICORN_COMPOSE_FILE" exec -T postgres \
  sh -c 'pg_restore --username="$POSTGRES_USER" --dbname=postgres --clean --if-exists --create' \
  < bearicorn-postgres.dump

Start the application and inspect it:

bash
docker compose --env-file .env -f "$BEARICORN_COMPOSE_FILE" start hub-app
docker compose --env-file .env -f "$BEARICORN_COMPOSE_FILE" ps
docker compose --env-file .env -f "$BEARICORN_COMPOSE_FILE" logs --tail=100 hub-app postgres

Verify login, room history, tasks, and at least one attachment before declaring recovery complete.

What a database backup does not include

  • the deployment repository and checked-out revision;
  • .env and its secrets;
  • reverse-proxy certificate state; or
  • host firewall, DNS, and cloud configuration.

Record those separately in a protected operator runbook. Never place secrets inside this documentation repository.

Self-hosted chat and tasks with end-to-end encrypted content.