feat(workspace-client,desktop): relay WS outage telemetry + version-stamped desktop events
Merged
KI
3mo ago+359+359+012345678901234567890123456789-0-0-0123456789
Summary
- Add outage-episode telemetry to
createRelaySocket(the eventBus / workspace "disconnected" surface, previously silent):relay_ws_access_denied,relay_ws_degraded, andrelay_ws_recoveredPostHog events, at most one per outage plus one on recovery. - Register
app_versionas a PostHog super property in the desktop renderer so every event (including the existingterminal_connect_failed) is attributable to the build that emitted it.
Why / Context
Investigating the remote-workspace disconnect reports (relay 401 redial loop, fixed by #5628/#5637 but not yet released) hit two observability gaps:
terminal_connect_failedevents carry no app version — once 1.14.4 ships there's no way to segment pre/post-fix builds and confirm the 401 curve dies. The person-profiledesktop_versionreflects the current install, not the build at event time.- The eventBus relay socket that drives workspace "disconnected" state emits no telemetry at all, so access-denial episodes (the v2Hosts/v2UsersHosts class of failure) and outage durations are invisible in production.
How It Works
outageReporter.ts(co-located inrelaySocket/) is a pure state machine: callers feed it dial outcomes (attempt,accessDenied,failed,opened) and it collapses connection churn into episodes — oneaccess_denied(preflight 403) ordegraded(≥5 consecutive failed dials) event per episode, onerecoveredwithoutage_msand attempt count when the socket reconnects. partysocket'sretryCountonly resets after 5s of stable uptime, so flapping accumulates into one episode instead of spamming pairs.- The sink is process-wide (
setRelaySocketTelemetry), keeping@superset/workspace-clientanalytics-vendor-free; the desktop renderer wires it to PostHog ininitPostHog. Web consumers are unaffected (sink defaults to null). - Sockets carry a
namelabel (event-bus,web-terminal) so consumers are distinguishable in queries. The reported endpoint is the attempt URL minus its query string — the token never leaves the module.
Manual QA Checklist
- Desktop dev app: events carry
app_version(CDP-verified: super property registered,1.14.1in dev) - Outage cycle CDP-verified end-to-end: dead endpoint → one
relay_ws_degradedafter 5 failed dials → healed endpoint → onerelay_ws_recoveredwith saneoutage_ms; access-denied and terminal give-up paths verified too (see verification comment)
Testing
bun run typecheck(workspace-client, desktop, web)bun run lint(exits 0)bun testinpackages/workspace-client— 18 pass: new pure unit tests for the reporter policy (threshold boundary, once-per-episode dedup, silent short blips, episode reset on regrant, token stripping) plus WS integration tests proving the socket wiring end-to-end against a scriptable local relay- Mutation-verified: removing the
degradedemission and breaking the access-denied dedup each made exactly the expected test fail
Design Decisions
- Module-level sink instead of threading a callback through
RelaySocketOptions: everygetEventBuscall site would need plumbing for no gain; a process-wide analytics hook is the same shape posthog itself uses. - Once-per-episode emission instead of per-attempt: the eventBus 403 path re-probes every 5 minutes indefinitely — per-attempt events would flood; episode + recovery events preserve the debugging signal (cause, duration, attempt count) at bounded volume.
Known Limitations
terminal_connect_failedin the desktop terminal transport keeps its own capture path; it now gainsapp_versionvia the super property but doesn't use the outage reporter (it has its own max-attempts/give-up semantics). Unifying them is possible follow-up.
Summary by cubic
Adds relay WebSocket outage telemetry and version-stamped desktop analytics to improve visibility into remote workspace disconnects. Emits relay_ws_* events once per outage and records app_version on every desktop event; fixes attempt counting and filters synthetic closes for accurate stats.
- New Features
@superset/workspace-client: added outage reporter and process-wide telemetry sink (setRelaySocketTelemetry,RelaySocketTelemetryEvent).createRelaySocketnow reportsaccess_denied,degraded(≥5 failed dials), andrecoveredwithoutage_msand attempt count; tokens are stripped from endpoints. Hardened reporting: correct attempt ordinals, ignore partysocket synthetic closes, include last close info when errors cross the threshold, and guard the sink with try/catch.- Socket labeling: new
nameoption oncreateRelaySocket; event bus usesevent-bus, web terminal usesweb-terminal. - Desktop: PostHog sink forwards
relay_ws_${kind}events with endpoint, region, close info, and attempt counts. Registersapp_versionas a super property so all desktop events are attributed to the emitting build.
Summary by CodeRabbit
- New Features
- Added relay connection health telemetry for outages, access-denied episodes, and recovery, including endpoint context and outage duration.
- Desktop analytics now forward relay socket outage/recovery signals to PostHog and include the application version.
- Web terminal and event-bus relay connections now include identifiable connection labels for clearer attribution.
- Bug Fixes
- Improved reliability of relay outage telemetry emission, ensuring telemetry failures don’t affect socket behavior.
- Tests
- Expanded telemetry and outage episode coverage, including threshold crossing, recovery, access-denied semantics, and data privacy (no token leakage).