I would correct the state first: the model proposed an action and later claimed success. Neither event is a tool receipt. If the request was sent and timed out, the effect is unknown. The runtime should preserve the proposal, authorization decision, exact submitted arguments, operation identity, send time, transport outcome, and any provider response as separate events. Its state is something like submitted, outcome_unknown, not succeeded and not automatically failed.

Why unknown? A timeout tells us our caller stopped waiting. It does not say whether the remote system accepted the request. There are several boundaries: before send, after bytes left our process, after provider acceptance, after effect commit, and after response was lost. The runtime can distinguish some of them from its own logs, but it cannot infer the remote commit point from a model sentence. A restart should replay the durable ledger, not ask the planner what happened.

If the tool is a read with no consequential side effect, another read may be safe after the deadline. If it can issue a credit, send a message, change permissions, or create a job, an automatic retry might duplicate it. Look for a documented idempotency contract using the same operation ID and arguments over a known retention window. If that contract exists and covers this specific timeout, a bounded retry can resolve the same logical operation. An idempotency key generated afresh on retry is not the same operation. Stripe's idempotency documentation is a concrete example whose key retention and saved error response need to be understood, not an assumption to copy onto every tool.

The probe removes the query API. If there is no status lookup and no reliable idempotency guarantee, I stop automated progress on the dependent branch. Mark the action as unresolved, alert an operator or request a human reconciliation from the external system's records, and tell the user what we know. We might have a transaction identifier in another audit channel, a recipient-side receipt, or a provider support route. If none exists, the product must accept that the outcome may remain unknown. It should not continue as if the action succeeded, nor repeat it to make the dashboard green.

This also constrains what the planner sees next. Feed it a structured result such as “submission timed out, outcome unknown, no retry authorized,” with the runtime blocking any dependent action until resolution. Don't let the planner's language turn uncertainty into a durable fact. If the user asks to try again as a new action, present the duplicate risk and use a separate explicit authorization when appropriate. The runtime still owns the effect gate.

A useful incident test pauses a fake tool just before and just after remote acceptance, drops its response, then kills the worker. After resume, the state must remain unknown at the ambiguous boundary and no second effect may be sent without the documented safe-retry condition or a new decision. That is the difference between a workflow that is recoverable and one that merely sounds confident.