Files
hermes-agent/apps
Axl Ibiza, MBA d0ea5f1722 fix(desktop): surface Nous Cloud 503 at the OAuth ticket-mint boundary
The original implementation classified 502/503/504 only inside the readiness
loop, but for OAuth-backed Cloud connections the WebSocket-ticket mint runs
before waitForHermesReady. A server fault there was wrapped by
gatewayTicketFailure into a generic message and the Cloud-down classifier was
never reached. This closes that boundary and fixes a latent regex defect.

- isServerSideHttpError: structured-first (err.statusCode for 502/503/504),
  legacy 'NNN:' prefix as fallback, non-Error inputs rejected. Also fixes the
  committed '\d' (double-escaped, matched a literal backslash) that made the
  function never detect a status prefix.
- makeNousCloudBackendDownError: single factory for the actionable Cloud-down
  error (isCloudBackendDown/statusCode/detail/cause), shared by both the
  ticket-mint boundary and readiness exhaustion.
- main.ts: run the Cloud classifier at mintGatewayWsTicket before the
  gatewayTicketFailure wrap; 401/403 still route to reauth.
- connection-config.ts: gatewayTicketFailure preserves an integer statusCode
  from the source error; auth semantics unchanged.
- boot-progress/IPC: carry isCloudBackendDown and statusCode through
  DesktopBootProgress so the renderer overlay (a PR-body promise) can key on
  the structured result rather than re-classifying the message string.

Tests: backend-health (structured detection, non-Error rejection, factory
shape/cause/guards, legacy fallback), connection-config (statusCode preserve,
401/403 reauth, integer-only copy), and an OAuth ticket-mint integration
regression (Cloud 503 -> actionable Cloud-down; 401 -> reauth). Connection-
config suite 80/80 green; backend-health sync tests green; the async readiness
loop tests cannot run on this host (pre-existing local-run limitation) and are
the CI gate. PR #85373 (#85335).
2026-08-21 19:09:40 -07:00
..