Context
Identified during review of #44188 (unified fallback retry safety). The embedded runner path (attempt.ts) has orphaned-user-message repair that prevents duplicate user turns on fallback retries, but the CLI runner path (cli-runner.ts) does not.
When a CLI provider retry happens with an existing cliSessionId (resume mode) after a rate limit or timeout, the same prompt is appended again to the backend session. This is pre-existing behavior — not introduced by #44188 — but worth addressing.
Expected behavior
CLI runner fallback retries against resumed sessions should not produce duplicate user turns.
Possible approach
Port the orphaned-user-message repair pattern from the embedded runner (attempt.ts) to the CLI runner path, or detect and skip re-submission when the prompt already exists as the last user turn in the CLI session.
References
Context
Identified during review of #44188 (unified fallback retry safety). The embedded runner path (
attempt.ts) has orphaned-user-message repair that prevents duplicate user turns on fallback retries, but the CLI runner path (cli-runner.ts) does not.When a CLI provider retry happens with an existing
cliSessionId(resume mode) after a rate limit or timeout, the same prompt is appended again to the backend session. This is pre-existing behavior — not introduced by #44188 — but worth addressing.Expected behavior
CLI runner fallback retries against resumed sessions should not produce duplicate user turns.
Possible approach
Port the orphaned-user-message repair pattern from the embedded runner (
attempt.ts) to the CLI runner path, or detect and skip re-submission when the prompt already exists as the last user turn in the CLI session.References
runWithModelFallbackcall sites missing cross-provider guards