windlass.core.registry¶
registry
¶
The component registry — how Windlass stays open for extension.
Every replaceable part of the framework (LLMs, chunkers, retrievers, vector stores, ...) is a component kind. Implementations register a name against a kind; builders and the DI container resolve names to instances. Nothing in Windlass imports a concrete provider module directly, which is what keeps the core install tiny and the architecture pluggable.
Three ways to register¶
1. Decorator (in-process) — the common case for application code::
from windlass import register
from windlass.interfaces import Chunker
@register.chunker("sentence")
class SentenceChunker(Chunker):
...
2. Lazy path (used by Windlass itself) — records a dotted path without
importing the module, so import windlass never pulls in optional deps::
REGISTRY.register_lazy("vectordb", "faiss", "windlass.providers.vectordb.faiss:FaissStore")
3. Entry points (distributable plugins) — a third-party package publishes::
[project.entry-points."windlass.chunker"]
sentence = "my_pkg.chunkers:SentenceChunker"
and it appears in windlass automatically, with no code change on either side.
Thread safety¶
All mutating operations take a re-entrant lock, and lazy resolution is idempotent, so the registry is safe to use from worker threads.
ComponentSpec
dataclass
¶
ComponentSpec(
kind: str,
name: str,
target: Any = None,
path: str | None = None,
extra: str | None = None,
aliases: tuple[str, ...] = (),
description: str = "",
defaults: dict[str, Any] = dict(),
origin: str = "user",
)
A registry entry: how to obtain one implementation of a component kind.
Exactly one of target or path is set. path entries are resolved
on first use, which is what makes registration free of import cost.
Attributes:
| Name | Type | Description |
|---|---|---|
kind |
str
|
The component kind, e.g. |
name |
str
|
The lookup name, e.g. |
target |
Any
|
The resolved class or factory, once known. |
path |
str | None
|
Dotted |
extra |
str | None
|
Extras group needed for this component, used in error messages. |
aliases |
tuple[str, ...]
|
Additional names that resolve to this spec. |
description |
str
|
One-line summary shown by |
defaults |
dict[str, Any]
|
Keyword arguments merged under user config at construction. |
origin |
str
|
|
resolve
¶
Import and cache the target if it was registered lazily.
Returns:
| Type | Description |
|---|---|
Any
|
The class or factory for this component. |
Raises:
| Type | Description |
|---|---|
RegistryError
|
If the dotted path cannot be imported. Missing
optional dependencies surface as
:class: |
Source code in src\windlass\core\registry.py
Registry
¶
A thread-safe, kind-partitioned component registry.
You almost never construct this yourself — use the module-level
:data:REGISTRY singleton, or the :data:register decorator namespace.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
discover
|
bool
|
Whether the first lookup should scan installed distributions
for entry-point plugins. The process-wide :data: |
False
|
Example
reg = Registry() _ = reg.register("chunker", "shouty", lambda: None, description="demo") reg.has("chunker", "shouty") True reg.names("chunker") ['shouty']
Opt in explicitly when you do want the installed plugins:
discovered = Registry(discover=True) isinstance(discovered.load_plugins(), list) True
Source code in src\windlass\core\registry.py
add_kind
¶
Declare a brand new component kind at runtime.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
kind
|
str
|
The new kind's name. |
required |
kinds
¶
register
¶
register(
kind: str,
name: str,
target: Any,
*,
aliases: tuple[str, ...] | str = (),
description: str = "",
extra: str | None = None,
defaults: dict[str, Any] | None = None,
origin: str = "user",
override: bool = False
) -> ComponentSpec
Register a concrete class or factory.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
kind
|
str
|
Component kind. |
required |
name
|
str
|
Lookup name; case-insensitive. |
required |
target
|
Any
|
A class or a zero-or-more-argument factory callable. |
required |
aliases
|
tuple[str, ...] | str
|
Extra names resolving to the same component. |
()
|
description
|
str
|
One-line summary for CLI listings and docs. |
''
|
extra
|
str | None
|
Extras group required, used in error hints. |
None
|
defaults
|
dict[str, Any] | None
|
Config defaults merged beneath user-supplied kwargs. |
None
|
origin
|
str
|
|
'user'
|
override
|
bool
|
Allow replacing an existing registration. |
False
|
Returns:
| Type | Description |
|---|---|
ComponentSpec
|
The stored :class: |
Raises:
| Type | Description |
|---|---|
DuplicateComponentError
|
If |
Source code in src\windlass\core\registry.py
register_lazy
¶
register_lazy(
kind: str,
name: str,
path: str,
*,
aliases: tuple[str, ...] | str = (),
description: str = "",
extra: str | None = None,
defaults: dict[str, Any] | None = None,
origin: str = "builtin",
override: bool = False
) -> ComponentSpec
Register a component by dotted path without importing it.
This is how every built-in provider is wired up: the module is only imported the first time somebody actually asks for that component.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
kind
|
str
|
Component kind. |
required |
name
|
str
|
Lookup name. |
required |
path
|
str
|
|
required |
aliases
|
tuple[str, ...] | str
|
Extra names resolving here. |
()
|
description
|
str
|
One-line summary. |
''
|
extra
|
str | None
|
Extras group required by the target module. |
None
|
defaults
|
dict[str, Any] | None
|
Config defaults. |
None
|
origin
|
str
|
Provenance label. |
'builtin'
|
override
|
bool
|
Allow replacing an existing registration. |
False
|
Returns:
| Type | Description |
|---|---|
ComponentSpec
|
The stored :class: |
Source code in src\windlass\core\registry.py
unregister
¶
Remove a component and its aliases. No-op when absent.
Source code in src\windlass\core\registry.py
get
¶
Return the spec registered under name.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
kind
|
str
|
Component kind. |
required |
name
|
str
|
Name or alias, case-insensitive. |
required |
Returns:
| Type | Description |
|---|---|
ComponentSpec
|
The matching spec. |
Raises:
| Type | Description |
|---|---|
ComponentNotFoundError
|
If nothing matches. The error lists all available names for that kind. |
Source code in src\windlass\core\registry.py
has
¶
Return whether name resolves for kind.
names
¶
specs
¶
Return every spec for kind, sorted by name.
catalog
¶
create
¶
Instantiate a registered component.
Registered defaults are merged underneath config, so caller
arguments always win.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
kind
|
str
|
Component kind. |
required |
name
|
str
|
Name or alias. |
required |
**config
|
Any
|
Constructor keyword arguments. |
{}
|
Returns:
| Type | Description |
|---|---|
Any
|
The constructed component. |
Raises:
| Type | Description |
|---|---|
ComponentNotFoundError
|
If the name is not registered. |
ConfigurationError
|
If the constructor rejects the arguments. |
Example
from windlass.core.registry import REGISTRY llm = REGISTRY.create("llm", "fake", responses=["hi"]) llm.complete("anything").content 'hi'
Source code in src\windlass\core\registry.py
ensure_plugins_loaded
¶
Discover entry-point plugins exactly once, on first lookup.
A no-op unless this registry was constructed with discover=True.
:meth:load_plugins remains available on any registry for callers that
want discovery on demand.
Source code in src\windlass\core\registry.py
load_plugins
¶
Scan installed distributions for Windlass plugins.
Two entry-point conventions are supported:
windlass.plugins— the value is a callable taking the registry; use this to register many components or to do custom setup.windlass.<kind>(e.g.windlass.chunker) — the value is the component class itself, registered under the entry-point name.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
strict
|
bool
|
Raise on the first plugin that fails instead of warning. |
False
|
Returns:
| Type | Description |
|---|---|
list[str]
|
Names of the plugins that loaded successfully. |
Raises:
| Type | Description |
|---|---|
PluginError
|
Only when |
Source code in src\windlass\core\registry.py
snapshot
¶
Return a shallow copy of the registry state (for tests).
restore
¶
Restore a previously captured :meth:snapshot (for tests).
create
¶
Instantiate a component from the global registry.
Thin module-level shortcut for :meth:Registry.create.