docs(10): KEY-03 final scope — delete Core wallet path, harden LND PSBT

Core's wallet is outdated and used by nothing, so bitcoin.init-wallet-from-seed
is deleted outright rather than migrated: uncalled, authenticated and
password-gated, never ran on archi-dev-box, and its only job is deriving and
stringifying the master BIP-84 xprv.

D-07's parity-proof migration and its one-way checkpoint are withdrawn — there
is no wallet to migrate. A small discovery check folds into KEY-04; a wallet
found there is a finding to stop on, not an auto-migration trigger.

PSBT is already solved by LND and already implemented: lnd.create-psbt
(WalletKit FundPsbt) and lnd.finalize-psbt (finalize + broadcast), both
rate-limited, on LND v0.18.4-beta. KEY-03 becomes: delete the Core path and
make that flow first-class, tested and documented, including that the PSBT
carries the BIP-32 key-origin data a hardware signer needs.

Records the standing honesty constraint that Lightning channel/revocation/HTLC
keys are not air-gappable at all, and defers the BDK+ElectrumX cold vault to
its own phase (D-07c).

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
This commit is contained in:
archipelago
2026-08-01 06:43:22 -04:00
co-authored by Claude Opus 5
parent cb021a991c
commit 97b8fa485d
@@ -117,6 +117,48 @@ derivation paths, word counts, or the at-rest encryption envelope.
plan must say so plainly rather than implying a watch-only Core wallet delivers air-gapped
custody.
- **D-07b (final KEY-03 scope, supersedes D-07 and D-07a's conditional migration):** Core's
wallet is out entirely — it is outdated and used by nothing. **Delete
`bitcoin.init-wallet-from-seed`** (handler `bitcoin.rs:161-294` + its `dispatcher.rs:122`
registration): an uncalled, authenticated, password-gated endpoint whose only job is to derive
and stringify the master BIP-84 xprv. Pure liability, zero benefit. Deleted outright, not
deprecated — nothing in the repo or frontend calls it, no unattended caller can reach it
(password-gated), and archi-dev-box shows it never ran.
**No migration is planned.** D-07's parity-proof migration and its `one-way` checkpoint are
withdrawn — there is no wallet to migrate. If the KEY-03 discovery sweep unexpectedly finds a
descriptor wallet this handler created on some fleet node, that is a **finding to surface and
stop on**, not a trigger to auto-migrate: it would mean the endpoint was invoked manually and
the node's spending key is duplicated in Core, which deserves a human decision.
**PSBT is already solved by LND, not Core.** Verified in-repo:
- `lnd.create-psbt` (`api/rpc/lnd/wallet.rs:605`) → LND WalletKit `/v2/wallet/psbt/fund`;
its own doc comment says "Create an unsigned PSBT for hardware wallet signing".
- `lnd.finalize-psbt` (`:711`) takes `signed_psbt_base64``/v2/wallet/psbt/finalize`
broadcasts via `/v2/wallet/tx`.
- Both already rate-limited (`rate_limit.rs:68-69`, 5/300s). LND is pinned to **v0.18.4-beta**.
KEY-03 therefore becomes: **delete the Core path, and make the existing LND PSBT flow a
first-class, tested, documented path** — including an acceptance criterion that the PSBT
produced by `lnd.create-psbt` carries the BIP-32 derivation / key-origin data a hardware
signer needs to locate its key (this is what D-09 was really protecting; it no longer applies
to Core descriptors, which are being deleted).
**Reversibility:** reversible — deleting an uncalled endpoint is recoverable from git, and
the LND flow already exists. The `one-way` rating from D-07 no longer applies.
- **D-07c (deferred, not chosen now):** a true cold vault independent of both Core and LND —
BDK descriptor wallet in the daemon with the node's own **ElectrumX** app as chain source
(already shipped: `apps/electrumx`, `electrs_status.rs`). Considered and deliberately deferred
out of Phase 10; it needs its own phase (new dependency, new UI surface). Recorded so the
option is not lost. The alternative shape — LND watch-only via `importaccount` + remote
signing — was also considered and rejected for coupling cold storage to LND's upgrade path.
**Standing honesty constraint for any signing docs this phase touches:** on-chain funds held
by LND *are* air-gappable today via the create→sign-offline→finalize flow. Lightning channel,
revocation and HTLC keys are **not air-gappable at all** — they must sign in real time to
answer counterparty commitments. LND remote signing relocates those keys; it does not cool
them. No document produced by this phase may imply otherwise.
- **D-08:** Default signing stays **daemon-side PSBT signing** using the seed already held in
the encrypted envelope, with the air-gapped/external-signer path from
`docs/security/PSBT-SIGNING-ARCHITECTURE.md` available as **opt-in**. Send UX is unchanged;