跳到正文
DEV Community· Tomo·· 3 小時前AI 評分57

Supabase 備份與時間點復原(PITR):各方案內容、費用及 Free 方案還原演練

Supabase Backups and Point-in-Time Recovery: What Each Plan Includes, What It Costs, and a Restore Drill You Can Run on the Free Plan

AI 導讀

作者根據 2026-10-27 的資料與實測,整理 Supabase 各方案的備份內容及 PITR 費用,並在 Free 專案演練資料庫匯出、刪除與還原。Free 方案沒有自動備份;PITR 保留 7、14、28 日的費用分別約為 $100、$200、$400/月,並要求至少 Small compute,啟用後每日備份會停止。

正文

I wanted to know three things about Supabase backups: what I actually have on each plan, what PITR really costs, and whether I can restore. So I read the docs and the dashboard, then ran a restore drill on a Free project and built a small check page. Everything is from my run on 2026-10-27. Prices change, so every number is dated.

How this was made: I wrote this with Claude's help: it drafted, and I ran every step, edited the text, and checked the results. The mistakes are mine. This is a personal learning project, not an official guide, and I don't work for Supabase.

The non-technical version (three kinds of backup, worst case, drills): https://medium.com/p/f9c4c58ef3bd
The code: https://github.com/tomozilla/backup-drill-en-demo

What I did and did not do

  • Did: the drill on a Free project ($0): dump with the CLI, delete everything by accident, restore, count. I looked at a Pro project's backup pages read-only.
  • Did not: press Restore (it makes the project unavailable), enable PITR, use Restore to new project, or test Storage files, Auth users or role passwords.
  • Prices and conditions come from the docs and pricing page of 2026-10-27 (USD, no tax). I checked none of them against an invoice.
  • A correction. In my earlier article on plans I wrote that PITR costs $100 a month. The docs say more: see below.

Three kinds of backup

Three boxes: the nightly copy, rewind to a second ago (PITR), your own copy.

1. Daily backups

The docs say Pro, Team and Enterprise projects are backed up daily, with 7 days (Pro), 14 days (Team) and 30 days (Enterprise) kept. On a Free project the dashboard says:

The Backups page on a Free project: "Free Plan does not include project backups."

Free has no automatic backups. The docs recommend exporting regularly with the CLI db dump and keeping copies elsewhere.

On a Pro project (read-only):

The Backups page on a Pro project: one backup a day for 7 days, with a note that Storage objects are not included.

Note the banner: Storage objects are not included.

Two boxes: what is in the backup (the database) and what is not (uploaded files).

The docs add two cautions:

  • Passwords of custom roles are not stored, so after a restore you set them again.
  • The project is unavailable while a restore runs, and the larger the database, the longer.

2. Point-in-time recovery (PITR)

The Point in time tab: "Point in Time Recovery is available as an add-on".

From the docs:

  • It combines a daily snapshot with a continuous record of changes (WAL), archived every two minutes by default: worst case about two minutes of loss.
  • Price by retention: about $100 / month for 7 days, $200 for 14, $400 for 28.
  • Condition: the project needs at least the Small compute add-on. Micro is not enough. That is what I left out earlier: PITR is the $100 plus the step from Micro ($10) to Small ($15).
  • With PITR on, daily backups are no longer taken.

3. Your own copy

On Free, this is the main route. The drill below uses it.

The drill: take, break, restore, count

Four steps: take a copy, break things, restore, count.

A backup that has never been restored is a hope. So I practised, on a Free project, with fake orders in their own schema backup_demo.

Before

Result: 5 orders, total 1004.00.

Take

With the CLI logged in and linked (supabase login, supabase link):

supabase db dump --schema backup_demo -f backup/schema.sql
supabase db dump --schema backup_demo --data-only -f backup/data.sql

(scripts/backup.sh wraps both.) Two things I noticed:

  • I never typed a database password. The CLI made a temporary login role for itself.
  • The first attempt printed Direct connection ... is unavailable because this environment does not support IPv6. Retrying via the IPv4 connection pooler. and then worked. The direct database host is IPv6-only on this plan, and my machine has no IPv6, so the CLI fell back by itself.

