mirror of
https://github.com/wu736139669/hapi.git
synced 2026-08-07 06:52:28 +00:00
fix(cli): buffer Pi prompts until RPC startup ready (#1146)
* fix(cli): buffer Pi prompts until RPC startup ready A prompt POSTed immediately after spawn (a supported handoff pattern used by hapi-ping-peer and intake scripts) could reach `pi --mode rpc` before its `new_session`/`get_state` startup finished, wedging the turn: `agent_start` then silence, no tool calls. The socket goes `active` (spawn success) well before Pi's session is initialized, so `active` is not a safe ready signal for Pi. Gate outbound prompt/steer sends behind a startup ready gate on PiSession: `runWhenReady()` delivers immediately once ready, else buffers FIFO; `markReady()` fires on the first `get_state` response (the signal that persists `metadata.piSessionId`, which working callers already wait for) and drains the buffer in order. A 30s unref'd fallback timer force-drains if `get_state` never lands, degrading to prior send-anyway behaviour rather than swallowing the message forever. Fixes #1143 Co-authored-by: Cursor <cursoragent@cursor.com> * fix(cli): honor cancel-queued-message for buffered Pi prompts Addresses the MAJOR review finding on the startup ready-buffer: while a prompt is held behind runWhenReady, the hub can send cancel-queued-message for its localId. Pi registered no onCancelQueuedMessage handler, so ApiSessionClient acked removed:false, the hub marked the row invoked, yet the buffered closure still drained on get_state and fired the cancelled prompt. Carry the localId with each buffered send and add PiSession.cancelBufferedMessage, then register apiSession.onCancelQueuedMessage so a cancel drops the still-buffered prompt (returns true) instead of sending it. Once drained to Pi it cannot be recalled — returns false, matching the other agents' queue.cancelByLocalId best-effort semantics. Co-authored-by: Cursor <cursoragent@cursor.com> --------- Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
@@ -154,6 +154,13 @@ function handleResponse(
|
||||
switch (command) {
|
||||
case 'get_state': {
|
||||
handleGetState(response.data, session);
|
||||
// Pi has finished startup init (this is the response that persists
|
||||
// metadata.piSessionId — the signal working callers already wait
|
||||
// for). Release any prompts buffered during the spawn window so they
|
||||
// reach an initialized Pi session instead of wedging (issue #1143).
|
||||
// markReady is idempotent; a missing sessionId still flips ready so
|
||||
// buffered prompts are never swallowed forever.
|
||||
session.markReady();
|
||||
break;
|
||||
}
|
||||
case 'set_model': {
|
||||
|
||||
Reference in New Issue
Block a user