run-llama/llama_index · error · NotImplementedError

FnNodeMapping does not support persist method.

Error message

FnNodeMapping does not support persist method.

What it means

FnObjectNodeMapping.persist raises NotImplementedError because a function-based mapping holds no state worth pickling (its behavior lives in the to/from-node callables, which are generally not pickleable anyway). Persistence must be handled by the user outside the class.

Source

Thrown at llama-index-core/llama_index/core/objects/fn_node_mapping.py:56

    def to_node(self, obj: Any) -> BaseNode:
        """To node."""
        return self._to_node_fn(obj)

    def _from_node(self, node: BaseNode) -> Any:
        """From node."""
        return self._from_node_fn(node)

    @property
    def obj_node_mapping(self) -> Dict[int, Any]:
        """The mapping data structure between node and object."""
        raise NotImplementedError("FnNodeMapping does not support obj_node_mapping")

    def persist(
        self, persist_dir: str = ..., obj_node_mapping_fname: str = ...
    ) -> None:
        """Persist objs."""
        raise NotImplementedError("FnNodeMapping does not support persist method.")

    @classmethod
    def from_persist_dir(
        cls,
        persist_dir: str = DEFAULT_PERSIST_DIR,
        obj_node_mapping_fname: str = DEFAULT_PERSIST_FNAME,
    ) -> "FnNodeMapping":
        raise NotImplementedError("FnNodeMapping does not support persist method.")

View on GitHub (pinned to afd0fef371)

Solutions

  1. Persist only the underlying index (persist its storage_context / index_store) and rebuild the FnObjectNodeMapping from the same callables at load time
  2. Use SimpleObjectNodeMapping instead if whole-object persistence is required
  3. Wrap the persist call in a check for the mapping type before calling it

Example fix

# before
obj_index = ObjectIndex.from_objects(objs, object_mapping_fn=..., index=index)
obj_index.persist("./storage")  # NotImplementedError from FnObjectNodeMapping.persist

# after
index.storage_context.persist(persist_dir="./storage")  # save index only
# at load time: rebuild FnObjectNodeMapping(to_node_fn, from_node_fn) and ObjectIndex(index=loaded_index, object_node_mapping=fn_mapping)
Defensive patterns

Strategy: type-guard

Validate before calling

from llama_index.core.objects import FnObjectNodeMapping
if isinstance(obj_index.object_node_mapping, FnObjectNodeMapping):
    obj_index.index.storage_context.persist(persist_dir=persist_dir)  # persist index only
else:
    obj_index.persist(persist_dir)

Type guard

def can_persist_mapping(mapping) -> bool:
    from llama_index.core.objects import FnObjectNodeMapping
    return not isinstance(mapping, FnObjectNodeMapping)

Try / catch

try:
    obj_index.persist(persist_dir)
except NotImplementedError:
    obj_index.index.storage_context.persist(persist_dir=persist_dir)
    # rebuild FnObjectNodeMapping with the same callables at load time

Prevention

When it happens

Trigger: Calling obj_index.persist(persist_dir) (ObjectIndex.persist delegates to the mapping's persist) when the ObjectIndex was built with FnObjectNodeMapping; or calling fn_mapping.persist(...) directly.

Common situations: Building an ObjectIndex from custom functions then trying to save/load it across sessions; copy-pasting persistence code from a SimpleObjectNodeMapping example onto an Fn-based index.

Related errors


AI-assisted analysis of run-llama/llama_index@afd0fef371 (2026-08-15). Data as JSON: /api/errors/35b2a20d463a3be8. Report an issue: GitHub.