refactor(machine): drop VITE_LNBITS_HTTP_URL — lnurl now arrives populated from LNbits (#57 gap 2)

Closes gap 2 from coord log 2026-06-01T18:30Z. The LNbits withdraw
extension's nostr-transport RPC now populates `link.lnurl` from
`settings.lnbits_baseurl` (aiolabs/withdraw#1 / commit e9d911e), so the
ATM no longer needs a separate HTTP URL on the wire to compose the
LNURL-withdraw callback itself.

What goes:

- `VITE_LNBITS_HTTP_URL` env var (renderer + Electron main)
- `lnbitsHttpUrl` field on `LightningConfig`, `RuntimeConfig`, and the
  Window mirror in `src/types/electron.d.ts`
- The manual `${lnbitsHttpUrl}/withdraw/api/v1/lnurl/${unique_hash}`
  composition in `generateLnurlWithdraw`
- The `encodeLnurl` bech32 helper in `lightning.ts` (LNbits returns
  bech32-encoded; we just `.toUpperCase()` to match BOLT/LNURL convention)
- `@scure/base` dep from `apps/machine/package.json` (only used by the
  removed helper; clink still uses it directly)
- The `lnbitsHttpUrl` option + `LNBITS_HTTP_URL=…` env var + boot echo
  in `deploy/nixos/bitspire-atm.nix`
- Doc references in CLAUDE.md, README.md, deploy/nixos/README.md,
  docs/architecture-comparison.md, and the lightning-check skill

What stays:

- `link.lnurl` consumption, with an explicit error if LNbits returns
  null (which signals `LNBITS_BASEURL` is unset on the server side —
  better to fail clearly than silently)
- The receiver-side bech32 uppercasing (LNbits returns lowercase per
  the standard library)

Why this is a net win:

- Removes a config-drift surface — if LNbits's external URL moved
  (DNS, port, reverse-proxy rewrite), every ATM in the field would
  stop issuing redeemable LNURL-withdraw QRs until reconfigured.
  Now LNbits derives its own URL from `settings.lnbits_baseurl`,
  one source of truth.
- Removes an extra provisioning step. No more `LNBITS_HTTP_URL=…`
  before running `provision-atm.sh`; the relay + server pubkey suffice.
- Removes the misleading boot echo that triggered the §`18:30Z`
  smoke triage confusion ("LNbits HTTP: <url>" read like ATM-→-LNbits
  connectivity, when it was only ever a URL embedded in customer QRs).

Also adds a `# pragma: allowlist secret` marker above the
`VITE_ATM_PRIVATE_KEY` doc block in `.env.example` so the global
secret scanner stops false-positiving on the documentation prose.

Workspace typecheck + 24/24 apps/machine tests still green.

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
This commit is contained in:
Padreug 2026-06-01 20:33:28 +02:00
commit 4f68ddc40b
14 changed files with 63 additions and 91 deletions

View file

@ -153,7 +153,6 @@ Pull both USB sticks. Power Sintra back on. systemd-boot loads from the eMMC's E
LNBITS_SERVER_PUBKEY=$(docker logs <lnbits-container> 2>&1 | \
grep -oP 'Public key \(share this\):\s*\K[a-f0-9]{64}' | tail -1)
LNBITS_HTTP_URL=http://<dev-lan-ip>:5001 \
RELAY_URL=ws://<dev-lan-ip>:5001/nostrrelay/test \
LNBITS_SERVER_PUBKEY="$LNBITS_SERVER_PUBKEY" \
ATM_PRIVATE_KEY=$(openssl rand -hex 32) \
@ -166,7 +165,6 @@ bash deploy/nixos/provision-atm.sh <sintra-lan-ip> 22
set -a; source ~/sintra-backup-<date>/.env; set +a
ATM_PRIVATE_KEY=$VITE_ATM_PRIVATE_KEY \
LNBITS_SERVER_PUBKEY=$VITE_LNBITS_SERVER_PUBKEY \
LNBITS_HTTP_URL=$VITE_LNBITS_HTTP_URL \
RELAY_URL=$VITE_RELAY_URL \
bash deploy/nixos/provision-atm.sh <sintra-lan-ip> 22
```
@ -204,12 +202,12 @@ Production ATMs on `main` continue to read `main`'s flake (no `?ref=` pin → re
| Path | Owner | Purpose |
|------|-------|---------|
| `/var/lib/bitspire/` | bitspire:bitspire, 0750 | Service data directory |
| `/var/lib/bitspire/.env` | bitspire:bitspire, 0600 | Runtime config — `VITE_RELAY_URL`, `VITE_LNBITS_SERVER_PUBKEY`, `VITE_LNBITS_HTTP_URL`, `VITE_ATM_PRIVATE_KEY`, … |
| `/var/lib/bitspire/.env` | bitspire:bitspire, 0600 | Runtime config — `VITE_RELAY_URL`, `VITE_LNBITS_SERVER_PUBKEY`, `VITE_ATM_PRIVATE_KEY`, … |
| `/var/lib/bitspire/state.db` | bitspire:bitspire | SQLite — cassette inventory, cashbox state, transaction history |
| `/var/lib/bitspire/logs/` | bitspire:bitspire, 0750 | Service logs (if app writes them) |
| `/var/lib/bitspire/branding/` | bitspire:bitspire, 0755 | Operator branding override (logo.png + branding.json) — see issue #47 |
| `/opt/bitspire/` | bitspire:bitspire | Optional override drop for app assets (mostly unused — app comes from `/nix/store`) |
| `/etc/bitspire/config.env` | root:root | Static config emitted by the NixOS module (RELAY_URL, LNBITS_HTTP_URL — informational; the renderer reads `/var/lib/bitspire/.env` instead) |
| `/etc/bitspire/config.env` | root:root | Static config emitted by the NixOS module (RELAY_URL, LNBITS_SERVER_PUBKEY — informational; the renderer reads `/var/lib/bitspire/.env` instead) |
## Common operations
@ -266,7 +264,6 @@ ls -la /dev/serial/by-id/
enable = true;
relayUrl = "wss://relay.aiolabs.dev"; # ATM ↔ LNbits relay
lnbitsServerPubkey = "<64-hex>"; # LNbits transport pubkey
lnbitsHttpUrl = "https://lnbits.aiolabs.dev"; # LNURL callback URL prefix
appDir = "/opt/bitspire"; # rarely overridden — defaults via flake
dataDir = "/var/lib/bitspire"; # rarely overridden
logLevel = "info"; # error | warn | info | debug