mirror of
https://github.com/docker/docker-agent.git
synced 2026-11-06 15:07:58 +00:00
Addresses review feedback from rumpl and simonferquel on PR #2096. The previous approach extracted Retry-After metadata in a dispatcher function that type-switched on provider SDK error types (`*anthropic.Error`, `*openai.Error`). This kept all providers coupled to the modelerrors package and duplicated parsing logic. New design: 1. `modelerrors.StatusError` — a thin typed wrapper carrying: - StatusCode int - RetryAfter time.Duration (parsed from Retry-After header) - Err error (original SDK error, accessible via Unwrap) 2. `modelerrors.WrapHTTPError(statusCode, resp, err)` — wraps any provider error in StatusError; parses Retry-After from resp.Header if non-nil. 3. `modelerrors.ParseRetryAfterHeader(value)` — shared RFC 7231 §7.1.3 parser (integer seconds + HTTP-date). No SDK imports. 4. `modelerrors.ClassifyModelError(err)` — single-arg; uses errors.As to find *StatusError in the chain; falls back to message/pattern matching for providers not yet wrapped (e.g. Bedrock). 5. Three new wrap.go files (one per provider family), each a single function: - pkg/model/provider/anthropic/wrap.go — wrapAnthropicError(*anthropic.Error) - pkg/model/provider/oaistream/wrap.go — WrapOpenAIError(*openai.Error) (exported) - pkg/model/provider/gemini/wrap.go — wrapGeminiError(*genai.APIError) 6. Wrap sites — one-line change at Recv() in each adapter: - anthropic/adapter.go, beta_adapter.go - oaistream/adapter.go - openai/response_stream.go (reuses oaistream.WrapOpenAIError) - gemini/adapter.go No changes to fallback.go logic — ClassifyModelError signature stays `(err error)` and retry/rate-limit decisions are unchanged. Assisted-By: docker-agent