Public, anonymous backend for
network-dashboard.
One Fly app per env; no DB; no auth.
Streams a live view of the Moonlight network over WebSocket. Cold-start
self-syncs from council-platform's public endpoints and Soroban RPC; no
persistence.
Six event kinds drive the dashboard (see design sketch):
| Kind | Chain source |
|---|---|
council_formed |
Channel Auth contract_initialized event |
provider_added |
Channel Auth provider_added event |
provider_removed |
Channel Auth provider_removed event |
asset_registered |
New assetContractId appearing in council-platform/public/channels |
channel_deposit |
SAC transfer event TO a known channel address |
channel_settlement |
SAC transfer event FROM a known channel address |
| Path | Description |
|---|---|
GET /api/v1/health |
Liveness — {status,service,version} |
GET /api/v1/network/ws |
Public WebSocket. Subprotocol moonlight.network.v1. No auth. |
Server → client, JSON-encoded:
No client → server frames in v1. Clients reconnect rather than ping; on reconnect they receive a fresh snapshot.
council-platform /public/* ─┐
├─► in-memory state ─► WS clients
Soroban /getEvents (poll) ──┘ ▲
│
hourly re-sync + minute window sweep
- Cold start: fetch
council-platform/api/v1/public/councils(one call carries councils + channels + providers + jurisdictions), walk trailing 24h on every watched contract viarpc.getEvents, seed the rolling counter window + activity-feed ring buffer. - Forward poll: 5s cursor-based poll on the same contractId set.
- Hourly re-sync: refresh topology + re-anchor the rolling counter window.
- Minute sweep: drop window entries older than 24h.
cp .env.example .env
# Edit .env — set COUNCIL_PLATFORM_URL to your running council-platform.
deno task servelocal-dev/ notes: the canonical local-dev parallel-stack guide applies here.
Set PORT=<your-port> to avoid collisions with other services on the same host.
| Env | Required | Description |
|---|---|---|
PORT |
no (default 8080) | HTTP port |
MODE |
no (default development) |
development relaxes CORS to localhost |
LOG_LEVEL |
no (default INFO) |
FATAL/ERROR/WARN/INFO/DEBUG/TRACE |
NETWORK |
yes | testnet | mainnet | local |
STELLAR_RPC_URL |
yes | Soroban RPC URL |
COUNCIL_PLATFORM_URL |
yes | URL of council-platform (no trailing /api/v1) |
ALLOWED_ORIGINS |
recommended | Comma-separated CORS allowlist |
| Env | Fly app | Config |
|---|---|---|
| testnet | moonlight-beta-network-dashboard-platform |
fly.testnet.toml |
| mainnet | moonlight-mainnet-network-dashboard |
fly.mainnet.toml |
Tagged main pushes trigger .github/workflows/deploy-{testnet,mainnet}.yml.
deno.json version is the source of truth — bump it on every PR.