llm-seam
Unified LLM abstraction with a provider pattern — one interface, five backends, automatic fallback and retry.
Note on the name: this package was llm-base until 2026-08-21. It was
renamed to llm-seam because the PyPI name llm-base belongs to an
unrelated, older project — no relation to this package.
What's in the box
| Module | What it gives you |
|---|---|
llm_seam.client |
LLMClient — auto-selects a provider from the environment (Anthropic, then OpenAI, then a mock fallback), or accepts an explicit provider name/instance |
llm_seam.providers.base |
LLMProvider — the Protocol every provider implements (complete, get_name, supports_streaming) |
llm_seam.providers.anthropic |
AnthropicProvider — wraps the anthropic SDK |
llm_seam.providers.openai |
OpenAIProvider — wraps the openai SDK |
llm_seam.providers.claude_cli |
ClaudeCLIProvider — shells out to the Claude Code CLI |
llm_seam.providers.agent_sdk |
AgentSDKProvider — wraps claude-agent-sdk (requires the [sdk] extra); supports an optional can_use_tool security callback (see below); large system prompts are passed via a temp file, not argv |
llm_seam.providers.ollama |
OllamaProvider — local models via Ollama's OpenAI-compatible API (uses the openai SDK, no extra required) |
llm_seam.providers.mock |
MockProvider — fixed-response provider for tests and offline use |
llm_seam.fallback |
FallbackChain — tries a list of providers in order, raises AllProvidersFailed only if every one of them fails |
llm_seam.retry |
with_retry — decorator with exponential backoff, retries on RateLimitError by default (configurable) |
llm_seam.tool_guards |
path_scoped_tool_guard — ready-made can_use_tool callback for AgentSDKProvider; confines a tool's path arguments to an allowlist of directories, resists .. traversal, symlink escapes, and absolute paths outside the allowlist |
llm_seam.exceptions |
LLMError (base), RateLimitError, TokenLimitError, TimeoutError, AllProvidersFailed |
Design
One interface, provider-agnostic callers. LLMClient and every provider
implement the same three-method LLMProvider protocol (complete,
get_name, supports_streaming), so a caller can swap Anthropic for a local
Ollama model, the Claude CLI, or a mock in tests without touching call sites.
Auto-selection is a convenience, not a requirement. LLMClient() with no
arguments picks Anthropic if ANTHROPIC_API_KEY is set, else OpenAI if
OPENAI_API_KEY is set, else falls back to MockProvider. Pass an explicit
provider= name or instance to bypass auto-selection entirely.
Provider-name convention. When constructing by name string, this
portfolio distinguishes two Claude transports: "claude-sdk" selects
AgentSDKProvider (the claude-agent-sdk package, preferred for new
scheduled work — see libs/CLAUDE.md), and "claude-cli" selects
ClaudeCLIProvider (shells out to the installed Claude Code CLI). "claude-sdk"
is only registered as a valid name if claude-agent-sdk is installed (the
[sdk] extra); otherwise constructing by that name raises ValueError.
AgentSDKProvider's can_use_tool is a security boundary, not a hygiene
knob. It threads straight to ClaudeAgentOptions.can_use_tool. If a caller
passes a callback and the installed claude-agent-sdk can't accept the
field, the call raises LLMError rather than silently proceeding ungated —
a caller that believes tool calls are being permission-checked must never
find out otherwise the hard way. Use
tool_guards.path_scoped_tool_guard(allowed_dirs) rather than hand-rolling
path checks.
Fallback and retry compose, they don't replace each other. FallbackChain
moves between providers; with_retry retries a single call on a
transient error (rate limits by default). Wrap a FallbackChain's
.complete in with_retry, or use either alone.
Install
pip install llm-seam
Optional extras:
pip install "llm-seam[sdk]" # AgentSDKProvider (claude-agent-sdk)
Usage
from llm_seam import LLMClient, FallbackChain, with_retry
# Auto-select a provider from the environment
client = LLMClient()
response = client.complete("Hello, world!")
# Explicit provider by name
client = LLMClient(provider="anthropic")
# Fall back through providers in order
chain = FallbackChain(providers=[
LLMClient(provider="claude-cli").provider,
LLMClient(provider="anthropic").provider,
])
response = chain.complete("Hello")
# Retry a call with exponential backoff on rate limits
@with_retry(max_retries=3, initial_delay=1.0)
def call():
return client.complete("Hello")
Testing
cd llm-seam
pytest tests/
Dependencies
anthropic>=0.122.0,<2(1.0.0+ removedtemperature/top_p/top_kfromMessages.create;AnthropicProvider.complete()drops those three and emits aUserWarningif you pass them — useextra_body={"temperature": ...}if the target model still accepts it)openai>=3.1.0(also used byOllamaProvider, which talks to Ollama's OpenAI-compatible API — no extra required)claude-agent-sdk>=0.2.139(optional,[sdk]extra)
License
MIT
Metadata
Release files for llm-seam 0.4.0
For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.
Source distribution (sdist)
| File | Size | Uploaded | Provenance | Actions |
|---|---|---|---|---|
| llm_seam-0.4.0.tar.gz | 33.9 kB | With provenance | Details for llm_seam-0.4.0.tar.gz |
Built distribution (wheel)
| File | Interpreter | ABI | Platform | Actions Reset |
|---|---|---|---|---|
| llm_seam-0.4.0-py3-none-any.whl | Python 3 | none | any | Details for llm_seam-0.4.0-py3-none-any.whl |
Total release size: 63.6 kB
Release files / llm_seam-0.4.0.tar.gz
| Download URL | llm_seam-0.4.0.tar.gz |
|---|---|
| Size | 33.9 kB |
| Tags | Source |
|
SHA-256 checksum How to use checksums |
45ac273a388c68b34bfd2fde647a97f3dd3726e20460d920b59ef792af50b397
|
|
BLAKE2b-256 checksum How to use checksums |
c83e4907b47ecb478f58078709797c6dea0d92a3fad7fdce6d3d5583de67065a
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
Yes |
| Uploaded via |
twine/7.0.0 CPython/3.13.14
|
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
PyPI Publish Attestation
PyPI verified that this artifact, at this checksum, originated from the publisher listed below.
Signed by GitHub Actions, verified by PyPI on Sep 2, 2026.
Transparency logRelease files / llm_seam-0.4.0-py3-none-any.whl
| Download URL | llm_seam-0.4.0-py3-none-any.whl |
|---|---|
| Size | 29.7 kB |
| Tags | Python 3 |
|
SHA-256 checksum How to use checksums |
08140c3f75ffd291f410a3e9bd9e2782c0a3448acdb21e457d1bcddbd72286d4
|
|
BLAKE2b-256 checksum How to use checksums |
e2825f330956ba6c877c796c85d0ce6068e5caada5c467c2f292c367cc99e91a
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
Yes |
| Uploaded via |
twine/7.0.0 CPython/3.13.14
|
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
PyPI Publish Attestation
PyPI verified that this artifact, at this checksum, originated from the publisher listed below.
Signed by GitHub Actions, verified by PyPI on Sep 2, 2026.
Transparency logSecurity for llm-seam 0.4.0
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
Full provenance
All 2 files in this release have been uploaded with provenance metadata.
Attestation for llm_seam-0.4.0.tar.gz
PyPI Publish Attestation
PyPI verified that this artifact, at this checksum, originated from the publisher listed below.
Signed by GitHub Actions, verified by PyPI on Sep 2, 2026.
Transparency logA note on package security
PyPI is a repository for distributing packages, not a service for auditing them. While third-party security researchers and our staff do their best to detect and remove malicious packages, PyPI cannot guarantee the quality, security or suitability of any given package.
To learn more about protecting yourself from malicious actors, visit our package security documentation.