OpenBMB/ChatDev · critical · RegistryError
Entry '{name}' is not a BaseConfig subclass
Error message
Entry '{name}' is not a BaseConfig subclass What it means
get_subgraph_source_config loads a registered subgraph source entry and verifies it resolves to a BaseConfig subclass; if the registered object is not a class inheriting BaseConfig, RegistryError is raised. Called from subgraph config from_dict when resolving the source by name.
Source
Thrown at entity/configs/node/subgraph.py:41
def register_subgraph_source(
name: str,
*,
config_cls: type[BaseConfig],
description: str | None = None,
) -> None:
"""Register a subgraph source configuration class."""
metadata = {"summary": description} if description else None
subgraph_source_registry.register(name, target=config_cls, metadata=metadata)
def get_subgraph_source_config(name: str) -> type[BaseConfig]:
entry = subgraph_source_registry.get(name)
config_cls = entry.load()
if not isinstance(config_cls, type) or not issubclass(config_cls, BaseConfig):
raise RegistryError(f"Entry '{name}' is not a BaseConfig subclass")
return config_cls
def iter_subgraph_source_registrations() -> Dict[str, type[BaseConfig]]:
return {name: entry.load() for name, entry in subgraph_source_registry.items()}
def iter_subgraph_source_metadata() -> Dict[str, Dict[str, Any]]:
return {name: dict(entry.metadata or {}) for name, entry in subgraph_source_registry.items()}
@dataclass
class SubgraphFileConfig(BaseConfig):
file_path: str
@classmethod
def from_dict(cls, data: Mapping[str, Any], *, path: str) -> "SubgraphFileConfig":
mapping = require_mapping(data, path)View on GitHub (pinned to 4fb2db0ea9)
Solutions
- Register the BaseConfig subclass itself (or make entry.load() return it) for the subgraph source
- Verify with iter_subgraph_source_registrations() what each name currently resolves to
- Add an import-time check after registration asserting issubclass(cfg, BaseConfig)
Example fix
# before
register_subgraph_source('my_source', lambda: build_config_instance)
# after
class MySourceConfig(BaseConfig):
...
register_subgraph_source('my_source', lambda: MySourceConfig) Defensive patterns
Strategy: type-guard
Validate before calling
from entity.configs.node.subgraph import iter_subgraph_source_registrations
from entity.configs import BaseConfig
for name, cls in iter_subgraph_source_registrations().items():
assert issubclass(cls, BaseConfig), f'{name} registered wrongly' Type guard
def registration_is_valid(name: str) -> bool:
from entity.configs.node.subgraph import iter_subgraph_source_registrations
from entity.configs import BaseConfig
cls = iter_subgraph_source_registrations().get(name)
return isinstance(cls, type) and issubclass(cls, BaseConfig) Try / catch
try:
cfg = SubgraphConfig.from_dict(d, path='subgraph')
except RegistryError as e:
# the source name is registered incorrectly; fall back to inline config or fail fast
... Prevention
- Register config classes, not instances or factories
- Add an import-time self-check after plugin registration
- Test subgraph configs in plugin CI
When it happens
Trigger: Registering a subgraph source whose entry.load() returns a function, instance, or non-BaseConfig class, then parsing a subgraph node config referencing that name.
Common situations: Plugin/custom registration mistakes (registering a factory function instead of the config class); refactors changing what the entry returns; version drift where registration API expectations changed.
Related errors
- Edge condition type '{name}' already registered
- Entry '{name}' is not an EdgeConditionRegistration
- Edge processor type '{name}' already registered
- Entry '{name}' is not an EdgeProcessorRegistration
- Memory store '{name}' already registered
AI-assisted analysis of OpenBMB/ChatDev@4fb2db0ea9 (2026-08-27).
Data as JSON: /api/errors/ee5c6542389977db.
Report an issue: GitHub.