diff --git a/lib/crewai/src/crewai/flow/persistence/mongodb.py b/lib/crewai/src/crewai/flow/persistence/mongodb.py index e1a5e03bd..f8fe20fc0 100644 --- a/lib/crewai/src/crewai/flow/persistence/mongodb.py +++ b/lib/crewai/src/crewai/flow/persistence/mongodb.py @@ -148,7 +148,10 @@ class MongoDbFlowPersistence(FlowPersistence): def _to_state_dict(state_data: dict[str, Any] | BaseModel) -> dict[str, Any]: """Convert state_data to a plain dict.""" if isinstance(state_data, BaseModel): - return state_data.model_dump(mode="json") + try: + return state_data.model_dump(mode="json") + except Exception: + return state_data.model_dump(mode="python") if isinstance(state_data, dict): return state_data raise ValueError( diff --git a/lib/crewai/tests/test_flow_persistence_mongodb.py b/lib/crewai/tests/test_flow_persistence_mongodb.py index b01c88806..456de8001 100644 --- a/lib/crewai/tests/test_flow_persistence_mongodb.py +++ b/lib/crewai/tests/test_flow_persistence_mongodb.py @@ -11,7 +11,7 @@ from datetime import datetime, timezone import sys from typing import Any -from pydantic import BaseModel +from pydantic import BaseModel, ConfigDict import pytest from crewai.flow.async_feedback.types import PendingFeedbackContext @@ -213,6 +213,27 @@ def test_basemodel_state_serialized_as_json( assert loaded["when"].startswith("2026-01-02T03:04:05") +def test_basemodel_state_falls_back_to_python_serialization( + monkeypatch: pytest.MonkeyPatch, +) -> None: + _patch_client(monkeypatch) + + class NonJsonValue: + def __str__(self) -> str: + return "non-json value" + + class State(BaseModel): + model_config = ConfigDict(arbitrary_types_allowed=True) + + value: NonJsonValue + + persistence = MongoDbFlowPersistence(CONN) + + persistence.save_state("flow-1", "s", State(value=NonJsonValue())) + + assert persistence.load_state("flow-1") == {"value": "non-json value"} + + def test_dict_state_serializes_non_json_values( monkeypatch: pytest.MonkeyPatch, ) -> None: