Quick Start
How It Works
The registry is thread-safe and loads plugins lazily. Built-ins are discovered on first access, entry points are loaded when needed, and aliases are case-insensitive. The singleton registry is obtained viaget_default_registry().
Configuration / API
Functions
| Function / Method | Signature | Description |
|---|---|---|
register_provider(type, cls) | (str, Type[BaseProvider]) -> None | Backwards-compat module function; delegates to get_default_registry().register(...) |
get_provider(type, base_url, api_key, **kw) | (str, str, Optional[str], **Any) -> Optional[BaseProvider] | Resolve + instantiate; returns None for unknown type; raises if loader fails |
list_provider_types() | () -> List[str] | List registered + entry-point + built-in types |
get_provider_class(type) | (str) -> Optional[Type[BaseProvider]] | Returns the class without instantiating |
get_default_registry() | () -> ProviderRegistry | Thread-safe singleton accessor |
ProviderRegistry Class
| Method | Signature | Description |
|---|---|---|
ProviderRegistry.get(type, base_url, api_key, **kw) | identical to get_provider | OOP-style interface |
ProviderRegistry.list_types() | () -> List[str] | Back-compat alias for list_names() |
ProviderRegistry.get_class(type) | (str) -> Optional[Type] | Back-compat alias for resolve() |
Built-in Provider Types
| Type | Loaded From | Purpose |
|---|---|---|
recipe | endpoints/providers/recipe.py | Recipe runner endpoint |
agents-api | endpoints/providers/agents_api.py | OpenAI Agents-API compatible endpoint |
mcp | endpoints/providers/mcp.py | MCP server endpoint |
tools-mcp | endpoints/providers/tools_mcp.py | MCP tools-only endpoint |
a2a | endpoints/providers/a2a.py | A2A protocol endpoint |
a2u | endpoints/providers/a2u.py | A2U protocol endpoint |
Common Patterns
Override a Built-in
Override a Built-in
Last-write-wins behavior lets you replace built-in providers:
Multiple Aliases
Multiple Aliases
Use the underlying PluginRegistry for alias support:
Per-tenant Isolation
Per-tenant Isolation
Instantiate
ProviderRegistry directly for isolation:Best Practices
Always provide a _loader() function
Always provide a _loader() function
Never import your provider class at module top-level — defeats lazy loading and breaks the no-heavy-deps-at-import-time guarantee:
Subclass BaseProvider
Subclass BaseProvider
Required for type compatibility and consistent API:
Distinguish missing vs import failure
Distinguish missing vs import failure
get_provider("unknown") returns None, but import failures propagate:Prefer entry points for distributable packages
Prefer entry points for distributable packages
Use
pyproject.toml entry points instead of register_provider() calls:Related
Integration Registry
The sibling plugin registry for CLI tools / managed agents
Framework Adapter Plugins
Third sibling plugin registry, for framework adapters