data.sql is plain SQL:

INSERT INTO "backup_demo"."orders" ("id", "customer", "item", "amount_usd", "status", "created_at") OVERRIDING SYSTEM VALUE VALUES
    (1, 'Acme Demo', 'Starter kit', 49.00, 'paid', '2026-10-27 07:40:23.626218+00'),
    ... 5 rows ...

Break

I pretended to delete only the pending orders and forgot the WHERE: delete from backup_demo.orders;

Result: 0 orders, total 0.

Restore and count

I pasted data.sql into the SQL editor and ran it.

Result: 5 orders, total 1004.00, the same as before the accident.

Five rows and $1,004.00 again. Two lessons:

  • You are back to when the copy was taken. Anything written later is gone. How often you take copies decides how much you lose.
  • Replaying the file into a table that still has rows fails on duplicate ids. I restored into an empty table.

Restore to a new project (read-only look)

The Pro project has a Restore to new project (BETA) tab that restores a backup into a new project rather than overwriting the current one.

The Restore to new project tab: a list of available backups, each with a Restore button.

I did not press anything. It looks handy for checking a backup without touching production, but I haven't tried it.

The backup check page

I put the rules into a small page: you enter the facts of each project, and it shows the worst-case loss and what is missing. It never connects to a project.

The first screen: a paste box and a Load sample projects button.

Architecture: facts in, judgement, view, and a dated rules file.

Worst case: about 2 minutes with PITR, up to 24 hours with daily backups, and on Free the time since your last manual dump (or "everything" if there never was one). Problems and warnings include Free with no dump, PITR on a compute smaller than Small, no restore test on record, and Storage files with no separate copy.

python3 -m http.server 8000   # from the repository root, then open http://localhost:8000/app/
node app/test.js              # 18 checks

Five fictional projects: 2 problems, 1 warning, PITR add-ons $300 a month.

  • old-experiment (Free): no dump and files in Storage: problem, worst case "everything".
  • customer-portal (Pro + PITR, Micro): problem, because PITR needs at least Small.
  • billing-core (Team + PITR, Medium, tested, files backed up): OK, about 2 minutes.

The PITR add-ons total $300 a month ($100 for 7 days + $200 for 14 days). That excludes the compute upgrade.

Stumbles

"7 days old" tripped a 7-day limit

My first version warned that a dump taken 7 days earlier was "older than 7 days." The reason was the time of day: a date of 2026-10-20 compared with this afternoon is 7 days and a few hours. I now compare whole days. My tests used midnight timestamps, so they could not catch it. I only noticed when I ran the page.

Bad rows

A row with an unknown plan is skipped with a message, not dropped silently:

A warning: skipped 1 row, needs a name and a plan of free, pro or team.

Limits

  • You enter the facts, so stale input gives a stale verdict.
  • "I tested a restore" is a claim the page cannot check.
  • Not tested: dozens of projects, phone width, opening the page as a file.

What it costs

  • The drill and the page: $0 (Free project).
  • Daily backups: included in paid plans. PITR: about $100 / $200 / $400 a month for 7 / 14 / 28 days, plus at least the Small compute add-on.
  • Storing your own copies elsewhere may cost something. Nothing here was checked against an invoice.

If I took this further

Not tried: reading the list of backups through the Management API so the page fills in the last backup time itself (it needs an access token, which I didn't want to handle), recording the result of each restore test (rows and totals), and an alert when a check is overdue.

Cleanup

I dropped backup_demo (sql/99_cleanup.sql).

Takeaways

  • Three kinds: daily backups, PITR, your own copy. Free has only the last.
  • Storage files are not in database backups.
  • PITR needs Small compute or larger, and turns daily backups off.
  • Practise a restore and count the rows. "Having a backup" is not "restoring it".

Next in this series: logins and audit trails instead of shared passwords.

來源:DEV Community · dev.to