Skip to content
cronpad
Self-hosting / Production checklist

Production checklist

Go through this list before you rely on a self-hosted cronpad. Each item prevents a specific failure: lost data, duplicate scheduling, silent outages or leaked secrets.

Data

  • One cronpad process per data directory. Kubernetes: replicas: 1, strategy: Recreate. Two processes on one SQLite file can corrupt it. (A second process started by mistake waits in standby, because the dispatcher lock lives in the queue file, but don’t rely on it.)
  • Local or block storage, never NFS/SMB/EFS for the database and queue files. Keep the queue file (cronpad-queue.db) on the same volume, and leave it out of any backup or restore.
  • Backups in place. cronpad runs on plain SQLite unless you turn replication on, so pick one: Litestream (LITESTREAM_REPLICA_URL set) with a tested restore, or scheduled sqlite3 .backup of both databases, or volume snapshots.
  • secrets.encryption_key set from your secret manager, with a copy kept outside the server.
  • Retention set for your needs and disk size (Data retention).

Access

  • server.public_url is the real https:// URL, so cookies are Secure and OAuth callbacks work.
  • At least one OAuth provider configured; auth.dev_login is false.
  • You signed in first. On an empty server the first sign-in creates an account even with sign-up off, so sign in before exposing the server, or set auth.allowed_email_domains (First sign-in).
  • auth.allow_signup left false (the default), or, if you turned it on, auth.allowed_email_domains set to your organization’s domains.
  • Commands restricted with sinks.command.allowed_commands, or disabled if you don’t use them.
  • TLS terminated at your proxy or load balancer, with server.trusted_proxies set.

Operations

  • Liveness probe on /healthz, readiness probe and external uptime check on /readyz.
  • Stop timeout longer than server.shutdown_grace (default 30 s), so in-flight runs finish on deploy.
  • Metrics scraped or exported (Observability), with alerts on at least:
    • /readyz failing;
    • cronpad.queue.oldest_due_age above 30 s (work is waiting);
    • cronpad.leases.expired increasing (workers crashing or hanging);
    • SLA breach ratio above 1%.
  • Logs collected, in json for a log pipeline or logfmt for humans.
  • Alert email (SMTP) configured, so auto-disable notifications reach someone.

Expectations

  • A deploy or restart pauses scheduling for a few seconds. Runs due during it start late and are flagged as SLA breaches; none are lost.
  • Receivers should be idempotent (Delivery guarantees).