PrefectHQ/fastmcp · error · ValueError
Cannot add versioned {type_name} {logical_name!r} (version={
Error message
Cannot add versioned {type_name} {logical_name!r} (version={component.version!r}): an unversioned {type_name} with this name already exists. Either version all components or none. What it means
FastMCP requires each logical component name to be either entirely versioned or entirely unversioned. Adding a versioned component (version set) when an unversioned component of the same type and name already exists raises ValueError, since the two identity schemes cannot coexist and lookups would be ambiguous.
Source
Thrown at fastmcp_slim/fastmcp/server/providers/local_provider/local_provider.py:164
ValueError: If adding would mix versioned and unversioned components.
"""
comp_type, logical_name = self._get_component_identity(component)
is_versioned = component.version is not None
# Check all existing components of the same type and logical name
for existing in self._components.values():
if not isinstance(existing, comp_type):
continue
_, existing_name = self._get_component_identity(existing)
if existing_name != logical_name:
continue
existing_versioned = existing.version is not None
if is_versioned != existing_versioned:
type_name = comp_type.__name__.lower()
if is_versioned:
raise ValueError(
f"Cannot add versioned {type_name} {logical_name!r} "
f"(version={component.version!r}): an unversioned "
f"{type_name} with this name already exists. "
f"Either version all components or none."
)
else:
raise ValueError(
f"Cannot add unversioned {type_name} {logical_name!r}: "
f"versioned {type_name}s with this name already exist "
f"(e.g., version={existing.version!r}). "
f"Either version all components or none."
)
def _add_component(self, component: _C) -> _C:
"""Add a component to unified storage.
Args:
component: The component to add.View on GitHub (pinned to 1f02114297)
Solutions
- Add a version to the existing unversioned component so both are versioned.
- Remove the version from the new component to keep the name unversioned.
- Rename one of the components so the logical names don't collide.
Example fix
// before mcp.add_tool(greet_tool) # unversioned 'greet' mcp.add_tool(greet_v2, version='2') # raises // after mcp.add_tool(greet_tool, version='1') mcp.add_tool(greet_v2, version='2')
Defensive patterns
Strategy: validation
Validate before calling
def assert_version_scheme_consistent(existing_components, new_component):
same_name = [c for c in existing_components
if type(c).__name__.lower() == type(new_component).__name__.lower()
and (c.name or c.uri) == (new_component.name or new_component.uri)]
if same_name:
existing_versioned = same_name[0].version is not None
if (new_component.version is not None) != existing_versioned:
raise ValueError('version all components or none for this name') Type guard
def version_schemes_match(a, b) -> bool:
return (a.version is None) == (b.version is None) Try / catch
try:
mcp.add_tool(greet_v2, version='2')
except ValueError as e:
if 'Cannot add versioned' in str(e):
logging.error('mixing versioned/unversioned for same name — align versions')
raise Prevention
- Adopt one convention: either version every component or none.
- Keep versions in a single registry/config module so they stay consistent.
- Add a startup test that registers all components to catch mixing early.
When it happens
Trigger: Calling add_tool/add_resource/add_template/add_prompt (or _add_component) with a component whose version is set while a same-name, same-type component with version=None is already registered.
Common situations: Incrementally introducing versioning into an existing app: some tools get version='2.0' while older same-name tools remain unversioned; merging registries from two codebases with different conventions.
Related errors
- Cannot add unversioned {type_name} {logical_name!r}: version
- Version string cannot contain '@' (used as key delimiter): {
- mcp_tool() got unexpected keyword argument(s): {sorted(unkno
- mcp_resource() got unexpected keyword argument(s): {sorted(u
- mcp_prompt() got unexpected keyword argument(s): {sorted(unk
AI-assisted analysis of PrefectHQ/fastmcp@1f02114297 (2026-08-29).
Data as JSON: /api/errors/e9d7ff28722039c6.
Report an issue: GitHub.