Skip to content

ACP subagents terminate on repeated openai-subscription server overloads #35

Description

@walker-tx

Summary

ACP subagent runs against openai-subscription terminate on transient provider overload without an observable in-harness retry/recovery path. Two consecutive attempts at the same task failed; a third earlier run in the same work sequence failed with the same signature.

Environment

  • Kit: 0.1.96
  • OS: Darwin 25.6.0 arm64
  • Surface: acp
  • Provider route: openai-subscription
  • Invocation: subagent(...) launched inside compose(background=true)
  • No explicit harness/model override

Frequency and retry history

Three occurrences in one work sequence:

Attempt Session ID Event ID Approx. time to failure Outcome
Earlier task s-1787818223426-64387-40 e-1787818940141-22632-1 716.715 s Partial work occurred before termination and was recoverable
Same-task attempt 1 s-1787819654275-64387-44 e-1787819736385-47378-1 82.110 s Terminated; no diff/report preserved
Same-task attempt 2 s-1787819762526-64387-45 e-1787819912761-49411-1 150.235 s Terminated; no diff/report preserved

The latest two were consecutive fresh-session retries of the same task. Both failed, after which retries were stopped to avoid an unbounded loop. Their failure times were 2026-08-27T08:35:36.385Z and 2026-08-27T08:38:32.761Z.

Observed behavior

The parent receives:

tool execution failed: Internal error: loop error: provider error:
openai-subscription response failed:
service_unavailable_error/server_is_overloaded

The corresponding schema-v2 fatal records under ~/.kit/errors/<session>/<event>.json retain only:

{
  "surface": "acp",
  "kind": "provider",
  "code": "response_failed",
  "message": "openai-subscription failed (response_failed)"
}

The failed tool call does not return a reusable subagent value/handle. The parent therefore cannot distinguish a retry-safe pre-output failure from a failure after effectful tool calls without separately inspecting external state.

Expected behavior

For transient service_unavailable_error/server_is_overloaded, Kit should either:

  1. retry internally with bounded exponential backoff and jitter while exposing retry progress/count; or
  2. return a resumable subagent session or typed transient failure so the parent can retry safely without starting a new session.

After retry exhaustion, diagnostics should preserve the sanitized upstream classification, attempt count, cumulative backoff, and whether assistant output/tool activity had occurred.

Reproduction

  1. Configure ACP to use openai-subscription.
  2. Launch a nontrivial subagent through compose(background=true).
  3. Inject or encounter a response classified as service_unavailable_error/server_is_overloaded.
  4. Observe generic tool-call termination, no reusable session value, and a fatal record reduced to code=response_failed.
  5. Start the same task in a fresh subagent; under sustained overload it fails identically.

Suggested automated coverage

  • Fake provider overloads N times then succeeds: assert bounded backoff and one successful ACP result.
  • Provider always overloads: assert typed exhaustion includes upstream code, attempts, delay, and session/event IDs without provider body or secrets.
  • Overload after assistant output/tool activity: assert resumability or explicit possible-effects metadata.
  • Exercise both cases through compose(background=true) and verify structured completion/failure delivery.
  • Assert schema-v2 fatal JSON retains sanitized upstream classification and retry metadata.

No credentials, private prompts, provider payloads, or customer identifiers are included in this report.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions