{"record":{"id":"2b75b5b5791ecf61","repo":"BerriAI/litellm","slug":"unmapped-response-type-got-type-type-result","errorCode":null,"errorMessage":"Unmapped response type. Got type: {type(result)}","messagePattern":"Unmapped response type\\. Got type: (.+?)","errorType":"exception","errorClass":"Exception","httpStatus":null,"severity":"error","filePath":"litellm/endpoints/speech/speech_to_completion_bridge/handler.py","lineNumber":123,"sourceCode":"            input=input,\n            optional_params=optional_params,\n            litellm_params=litellm_params,\n            headers=headers,\n            litellm_logging_obj=logging_obj,\n            custom_llm_provider=custom_llm_provider,\n            voice=voice,\n        )\n\n        result: Final = completion(\n            **request_data,\n        )\n\n        if isinstance(result, ModelResponse):\n            return self.transformation_handler.transform_response(\n                model_response=result,\n            )\n        else:\n            raise Exception(f\"Unmapped response type. Got type: {type(result)}\")\n\n\nspeech_to_completion_bridge_handler = SpeechToCompletionBridgeHandler()\n","sourceCodeStart":105,"sourceCodeEnd":127,"githubUrl":"https://github.com/BerriAI/litellm/blob/6c2dcb801bf2b75c18f1bb24140e7cf57465cc4d/litellm/endpoints/speech/speech_to_completion_bridge/handler.py#L105-L127","documentation":"Raised in SpeechToCompletionBridgeHandler.speech (handler.py:123) when the internal litellm.completion() call returns something that is not a ModelResponse — e.g. a streaming iterator (CustomStreamWrapper) or an executor/future. The bridge can only convert a complete ModelResponse containing an audio part into HttpxBinaryResponseContent, so any other result type is treated as a programming/configuration error.","triggerScenarios":"The transformed request data includes stream=True (optional_params leaking a stream flag into the completion call), so completion() returns a stream wrapper instead of ModelResponse; or a mocked/patched completion returning a different type.","commonSituations":"Passing stream=True (or a router/deployment default that sets stream) to an audio/speech call routed through the bridge; providers or custom callbacks that alter the completion return type; tests monkeypatching litellm.completion with a plain dict.","solutions":["Remove stream=True from the speech/TTS call — the bridge requires a non-streaming response","Inspect optional_params and litellm_params forwarded to the bridge and strip any 'stream' key","If you patched litellm.completion in tests, make the mock return a ModelResponse instance"],"exampleFix":"# before\nresp = litellm.audio_speech(model=\"gpt-4o-audio-preview\", input=\"hi\", voice=\"alloy\", stream=True)\n\n# after\nresp = litellm.audio_speech(model=\"gpt-4o-audio-preview\", input=\"hi\", voice=\"alloy\")","handlingStrategy":"validation","validationCode":"optional_params = {k: v for k, v in (optional_params or {}).items() if k != \"stream\"}\n# ensure the bridge receives a non-streaming completion call","typeGuard":"from litellm.types.utils import ModelResponse\n\ndef is_model_response(result: object) -> bool:\n    return isinstance(result, ModelResponse)","tryCatchPattern":"try:\n    audio = litellm.audio_speech(model=model, input=text, voice=voice)\nexcept Exception as e:\n    if \"Unmapped response type\" in str(e):\n        logger.error(\"completion() returned %s; disable streaming for speech calls\", e)\n        raise","preventionTips":["Never pass stream=True to audio/speech endpoints routed through the chat bridge","Strip 'stream' from optional_params before they reach TTS calls","Test mocks of litellm.completion must return ModelResponse instances"],"tags":["tts","speech","streaming","response-type","type-check"],"backgroundTag":null,"analyzedSha":"6c2dcb801bf2b75c18f1bb24140e7cf57465cc4d","analyzedAt":"2026-08-15T07:12:03.035Z","schemaVersion":2},"datasetVersion":"2026-08-15T17:31:12.345Z"}