Public: anyone can read this; the crew can change it.

The Backups page opens with one line: "Recoverable now", or the first thing that stands in the way #2153

Merged opened this

Check · Review · Land · Live done — Landed and live in production.

Merged

/settings/backups now opens with one line: "Recoverable now" with a check icon, or "Not recoverable now: …" with an alert icon and the first fact that fails.

shipped production is serving it deploy 97ab7b8

opened this

/settings/backups now opens with one line: "Recoverable now" with a check icon, or "Not recoverable now: …" with an alert icon and the first fact that fails.

What changed

  • The line is built from four facts, checked in this order:

1. The store answers. 2. The newest snapshot is under 26 h old. 3. That snapshot carries a wrapped key. 4. The last drill is green and under 8 days old.

  • Example sentences: "the newest snapshot is 3 days old", "no restore drill has run yet", "the last restore drill is 9 days old".
  • A forge with no store shows "Not recoverable now: no snapshot store is set".
  • The line adds no request. It uses the snapshot listing and drill row the page already reads, and the sentence is escaped by the page's html template.
  • src/web/pages/backups.ts has the new pure recoverySentence().
  • test/snapshot-drill-page.test.ts has the all-good case and one case per failing fact, each asserting the exact sentence. It also has a page test for the no-store sentence.

Choices and omissions

  • A snapshot that carries the key unwrapped (older ones) counts as "does not carry a wrapped key", because the page already tells the owner to take a new one.
  • "Reachable" means the page's listing succeeded. I added no probe of the store.
  • The mirror is not part of the line. The issue named four facts.

Testing

  • bun test on the test/snapshot* files passes except two failures in test/snapshot-destination.test.ts. Both fail the same way without my change: the connection test needs a loopback connection the sandbox blocks, and I didn't look into the second.
  • bun x tsc --noEmit couldn't run here because the sandbox has no type definitions for bun, so the type check is left to the forge's check.

Try it: sign in as an admin and open /settings/backups.

🤖 Generated with Claude Code

Closes #2146

commented

/settings/backups now opens with one line: "Recoverable now" with a check icon, or "Not recoverable now: …" with an alert icon and the first fact that fails.

What changed

  • The line is built from four facts, checked in this order:

1. The store answers. 2. The newest snapshot is under 26 h old. 3. That snapshot carries a wrapped key. 4. The last drill is green and under 8 days old.

  • Example sentences: "the newest snapshot is 3 days old", "no restore drill has run yet", "the last restore drill is 9 days old".
  • A forge with no store shows "Not recoverable now: no snapshot store is set".
  • The line adds no request. It uses the snapshot listing and drill row the page already reads, and the sentence is escaped by the page's html template.
  • src/web/pages/backups.ts has the new pure recoverySentence(). Its optional Recovery fields now accept undefined explicitly, which fixes the type error the check reported (exactOptionalPropertyTypes).
  • test/snapshot-drill-page.test.ts has the all-good case and one case per failing fact, each asserting the exact sentence. It also has a page test for the no-store sentence.

Choices and omissions

  • A snapshot that carries the key unwrapped (older ones) counts as "does not carry a wrapped key", because the page already tells the owner to take a new one.
  • "Reachable" means the page's listing succeeded. I added no probe of the store.
  • The mirror is not part of the line. The issue named four facts.

Testing

  • bun x tsc --noEmit is clean after bun install, and test/snapshot-drill-page.test.ts passes (11 tests).
  • Earlier, the wider test/snapshot* run had two failures in test/snapshot-destination.test.ts. They fail the same way without my change, because the sandbox blocks a loopback connection. I didn't run that suite again this round.

Try it: sign in as an admin and open /settings/backups.

🤖 Generated with Claude Code

Approved

The Backups page now opens with one plain line, "Recoverable now" or "Not recoverable now: <first failing fact>". It reads the listing and drill row the page already loads, so it adds no request. The sentence is escaped by the page template, and the page is still admin-gated. The README already says the terminal has no backups view, so there is no second door to match. The tests pin each sentence. I did not open the preview, because the page needs an admin sign-in and I had none. I judged it from the diff only.

Two things I would do next:

  1. Add a sentence to the README's Backups section saying what the opening line means and which four facts it checks, with the 26 h and 8 day limits.
  2. Move the mid-file import in test/snapshot-drill-page.test.ts to the top with the other imports. Also pass the listing error text through, or log it, so that "could not be listed" tells the owner something.
Sign in to join this conversation.

↑↓ navigate ↵ open ⌘↵ its app esc close

Keyboard shortcuts

Docs