← Back to Business Systems Specialist Collection
See how it helps
LLM provider adapters
Provides a consistent application-facing contract across LLM APIs while retaining the provider details needed for correct replay and accounting.
llm-provider-adapters
Team members using this skill
When is it useful?
Use it when adding a model provider or CLI backend without spreading vendor-specific behavior through the runtime.
What does it help you do?
- Normalizes content blocks, tools, stop reasons and token usage.
- Preserves provider-specific reasoning signatures and streaming semantics.
- Classifies retryable errors and cleans up wrapped CLI processes.
Try asking this
Add a provider without losing tool results or confusing token-limit stops with completion. Replay a tool call, a partial stream and a token-limit stop through both adapters. Preserve equivalent message identity and clearly mark incomplete output.
Detailed documentation
Read the skill’s original instructions, examples and checks in their authored language.
Show less
LLM Provider Adapters & Fallbacks
Isolate provider-specific wire formats, SDK quirks, and CLI flags behind a narrow, canonical internal interface so application workflows never depend on a single vendor's message schema or streaming protocol.
Canonical Internal Domain Model
Define a provider-neutral contract at the boundary of your LLM gateway:
- Canonical Message & Content Blocks: Represent turns as ordered blocks (
text,thinking/reasoningwith opaque cryptographicsignaturepreserved for multi-turn replay,tool_use,tool_result, andimage/documentattachments). - Canonical Tool Definition: JSON Schema
inputSchema, description, and behavioral hints (strict,defer_loading,cache_control) translated by each provider adapter into its native format. - Canonical Stop Reasons: Normalize provider stop reasons (
end_turn/stop,tool_use/tool_calls,max_tokens/length,content_filter/safety,pause_turn) so the runtime state machine handles every model uniformly. - Canonical Usage Ledger: Always normalize
inputTokens,outputTokens,cacheReadInputTokens,cacheCreationInputTokens, andreasoningTokensinto a singleTokenUsagestruct on every turn.
Provider-Specific Translation Pitfalls
Guard against subtle cross-provider incompatibilities inside the adapter layer:
| Area | Anthropic Claude | OpenAI Responses / Chat | Google Gemini | Adapter Requirement |
|---|---|---|---|---|
| System Prompt | Top-level system array of blocks with cache_control |
developer / system role items or instructions |
systemInstruction content object |
Keep system instructions separate from the messages array in the canonical request; let the adapter place them. |
| Tool Results | user message containing tool_result content blocks ordered before text |
Dedicated function_call_output / tool role items per call_id |
functionResponse parts grouped in a user/function turn |
Enforce strict 1-to-1 pairing between tool_use.id and tool_result.tool_use_id; coalesce adjacent tool results when a provider requires a single turn. |
| Thinking / Reasoning Blocks | thinking & redacted_thinking blocks with signature must be echoed unmodified during tool loops |
reasoning items with encrypted content or summary |
thought: true parts with thoughtSignature |
Store reasoning blocks verbatim in turn history; if switching providers mid-run, strip vendor-specific signatures and keep only plain-text summaries if permitted. |
| Strict JSON Schemas | Requires explicit "additionalProperties": false on objects |
Strict mode requires all properties in required (use nullable types for optional fields) |
Subset of OpenAPI/JSON Schema keywords supported | Run a schema normalizer per provider before sending tool or structured-output definitions. |
Resilient Retries, Circuit Breakers & Model Fallbacks
- Classify errors before retrying:
- Retryable transient: HTTP
408,429(respectRetry-After/x-ratelimit-reset-*headers),500,502,503,529(overloaded), or mid-stream socket reset before irreversible side effects. Use exponential backoff with full jitter. - Context window overflow (
400 context_length_exceeded): Do not blind-retry or switch to a smaller model. Trigger emergency context compaction or tool-output truncation and retry once. - Non-retryable client error (
400 invalid_request,401,403): Fail immediately with a structured diagnostic error; inspect schema translation bugs.
- Retryable transient: HTTP
- Safe cross-model fallback:
- Maintain an ordered fallback chain (
primaryModel$\rightarrow$fallbackModels) with capability tags (supportsTools,supportsVision,supportsStructuredOutput,maxContextTokens). - Only fall back to a model that satisfies all capabilities required by the current turn (e.g., never fall back to a model without tool support during an active tool loop).
- When switching providers mid-conversation, re-serialize the canonical transcript through the target provider's adapter so vendor-specific blocks (
thinkingsignatures, cache markers, tool ID formats matching^[a-zA-Z0-9_-]+$) are sanitized cleanly.
- Maintain an ordered fallback chain (
- CLI Agent Wrappers: When wrapping headless CLI agents (e.g., Claude Code, Codex CLI, Gemini CLI), communicate via structured JSONL streams (
--output-format stream-json), enforce process-group cleanup (kill(-pid)), isolate working directories, and parse exit codes and stderr into the same canonicalAgentRunResult.
Included files 1
SKILL.md
