{"record":{"id":"1734f2cf1d274628","repo":"microsoft/autogen","slug":"unsupported-handoff-type-type-handoff","errorCode":null,"errorMessage":"Unsupported handoff type: {type(handoff)}","messagePattern":"Unsupported handoff type: (.+?)","errorType":"validation","errorClass":"ValueError","httpStatus":null,"severity":"error","filePath":"python/packages/autogen-agentchat/src/autogen_agentchat/agents/_assistant_agent.py","lineNumber":804,"sourceCode":"        # Check if tool names are unique.\n        tool_names = [tool.name for tool in self._tools]\n        if len(tool_names) != len(set(tool_names)):\n            raise ValueError(f\"Tool names must be unique: {tool_names}\")\n\n        # Handoff tools.\n        self._handoff_tools: List[BaseTool[Any, Any]] = []\n        self._handoffs: Dict[str, HandoffBase] = {}\n        if handoffs is not None:\n            if model_client.model_info[\"function_calling\"] is False:\n                raise ValueError(\"The model does not support function calling, which is needed for handoffs.\")\n            for handoff in handoffs:\n                if isinstance(handoff, str):\n                    handoff = HandoffBase(target=handoff)\n                if isinstance(handoff, HandoffBase):\n                    self._handoff_tools.append(handoff.handoff_tool)\n                    self._handoffs[handoff.name] = handoff\n                else:\n                    raise ValueError(f\"Unsupported handoff type: {type(handoff)}\")\n        # Check if handoff tool names are unique.\n        handoff_tool_names = [tool.name for tool in self._handoff_tools]\n        if len(handoff_tool_names) != len(set(handoff_tool_names)):\n            raise ValueError(f\"Handoff names must be unique: {handoff_tool_names}\")\n        # Create sets for faster lookup\n        tool_names_set = set(tool_names)\n        handoff_tool_names_set = set(handoff_tool_names)\n\n        # Check if there's any overlap between handoff tool names and tool names\n        overlap = tool_names_set.intersection(handoff_tool_names_set)\n\n        # Also check if any handoff target name matches a tool name\n        # This handles the case where a handoff is specified directly with a string that matches a tool name\n        for handoff in handoffs or []:\n            if isinstance(handoff, str) and handoff in tool_names_set:\n                raise ValueError(\"Handoff names must be unique from tool names\")\n            elif isinstance(handoff, HandoffBase) and handoff.target in tool_names_set:\n                raise ValueError(\"Handoff names must be unique from tool names\")","sourceCodeStart":786,"sourceCodeEnd":822,"githubUrl":"https://github.com/microsoft/autogen/blob/027ecf0a379bcc1d09956d46d12d44a3ad9cee14/python/packages/autogen-agentchat/src/autogen_agentchat/agents/_assistant_agent.py#L786-L822","documentation":"While processing the handoffs argument, AssistantAgent accepts only strings (converted to HandoffBase with that target) or HandoffBase instances; each entry that is neither raises ValueError with its type. This runs after the function-calling check, inside the per-handoff loop.","triggerScenarios":"Passing handoffs=[123], handoffs=[{\"target\": \"b\"}], a Tool instance, or any custom handoff class that does not subclass HandoffBase (or subclasses one from a mismatched autogen install).","commonSituations":"Using dict-style handoff specs from tutorials of other frameworks, duplicate autogen package copies breaking isinstance, or passing a HandoffBase subclass instance from an older API version.","solutions":["Use plain strings (target agent names) or HandoffBase/its subclasses for handoffs entries.","Ensure only one consistent autogen-agentchat/autogen-core version is installed (`pip list | grep autogen`).","Wrap custom handoff logic in a HandoffBase subclass with a message and target."],"exampleFix":"# before\nagent = AssistantAgent(name=\"a\", model_client=client, handoffs=[{\"target\": \"researcher\"}])\n\n# after\nagent = AssistantAgent(name=\"a\", model_client=client, handoffs=[HandoffBase(target=\"researcher\", message=\"Task passed to researcher.\")])","handlingStrategy":"type-guard","validationCode":"from autogen_agentchat.agents._assistant_agent import HandoffBase\nfor h in handoffs or []:\n    if not isinstance(h, (str, HandoffBase)):\n        raise ValueError(f\"Unsupported handoff entry: {h!r} ({type(h).__name__})\")","typeGuard":"def is_valid_handoff(h) -> bool:\n    return isinstance(h, str) or isinstance(h, HandoffBase)","tryCatchPattern":"try:\n    agent = AssistantAgent(name=\"a\", model_client=client, handoffs=handoffs)\nexcept ValueError as e:\n    if \"Unsupported handoff type\" in str(e):\n        handoffs = [h if isinstance(h, (str, HandoffBase)) else HandoffBase(target=str(h)) for h in handoffs]\n    else:\n        raise","preventionTips":["Use only string targets or HandoffBase instances in handoff lists.","Keep one autogen installation per environment to keep isinstance checks reliable."],"tags":["python","handoffs","type-validation","autogen"],"backgroundTag":null,"analyzedSha":"027ecf0a379bcc1d09956d46d12d44a3ad9cee14","analyzedAt":"2026-08-15T03:38:00.719Z","schemaVersion":2},"datasetVersion":"2026-08-15T22:17:37.221Z"}