refactor(fe): trim >30-line comment blocks (second pass, #2077)
This commit is contained in:
parent
ccc69bbc7b
commit
95b866a53d
5 changed files with 55 additions and 118 deletions
|
|
@ -4,39 +4,26 @@
|
|||
// account and store its access token, without editing the agent's config
|
||||
// repo. Companion to the multi-account harness support.
|
||||
//
|
||||
// Backend contract (v2 — BE-4 adds live/user_id/as_of from the daemon snapshot):
|
||||
// Backend contract:
|
||||
// GET /api/matrix-accounts?agent=<name>
|
||||
// -> { accounts: [ { name, homeserver: string|null, token_present: bool,
|
||||
// live: bool, user_id: string|null } ],
|
||||
// -> { accounts: [{name, homeserver, token_present, live, user_id}],
|
||||
// as_of_unix: int|null }
|
||||
// POST /api/matrix-account-login (x-www-form-urlencoded, operator-auth)
|
||||
// POST /api/matrix-account-login (x-www-form-urlencoded)
|
||||
// fields: agent, account, homeserver, mode=password|token,
|
||||
// user_id?, password?, token?
|
||||
// -> 200 JSON { ok: true, user_id } on success
|
||||
// -> error body in transition: today a bare plain-text body
|
||||
// (hive-c0re's error_response), migrating to RFC 9457
|
||||
// application/problem+json { type, title, detail, … }. The error
|
||||
// path reads shape-agnostically (text first, then JSON `detail` if
|
||||
// it parses) so both shapes work regardless of BE/FE merge order.
|
||||
// The token is NEVER echoed back in any response, and this page never
|
||||
// re-renders a submitted secret.
|
||||
// -> 200 { ok: true, user_id }. Error body shape-agnostic: plain text
|
||||
// today, migrating to RFC 9457 problem+json { detail, … }.
|
||||
// Token is never echoed; page never re-renders a submitted secret.
|
||||
//
|
||||
// Live status dot (coordinated with the BE snapshot + heartbeat): the daemon
|
||||
// force-rewrites its host-visible snapshot every ~30s (heartbeat, BE), so
|
||||
// `as_of_unix` advances while the daemon is alive — a stalled `as_of` is now an
|
||||
// honest "daemon stopped publishing" signal, not just "snapshot is old". We
|
||||
// render —
|
||||
// green (live + running + fresh) = online
|
||||
// dim green (live but as_of stale > ~90s) = heartbeat stopped, likely dead
|
||||
// amber (live + container DOWN) = stale (container down ⟹ down)
|
||||
// amber (token_present + !live) = provisioned but offline
|
||||
// grey (no token) = not provisioned
|
||||
// The dim-green age case is meaningful only because of the heartbeat: 3 missed
|
||||
// ~30s beats (>90s) without the container being explicitly down means the
|
||||
// daemon is up-but-dead or wedged. The container cross-ref still takes
|
||||
// precedence (a stopped container is definitively stale regardless of age).
|
||||
// `as_of_unix` is tooltipped throughout so freshness is always legible. When
|
||||
// `live` is absent (v1 backend) the dot falls back to token-present rendering.
|
||||
// Live status dot — the daemon heartbeats every ~30s (advances as_of_unix),
|
||||
// so a stalled as_of = daemon dead, not just stale snapshot:
|
||||
// green live + running + fresh = online
|
||||
// dim green live but as_of stale > ~90s = heartbeat stopped
|
||||
// amber live + container DOWN = definitively stale
|
||||
// amber token_present + !live = provisioned but offline
|
||||
// grey no token = not provisioned
|
||||
// Container state takes precedence; as_of_unix is tooltipped for freshness.
|
||||
// v1 backend (no `live` field) falls back to token-present rendering.
|
||||
|
||||
import { $, el, esc, fmtAgeSecs, renderServerWarnings } from './common.js';
|
||||
|
||||
|
|
|
|||
|
|
@ -14,21 +14,12 @@
|
|||
// it reads — to union live containers with agents already named in the
|
||||
// assignments map.
|
||||
//
|
||||
// Editing model (the save-all issue): the operator toggles any number of
|
||||
// checkboxes across BOTH matrices, then clicks the single "save all (N)"
|
||||
// button. We diff each checkbox against the baseline captured at render
|
||||
// time (stored on `data-baseline`) and POST only the perm-types that
|
||||
// actually changed per agent to `POST /api/permissions`:
|
||||
//
|
||||
// { changes: [ { agent, tool_groups?, capabilities? } ] }
|
||||
//
|
||||
// Omitted field = leave that perm-type untouched (no commit, no diff);
|
||||
// an included array fully replaces that perm-type for that agent. The
|
||||
// backend coalesces caps+groups for one agent into ONE combined queue
|
||||
// entry → one rebuild per agent (no more double-rebuilds). The batch is
|
||||
// atomic: validated whole, applied whole, or rejected whole with
|
||||
// `{error}` — so the saved→rebuilding transition only fires on a clean
|
||||
// 200.
|
||||
// Editing model: checkboxes are diffed against a `data-baseline` captured at
|
||||
// render time; only changed perm-types per agent are POSTed to
|
||||
// `POST /api/permissions` as `{ changes: [{agent, tool_groups?, capabilities?}] }`.
|
||||
// Omitted field = leave untouched; included array = full replace. The backend
|
||||
// coalesces caps+groups per agent into ONE queue entry (one rebuild, no
|
||||
// double-rebuild). Batch is atomic — saved→rebuilding only fires on a clean 200.
|
||||
|
||||
import { $, el } from './common.js';
|
||||
import { containersState } from './state.js';
|
||||
|
|
|
|||
|
|
@ -9,32 +9,19 @@
|
|||
// { kind: 'unsubscribe', url: '/api/dashboard/stream' }
|
||||
//
|
||||
// worker → tab
|
||||
// { kind: 'open', url: '...' } relayed from EventSource.onopen,
|
||||
// plus a synthetic open fired to
|
||||
// a brand-new subscriber when the
|
||||
// upstream is already OPEN — so
|
||||
// the page's onStreamOpen still
|
||||
// runs and triggers a snapshot
|
||||
// re-sync after a reconnect gap.
|
||||
// { kind: 'open', url: '...' } relayed from EventSource.onopen; also
|
||||
// fired synthetically to new subscribers
|
||||
// when upstream is already OPEN (so
|
||||
// onStreamOpen runs + re-syncs state).
|
||||
// { kind: 'message', url: '...', data: '<raw SSE data string>' }
|
||||
// { kind: 'error', url: '...' } relayed from EventSource.onerror.
|
||||
// { kind: 'ping' } heartbeat — fired every
|
||||
// PING_INTERVAL_MS to every
|
||||
// connected port. The client's
|
||||
// watchdog uses these as
|
||||
// proof-of-life; silence past
|
||||
// ~3× the interval triggers a
|
||||
// re-subscribe on a fresh port
|
||||
// (recovers from Firefox killing
|
||||
// the SharedWorker out from
|
||||
// under us, which it does under
|
||||
// memory pressure with no native
|
||||
// signal to the client).
|
||||
// { kind: 'ping' } heartbeat every PING_INTERVAL_MS.
|
||||
// Silence past ~3× triggers a re-subscribe
|
||||
// (guards Firefox silently GCing the
|
||||
// SharedWorker under memory pressure).
|
||||
//
|
||||
// Subscriptions are tracked per (port, url): a single port can
|
||||
// subscribe to multiple URLs (only one is in use today).
|
||||
// Unsubscribing the last port for a URL closes the EventSource so we
|
||||
// don't keep idle streams open.
|
||||
// Per (port, url) subscriptions; unsubscribing the last port for a URL closes
|
||||
// the EventSource. One URL in use today; design allows multiple.
|
||||
|
||||
const streams = new Map();
|
||||
// All currently-connected ports. Used by the heartbeat tick to fan
|
||||
|
|
|
|||
Loading…
Reference in a new issue