run-llama/llama_index · warning · ValueError
'handoff' is a reserved tool name. Please use a different na
Error message
'handoff' is a reserved tool name. Please use a different name.
What it means
MutableMappingKVStore.persist unconditionally raises NotImplementedError; it exists only so type checkers accept the method on the base class. Persistence is a capability of concrete dict-backed stores like SimpleKVStore, which implements persist(persist_path, fs) to write JSON; calling it on the base (or a subclass that inherits it) means you asked a non-persistable store to persist.
Source
Thrown at llama-index-core/llama_index/core/agent/workflow/base_agent.py:228
"""
Validate tools.
If tools are not of type BaseTool, they will be converted to FunctionTools.
This assumes the inputs are tools or callable functions.
"""
if v is None:
return None
validated_tools: List[BaseTool] = []
for tool in v:
if not isinstance(tool, BaseTool):
validated_tools.append(FunctionTool.from_defaults(tool))
else:
validated_tools.append(tool)
for tool in validated_tools:
if tool.metadata.name == "handoff":
raise ValueError(
"'handoff' is a reserved tool name. Please use a different name."
)
return validated_tools # type: ignore[return-value]
def _get_prompts(self) -> PromptDictType:
"""Get prompts."""
return {}
def _get_prompt_modules(self) -> PromptMixinType:
"""Get prompt sub-modules."""
return {}
def _update_prompts(self, prompts_dict: PromptDictType) -> None:
"""Update prompts."""
@abstractmethod
async def take_step(View on GitHub (pinned to afd0fef371)
Solutions
- Use SimpleKVStore (or a subclass that implements persist) when you need to persist to disk.
- Override persist in your custom store: serialize self._data with json.dump to persist_path.
- Branch on capability: if isinstance(store, SimpleKVStore): store.persist(...) else: <export via your own mechanism>.
- Rely on your backend's native durability (e.g. MongoDB/Redis stores persist implicitly) instead of persist().
Example fix
# before
kvstore: MutableMappingKVStore = CustomKVStore()
kvstore.persist("out.json") # NotImplementedError
# after
import json
class CustomKVStore(MutableMappingKVStore):
def persist(self, persist_path, fs=None):
with open(persist_path, "w") as f:
json.dump(self._data, f) Defensive patterns
Strategy: type-guard
Validate before calling
if not hasattr(type(kvstore), 'persist') or type(kvstore).persist is MutableMappingKVStore.persist:
raise TypeError('store cannot persist; use SimpleKVStore')
kvstore.persist(path) Type guard
from llama_index.core.storage.kvstore.simple_kvstore import SimpleKVStore
from llama_index.core.storage.kvstore.types import MutableMappingKVStore
def is_persistable(store) -> bool:
return not (type(store).persist is MutableMappingKVStore.persist) Try / catch
try:
kvstore.persist('out.json')
except NotImplementedError:
# export via store-native mechanism instead
... Prevention
- Implement persist in custom MutableMappingKVStore subclasses.
- Only annotate variables as the concrete persistable type when persistence is required.
- Prefer SimpleKVStore when disk snapshots are part of the workflow.
When it happens
Trigger: Calling kvstore.persist('store.json') on an instance of MutableMappingKVStore or a subclass that does not override persist (e.g. a custom in-memory store); generic code that receives a MutableMappingKVStore-typed value and assumes persistence.
Common situations: Pluggable storage configurations where a custom or third-party store replaces SimpleKVStore but persistence code paths (StorageContext.persist, docstore.persist) were not updated; type annotations widened to MutableMappingKVStore letting non-persistable stores flow into persist calls.
Related errors
- Could not extract final answer from input text: {input_text}
- Got empty streaming response
- Could not parse output: {output}
- FnNodeMapping does not support persist method.
- This object node mapping does not support persist method.
AI-assisted analysis of run-llama/llama_index@afd0fef371 (2026-08-15).
Data as JSON: /api/errors/6c48c86591ccdd1a.
Report an issue: GitHub.