Skip to content
Rowsafe
Docs

How Rowsafe works

The agent on your server, the hosted service, and your own storage bucket, and what each of them can and can't do.

Rowsafe has three parts. Only one of them runs on your server.

PartRuns onWhat it does
Agent (rowsafe-agent)your database server, or next to your database containerRuns backups, checks and restore drills. Reports status and metrics. Open source.
Rowsafe serviceour servers (api.rowsafe.sh, dashboard at app.rowsafe.sh)Schedules work, keeps the history, evaluates alerts, serves the dashboard, the API and the CLI.
Your bucketyour S3-compatible storage (for example Cloudflare R2)Holds the encrypted backups and the continuous change log.

You talk to Rowsafe through the dashboard, the rowsafe CLI, the API, or AI assistants over MCP.

The agent asks for work

The agent only makes outbound HTTPS requests to the Rowsafe service. Nothing on your server listens for Rowsafe, and you don't open any port.

  • Every 30 seconds it sends a heartbeat with its status.
  • Every 5 seconds, when idle, it asks for a task.
  • Every minute it sends database and server metrics.

It runs only a fixed set of tasks. The service can't send it anything else, and it never runs commands or SQL sent over the network.

TaskWhat it does
inspectReads the database's version, settings and sizes.
adoptPlans the changes backups need (read-only), or applies them.
checkProves that changes reach your bucket.
backupTakes a full, differential or incremental backup.
drillRestores the latest backup on a scratch copy and checks it.
restore_pointCreates a named point you can restore to.

The agent runs one task at a time. Restore points have their own fast lane, so they never wait behind a long backup.

Your data and secrets stay with you

  • Backups are encrypted on your server before they are uploaded, with a passphrase only you have.
  • The bucket keys and the passphrase live only on your server, in files that only the database's system user can read.
  • The Rowsafe service never sees your data, your bucket or your passphrase. It stores metadata: server and database names, sizes, settings, task logs and metrics.

Read the security model for what Rowsafe can and can't do.

The life of a database

When you add a database, it moves through four states:

 rowsafe adopt        rowsafe apply              you restart,
      |              (restart needed)            rowsafe verify
      v                     |                          |
 pending_adopt ------------+--> awaiting_restart ------+--> verifying --> active
StateMeaningBackups scheduled
pending_adoptRegistered. Only read-only plans have run.No
awaiting_restartSettings applied. The database needs a restart before archiving starts.No
verifyingRowsafe is proving that changes reach your bucket. If the check fails, fix the cause and run rowsafe verify again.No
activeArchiving is proven. Backups and drills run on schedule.Yes

If applying the plan needs no restart, Rowsafe goes straight to verifying.

Schedules

Each database has three schedules, in UTC, written as 5-field cron expressions:

ScheduleDefault
Full backup0 1 * * 0Sundays at 01:00
Differential backup0 1 * * 1-6Monday to Saturday at 01:00
Restore drill15 21 * * 0Sundays at 21:15
  • Schedules start when a database becomes active. Missed runs are not replayed as a backlog.
  • If the previous run is still going, the next one is skipped.
  • A schedule may run at most once an hour.
  • Change them with rowsafe db set or in the database's settings in the dashboard.

If the service is down

Your database keeps archiving its changes to your bucket by itself, so point-in-time recovery keeps working. Only scheduled backups, drills and alerts pause until the service is back.

PostgreSQL details

How backups and archiving work on PostgreSQL, with pgBackRest: How PostgreSQL backups work.

Edit on GitHub