Skip to content

Codex app-server: message(action=send) tool prematurely terminates turn — agent goes silent mid-task #100175

Description

@michaelrlee01-sys

Bug Summary

When a Codex-backed agent (e.g. GPT-5.5) calls the OpenClaw message(action=send) tool to deliver a progress update mid-turn, the Codex app-server treats the tool result as sufficient to release the turn. The agent announces intent, sends a progress message, and then goes completely silent — no further tool calls, no final response, no artifact written.

Reproduction

  1. Agent receives a task from user via Telegram
  2. Agent runs some bash commands (works fine)
  3. Agent calls message(action=send) to send a progress update to Telegram: {"ok": true, "messageId": "9805"}
  4. Turn ends. No further tool calls. No final response.
  5. User asks "Did you complete?" → same cycle repeats

Observed in transcript (stopReason: "toolUse" on the assistant message — the model wanted to continue, but the app-server ended the turn).

Environment

  • OpenClaw: 2026.7.1-beta.1 (4eb1d33)
  • Agent: Stark (gpt-5.5, Codex app-server, yolo mode)
  • Channel: Telegram
  • Config: turnCompletionIdleTimeoutMs: 60000 (default), postToolRawAssistantCompletionIdleTimeoutMs: 300000

Root Cause Analysis

In run-attempt (dist), the message tool is handled as a dynamic tool with a 120s timeout (CODEX_DYNAMIC_MESSAGE_TOOL_TIMEOUT_MS = 12e4). After the tool returns successfully:

  1. shouldBlockTerminalReleaseForNonTerminalDynamicToolResult(response) checks response.asyncStarted !== true
  2. For the message tool, the response is synchronous (ok: true, messageId: ...), so asyncStarted is not set
  3. This means shouldBlockTerminalReleaseForNonTerminalDynamicToolResult returns true → sets currentTurnHadNonTerminalDynamicToolResult = true
  4. But then shouldReleaseTurnAfterTerminalDynamicTool checks !state.currentTurnHadNonTerminalDynamicToolResult — which is now false
  5. The turn is released

The logic appears to be: synchronous dynamic tool results block the terminal-release shortcut, but the combination of currentTurnHadNonTerminalDynamicToolResult = true + no pending terminal dynamic tool + no active app-server turn requests results in the turn being released anyway via the idle watch.

The message tool should not be turn-terminal. It's a delivery mechanism, not a completion signal.

Proposed Fixes

1. Runtime fix (structural)

message(action=send) must never be turn-terminal unless the assistant has emitted a final response or an explicit terminal flag is set. The message tool is a delivery mechanism, not a completion signal. Consider either:

  • Treating message results as async for turn-completion purposes (so asyncStarted = true), or
  • Adding a turnTerminal: false flag to the message tool's response, or
  • Excluding message from the terminal-release check entirely

2. Integration test

Add a test: agent sends progress via message, then runs a bash command, writes an artifact, and sends a final message. The test should fail if the bash command or artifact never executes.

3. Stalled-turn watchdog

If a turn sends only a message tool call and then has no further tool activity or final response within 30-60s, mark it as stalled. Either auto-resume the turn or alert the user.

4. Delivery metadata distinction

Distinguish progress_message from final_delivery in OpenClaw tool metadata so Telegram delivery does not collapse the work loop. The message tool could accept an optional kind: "progress" | "final" parameter. Progress messages would be explicitly non-terminal; final messages could optionally be terminal.

Workaround Applied

  • Agent-side: Instructed agent via AGENTS.md to never send progress messages mid-turn — do all work first, then send only a final summary. This prevents the bug from triggering but limits agent communication.
  • Config-side: Bumped turnCompletionIdleTimeoutMs from 60s → 300s. This is a shot in the dark — if the app-server is explicitly treating message as terminal, the timeout bump doesn't help.

Impact

This affects all Codex-backed agents that use the message tool mid-turn for progress updates. Stark (gpt-5.5) has been consistently failing on multi-step tasks because of this. Other agents (Donna, Hermione, Jack) may be affected but haven't exhibited the pattern as clearly.

Metadata

Metadata

Assignees

No one assigned

    Labels

    P1High-priority user-facing bug, regression, or broken workflow.impact:message-lossChannel message delivery can be lost, duplicated, or misrouted.

    Type

    No type

    Fields

    Priority

    None yet

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions