()
| 1982 | // ask() call so messages that queued up during a long turn coalesce |
| 1983 | // into a single follow-up turn instead of N separate turns. |
| 1984 | const drainCommandQueue = async () => { |
| 1985 | while ((command = dequeue(isMainThread))) { |
| 1986 | if ( |
| 1987 | command.mode !== 'prompt' && |
| 1988 | command.mode !== 'orphaned-permission' && |
| 1989 | command.mode !== 'task-notification' |
| 1990 | ) { |
| 1991 | throw new Error( |
| 1992 | 'only prompt commands are supported in streaming mode', |
| 1993 | ) |
| 1994 | } |
| 1995 | |
| 1996 | // Non-prompt commands (task-notification, orphaned-permission) carry |
| 1997 | // side effects or orphanedPermission state, so they process singly. |
| 1998 | // Prompt commands greedily collect followers with matching workload. |
| 1999 | let batch: QueuedCommand[] = [command] |
| 2000 | if (command.mode === 'prompt') { |
| 2001 | while (canBatchWith(command, peek(isMainThread))) { |
| 2002 | batch.push(dequeue(isMainThread)!) |
| 2003 | } |
| 2004 | } |
| 2005 | const queuedAutonomyClaim = |
| 2006 | await claimConsumableQueuedAutonomyCommands(batch) |
| 2007 | batch = queuedAutonomyClaim.attachmentCommands |
| 2008 | if (batch.length === 0) { |
| 2009 | continue |
| 2010 | } |
| 2011 | command = batch[0]! |
| 2012 | if (command.mode === 'prompt' && batch.length > 1) { |
| 2013 | command = { |
| 2014 | ...command, |
| 2015 | value: joinPromptValues(batch.map(c => c.value)), |
| 2016 | uuid: batch.findLast(c => c.uuid)?.uuid ?? command.uuid, |
| 2017 | } |
| 2018 | } |
| 2019 | const batchUuids = batch.map(c => c.uuid).filter(u => u !== undefined) |
| 2020 | |
| 2021 | // QueryEngine will emit a replay for command.uuid (the last uuid in |
| 2022 | // the batch) via its messagesToAck path. Emit replays here for the |
| 2023 | // rest so consumers that track per-uuid delivery (clank's |
| 2024 | // asyncMessages footer, CCR) see an ack for every message they sent, |
| 2025 | // not just the one that survived the merge. |
| 2026 | if (options.replayUserMessages && batch.length > 1) { |
| 2027 | for (const c of batch) { |
| 2028 | if (c.uuid && c.uuid !== command.uuid) { |
| 2029 | output.enqueue({ |
| 2030 | type: 'user', |
| 2031 | content: c.value, |
| 2032 | message: { role: 'user', content: c.value } as unknown, |
| 2033 | session_id: getSessionId(), |
| 2034 | parent_tool_use_id: null, |
| 2035 | uuid: c.uuid as string, |
| 2036 | isReplay: true, |
| 2037 | } as unknown as StdoutMessage) |
| 2038 | } |
| 2039 | } |
| 2040 | } |
| 2041 |
no test coverage detected