Skip to content
Docs

Self-hosting

Backups and recovery

What to back up, what can be rebuilt, retention, and a recovery order. Operational guidance; the repository ships no backup tooling.

The repository does not include backup automation. This page says what holds irreplaceable data so you can protect it with your own tools.

What matters, in order

StoreContentsLoss meansBack up with
PostgreSQLConfiguration, the ledger, statements, invoices, payout runs, audit log, users, apps, fraud cases, conversion keys.Losing money records and configuration.Continuous WAL archiving with point-in-time recovery plus periodic base backups (for example pgBackRest or your cloud's managed PITR). This is the most important store.
ClickHouseClicks, conversions, events, installs, logs, aggregates.Losing reporting history.BACKUP ... TO S3(...) on a schedule, or replicas across zones. Raw tables are the source of truth for the aggregates.
S3 storageCreatives, invoices and statements PDFs, report exports, the data locker.Losing files; the locker can be regenerated.Bucket versioning and cross-region replication.
SecretsDT_SECRETS_KEY, SDK secrets, provider tokens.Sealed values in Postgres (payment methods, provider credentials, import credentials, connector credentials) become unreadable.Store DT_SECRETS_KEY in your secret manager and back it up separately from the database. Without it a restored database cannot decrypt its secrets.
NATS JetStreamIn-flight events.Events not yet written to ClickHouse or processed by workers.Persist the JetStream volume. Streams are at-least-once and consumers are idempotent, so a lost tail is the only exposure.
RedisCounters, dedupe keys, caches.Cap counters restart empty; caps fail open and a nightly job reconciles them from ClickHouse.Not required. Persistence is optional.

Rebuildable data

  • The edge and ingest config snapshot is rebuilt from Postgres; a new node is ready when it has loaded it.
  • ClickHouse aggregates (agg_hourly) are materialised views over the raw tables.
  • Cap counters reconcile nightly (DT_CAP_RECONCILE_HOUR).
  • Report exports, data-locker partitions and statements can be regenerated from the ledger and ClickHouse.

Retention

Raw event retention is a ClickHouse TTL decision you make per table; plan limits are visible in Settings, Plan & usage. Soft-deleted configuration is hidden, not erased, and every change is in the audit log. Device erasure (/v1/erase, POST /mobile/devices/{id}/forget) removes device-level data on request.

Recovery order

  1. Restore PostgreSQL to the target time and bring up api and workers read-only first if you want to inspect state.
  2. Restore DT_SECRETS_KEY and the S3 objects.
  3. Restore ClickHouse, or point reporting at the replica; re-apply scripts/ch-apply.sh to be sure schemas and views exist.
  4. Start NATS with its volume, then workers, then ingest and edge. Edges load their snapshot from Postgres (or Redis) when they start and refresh it as changes arrive.
  5. Replay anything lost between the restore point and the failure from the partners' or advertisers' own logs: conversion endpoints are idempotent on txn_id, so re-sending postbacks is safe (see deduplication).
  6. Run the reconciliation views: the caps reconciliation report and the ledger balances against statements.

Test your restore

A backup you have not restored is a hope. Restore Postgres into a scratch database, apply the migrations (they are idempotent), and run the reporting and ledger oracles (make reporting-oracle, make ledger-oracle) against it as a smoke test of the data.