The browser path (no electronAPI) is already a first-class code path: initializeWithLightning() resolves an EPHEMERAL LocalSigner, allows mock fallback and leaves debugMode on, so the bill simulator stands in for the validator. That is what makes a hosted kiosk demo possible at all. Two things still needed fixing for it. 1. Cursor. `cursor: none` was applied globally for the touchscreen, which in an ordinary browser reads as a broken page. Scope it to `.kiosk`, set on <html> by main.ts unless VITE_DEMO_TAG is present — so every real machine keeps today's behavior and only the demo build shows a pointer. 2. Cleanup. An ephemeral identity per page load is the right call (it isolates concurrent visitors, and each fresh account gets its own auto-credit under LNBITS_DEMO_MODE, whereas a single baked-in key would be credited once and then drain). The cost is a throwaway LNbits account per visit, and nothing in an auto-created row distinguishes one: pubkey-set/prvkey-NULL equally describes a real ATM. A nostr pubkey can't carry a marker — grinding a vanity prefix is far too slow to do on page load — and the account/wallet the server auto-creates isn't nameable by the client. So when VITE_DEMO_TAG is set the ATM mints one extra, never-used wallet whose NAME is the tag, turning the sweep into an exact string match instead of a heuristic about what looks disposable. Both are inert on a real machine: the var is unset outside the demo build. The marker call is fire-and-forget — losing it degrades cleanup, not the demo. Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_013A6683cCHnQxFUosx1krY4
95 lines
4.3 KiB
Bash
95 lines
4.3 KiB
Bash
# bitSpire ATM Configuration
|
|
# Copy this file to .env and fill in your values
|
|
|
|
# =============================================================================
|
|
# Hardware Configuration
|
|
# =============================================================================
|
|
|
|
# Machine model preset (sintra, gaia, or custom)
|
|
VITE_LAMASSU_MACHINE_MODEL=sintra
|
|
|
|
# Fiat currency code (ISO 4217)
|
|
VITE_LAMASSU_FIAT_CODE=USD
|
|
|
|
# Custom device paths (optional - uses preset defaults if not set)
|
|
# VITE_LAMASSU_VALIDATOR_DEVICE=/dev/ttyJ5
|
|
# VITE_LAMASSU_DISPENSER_DEVICE=/dev/ttyJ7
|
|
|
|
# Cassette configuration (optional - JSON array)
|
|
# VITE_LAMASSU_CASSETTES='[{"denomination":20,"count":100}]'
|
|
|
|
# =============================================================================
|
|
# LNbits Connection (dev override — normally seed-provided) — nostr-native-transport
|
|
# =============================================================================
|
|
# On a real machine the pairing SEED (VITE_SPIRE_SEED) carries the relay AND the
|
|
# server pubkey (aiolabs/bitspire#70), so leave both blank there. Set them here
|
|
# only for browser dev without a seed/bunker — they WIN over the seed.
|
|
|
|
# Nostr relay WebSocket URL. Dev stack uses LNbits's bundled nostrrelay:
|
|
# VITE_RELAY_URL=ws://localhost:5001/nostrrelay/test
|
|
VITE_RELAY_URL=
|
|
|
|
# LNbits nostr-transport server pubkey (hex, 64 chars).
|
|
# Printed by the LNbits server on startup:
|
|
# docker logs lnbits | grep 'nostr_transport pubkey'
|
|
VITE_LNBITS_SERVER_PUBKEY=
|
|
|
|
# (LNbits HTTP URL is no longer needed on the ATM side — the
|
|
# nostr-transport RPC `lnurlw_create_link` now returns `link.lnurl`
|
|
# populated from `settings.lnbits_baseurl` on the LNbits server. See
|
|
# aiolabs/withdraw#1 / commit e9d911e.)
|
|
|
|
# =============================================================================
|
|
# ATM Identity — spire pairing seed (NIP-46 bunker; aiolabs/bitspire#52)
|
|
# =============================================================================
|
|
|
|
# The spire pairing seed produced by the operator dashboard (spirekeeper):
|
|
# spire-seed:v1:<base64url>
|
|
# It carries a one-shot NIP-46 connect token + the spire's signing pubkey +
|
|
# the bunker URL. On first boot the ATM redeems the token, generates its own
|
|
# transport key, and persists the binding to state.db; thereafter it resumes
|
|
# from the binding (the seed can stay set — it's matched by fingerprint).
|
|
# A changed seed re-pairs (and re-publishes the cassette-state hello).
|
|
VITE_SPIRE_SEED=
|
|
|
|
# pragma: allowlist secret
|
|
# DEV ONLY fallback — a raw Nostr private key (hex, 64 chars) for running
|
|
# without a bunker. Ignored when VITE_SPIRE_SEED or a stored binding exists.
|
|
# Generate with: openssl rand -hex 32
|
|
# VITE_ATM_PRIVATE_KEY=
|
|
|
|
# =============================================================================
|
|
# Operator Identity
|
|
# =============================================================================
|
|
|
|
# Comma-separated list of Nostr hex pubkeys authorized to send operator commands
|
|
# (manual dispense, remote management).
|
|
# VITE_OPERATOR_PUBKEYS=abcd1234...,ef567890...
|
|
|
|
# =============================================================================
|
|
# Maintenance Mode
|
|
# =============================================================================
|
|
|
|
# Show "Under Service" screen and block all transactions
|
|
# VITE_MAINTENANCE_MODE=true
|
|
|
|
# =============================================================================
|
|
# Public Web Demo
|
|
# =============================================================================
|
|
|
|
# Set ONLY for the browser demo build (atm.demo.aiolabs.dev). Leave blank on
|
|
# every real machine. When set it:
|
|
# - keeps the mouse cursor visible (kiosk builds hide it)
|
|
# - mints one extra, never-used LNbits wallet named with this exact string,
|
|
# so the throwaway accounts the demo creates (one per page load, each with
|
|
# its own ephemeral identity) can be swept by name instead of guessed at.
|
|
# VITE_DEMO_TAG=bitspire-web-demo
|
|
|
|
# =============================================================================
|
|
# Mock Fallback (Production Safety)
|
|
# =============================================================================
|
|
|
|
# Allow fallback to mock services when hardware/Lightning fails (default: false)
|
|
# Set to 'true' for development/demo environments only
|
|
# When false (production default), initialization failures show a maintenance screen
|
|
# VITE_ALLOW_MOCK_FALLBACK=true
|