diff --git a/apps/cli/src/daemon/ws-lifecycle.ts b/apps/cli/src/daemon/ws-lifecycle.ts index 7a96e40..9522eca 100644 --- a/apps/cli/src/daemon/ws-lifecycle.ts +++ b/apps/cli/src/daemon/ws-lifecycle.ts @@ -143,23 +143,27 @@ export function connectWsWithBackoff(opts: WsLifecycleOptions): Promise((resolve, reject) => { sock.on("open", () => { + log("info", "ws_open_ok", { url: opts.url }); // Build and send the hello inside a microtask so any sync // throws from buildHello() reject this connect attempt cleanly. (async () => { try { const hello = await opts.buildHello(); sock.send(JSON.stringify(hello)); + log("info", "ws_hello_sent", { url: opts.url }); helloTimer = setTimeout(() => { log("warn", "hello_ack_timeout", { url: opts.url }); try { sock.close(); } catch { /* ignore */ } reject(new Error("hello_ack_timeout")); }, helloAckTimeoutMs); } catch (e) { + log("warn", "ws_build_hello_threw", { err: String(e) }); reject(e instanceof Error ? e : new Error(String(e))); } })(); @@ -174,9 +178,8 @@ export function connectWsWithBackoff(opts: WsLifecycleOptions): Promise { if (helloTimer) { clearTimeout(helloTimer); helloTimer = null; } const reasonStr = reason.toString("utf8"); + log("warn", "ws_closed", { url: opts.url, code, reason: reasonStr, status }); opts.onBeforeReconnect?.(code, reasonStr); if (closed) { @@ -200,8 +204,6 @@ export function connectWsWithBackoff(opts: WsLifecycleOptions): Promise openOnce().catch((err) => log("warn", "ws_reconnect_failed", { url: opts.url, err: String(err) })), wait, ); - // First attempt failure (still in connecting) also rejects the - // initial connect promise so callers can surface it. if (status === "connecting" || status === "reconnecting") { reject(new Error(`closed_before_hello_${code}`)); }