Ë
    uPêjÛ  ã                   óæ  — U d dl Z d dlZd dlmZmZmZ d dlmZ d dlmZm	Z	m
Z
mZmZmZmZmZ d dlmZ d dlmZ d dlmZ d dlmZ d d	lmZ d d
lmZmZmZ d dlm Z  d dl!m"Z" d dl#m$Z$m%Z%m&Z& d dl#m'Z( d dl)m*Z*m+Z+m,Z,m-Z-m.Z.m/Z/m0Z0 d dl1m2Z2m3Z3 erd dl4m5Z5 d dl4m6Z7 d dl8m9Z9 d dl:m;Z; ne	Z7ee<e=f   Z'ee>d<    G d„ de«      Z?dZ@e
e>d<   e@› d�ZAe
e>d<    e j„                  d«      ZCe
e>d<    G d„ d«      ZDy) é    N)ÚIterableÚMappingÚSequence)Údatetime)ÚTYPE_CHECKINGÚAnyÚFinalÚLiteralÚOptionalÚ	TypeAliasÚ	TypedDictÚoverload)ÚChatCompletionToolParam)ÚFunctionToolParam)Úverbose_logger)ÚMAXIMUM_TRACEBACK_LINES_TO_LOG)ÚLogging)Úlogging_safe_mcp_headersÚsplit_server_prefix_from_nameÚstrip_known_server_prefix©Ú
aresponses)Ú!BaseResponsesAPIStreamingIterator)ÚResponseInputParamÚResponsesAPIResponseÚResponsesAPIStreamingResponse)Ú	ToolParam)Ú	CallTypesÚ#ChatCompletionMessageCustomToolCallÚChatCompletionMessageToolCallÚChoicesÚMessageÚModelResponseÚStandardLoggingMCPToolCall)ÚRulesÚfunction_setup)ÚCallToolResult)ÚTool)ÚUserAPIKeyAuth)ÚProxyLoggingr   c                   ó8   — e Zd ZU edz  ed<   eed<   edz  ed<   y)ÚMCPToolResultNÚtool_call_idÚresultÚname)Ú__name__Ú
__module__Ú__qualname__ÚstrÚ__annotations__© ó    út/home/oem/CyberBrain26-unified/.venv/lib/python3.12/site-packages/litellm/responses/mcp/litellm_proxy_mcp_handler.pyr,   r,   2   s   … Ø˜‘*ÓØƒKØ
�‰*Ôr6   r,   Úlitellm_proxyÚLITELLM_PROXY_MCP_SERVER_URLz/mcp/Ú#LITELLM_PROXY_MCP_SERVER_URL_PREFIXz^https?://.+/mcp/([^/]+)$Ú_PROXY_MCP_PATH_REc                   óä  — e Zd ZdZedeeef   dz  dee   fd„«       Z	ede
e   dz  defd„«       Zede
eeef      dz  deee   ee   f   fd„«       Zed	ee   d
ee   ddddfd„«       Ze	 	 	 	 dOddde
eeef      dz  dedz  dedz  deeeeef   f   dz  dee   dz  deee   ee   f   fd„«       Zedee   dee   deee   eeef   f   fd„«       Zedee   deeeef      dee   fd„«       Ze	 	 dPdddeeeef      dedz  dee   dz  deee   eeef   f   f
d„«       Ze	 	 	 	 dOdedeeeef      dedz  dedz  deeeeef   f   dz  dee   dz  deee   eeef   f   fd„«       Zee	 dQdee   ded   dee   fd„«       «       Zeedee   ded   dee   fd„«       «       Ze	 dRdee   ded    deeez     fd!„«       Zedeeeef      defd"„«       Zed#e dee   fd$„«       Z!ed#e"dee   fd%„«       Z#ed&edeedz  edz  edz  f   fd'„«       Z$ed(edz  deeef   fd)„«       Z%ed*d+defd,„«       Z&e	 	 	 	 	 	 	 dSd-eeef   d.ee   dededz  deeeeef   f   dz  d/eeef   dz  d0eeef   dz  d1edz  dedz  dee   dz  dee'   fd2„«       Z(ed3ee   d#e"d4eeeef      deeeef      fd5„«       Z)e	 dTd#e d4eeeef      d6ee*z  dz  dee   fd7„«       Z+ed8ee   d9ed:ee,   dz  d;ed<ede e-z  fd=„«       Z.ed>e/d?   ddd@eeef   dAe0ddf
dB„«       Z1edCee*z  d9ed:ee   dz  deeeef      dDee2   d<eeef   dEedz  d-eeef   defdF„«       Z3edCee*z  d9ed:ee   dz  d<eeef   dEedz  dedeeef   fdG„«       Z4ed.ee   d4ee'   dee2   fdH„«       Z5ed<eeef   dIedeeef   fdJ„«       Z6ed<eeef   dKedeeef   fdL„«       Z7ed#e dMee   d4eeeef      de fdN„«       Z8y)UÚLiteLLM_Proxy_MCP_Handlerz¦
    Helper class with static methods for MCP integration with Responses API.

    This handles when a user passes mcp server_url="litellm_proxy" in their tools.
    ÚkwargsNÚreturnc                 ó¶   — | sg S ddl m} | j                  d«      xs | }|j                  d«      xs | j                  d«      xs i }|j                  ||¬«      S )ziTags from the parent LLM request, using the same extraction logic as standard logging (incl. User-Agent).r   )ÚStandardLoggingPayloadSetupÚlitellm_paramsÚproxy_server_request)rB   rC   )Ú*litellm.litellm_core_utils.litellm_loggingrA   ÚgetÚ_get_request_tags)r>   rA   rB   rC   s       r7   Ú_get_parent_request_tagsz2LiteLLM_Proxy_MCP_Handler._get_parent_request_tagsJ   sh   € ñ ØˆIÝZà &§
¡
Ð+;Ó <Ò FÀˆØ-×1Ñ1Ð2HÓIÒuÈVÏZÉZÐXnÓMoÒuÐsuÐØ*×<Ñ<Ø)Ø!5ð =ó 
ð 	
r6   Útoolsc                 ó$  — | rŽ| D ]‰  }t        |t        «      sŒ|j                  d«      dk(  sŒ)|j                  dd«      }t        |t        «      r|j	                  t
        «      r yt        |t        «      sŒst        j                  |«      sŒ‰ y y)zÆ
        Returns True if any MCP tool should be handled via the litellm proxy MCP gateway.
        This includes tools with server_url="litellm_proxy" as well as URLs ending in /mcp/<name>.
        ÚtypeÚmcpÚ
server_urlÚ TF)Ú
isinstanceÚdictrE   r3   Ú
startswithr9   r;   Úmatch)rH   ÚtoolrL   s      r7   Ú_should_use_litellm_mcp_gatewayz9LiteLLM_Proxy_MCP_Handler._should_use_litellm_mcp_gatewayX   s|   € ñ Øò $�Ü˜d¤DÕ)¨d¯h©h°vÓ.>À%Ó.GØ!%§¡¨,¸Ó!;�JÜ! *¬cÔ2°z×7LÑ7LÔMiÔ7jÙ#Ü! *¬cÕ2Ô7I×7OÑ7OÐPZÕ7[Ù#ð$ð r6   c                 ó  — g }g }| �r| D ]ü  }t        |t        «      rÙ|j                  d«      dk(  rÅ|j                  dd«      }t        |t        «      r'|j	                  t
        «      r|j                  |«       Œpt        |t        «      rZt        j                  |«      }|r1i |¥dt        › |j                  d«      › �i¥}|j                  |«       ŒÈ|j                  |«       ŒÚ|j                  |«       Œì|j                  |«       Œþ ||fS )z¬
        Parse tools and separate MCP tools with litellm_proxy from other tools.

        Returns:
            Tuple of (mcp_tools_with_litellm_proxy, other_tools)
        rJ   rK   rL   rM   é   )rN   rO   rE   r3   rP   r9   Úappendr;   rQ   r:   Úgroup)rH   Úmcp_tools_with_litellm_proxyÚother_toolsrR   rL   ÚmÚ	rewrittens          r7   Ú_parse_mcp_toolsz*LiteLLM_Proxy_MCP_Handler._parse_mcp_toolsh   s  € ð @BÐ$Ø(*ˆâØò -�Ü˜d¤DÔ)¨d¯h©h°vÓ.>À%Ò.GØ!%§¡¨,¸Ó!;�JÜ! *¬cÔ2°z×7LÑ7LÔMiÔ7jØ4×;Ñ;¸DÕAÜ# J´Ô4ô /×4Ñ4°ZÓ@˜Ùð)Ø"&ð)à ,Ô1TÐ0UÐVW×V]ÑV]Ð^_ÓV`ÐUaÐ.bñ)˜Ið 9×?Ñ?À	ÕJà'×.Ñ.¨tÕ4à#×*Ñ*¨4Õ0à×&Ñ& tÕ,ð)-ð, ,¨[Ð8Ð8r6   Úresolved_toolset_idsÚresolved_mcp_serversÚuser_api_key_authr)   c              ƒ   óh  K  — ddl m} 	 ddlm} |j	                  | ¬«      ƒ d{  –—† }t        t        |j                  «       «      t        |«      z  «      }|j                  }|�}t        |j                  xs i «      }|j                  «       D ]:  \  }	}
|j                  |	g «      }t        t        |«      t        |
«      z  «      ||	<   Œ< |j                  ||g dœ¬«      }n |d||¬	«      }|j                  d
|i¬«      S 7 ŒÜ# t        $ r"}t        j                   d|«       |cY d}~S d}~ww xY w­w)zPApply resolved toolset permissions to user_api_key_auth and return updated auth.r   )ÚLiteLLM_ObjectPermissionTable©Úglobal_mcp_server_manager)Útoolset_idsN)Úmcp_serversÚmcp_tool_permissionsÚmcp_toolsets©Úupdateztoolset-scope)Úobject_permission_idre   rf   Úobject_permissionz'Could not apply toolset permissions: %s)Úlitellm.proxy._typesra   Ú9litellm.proxy._experimental.mcp_server.mcp_server_managerrc   Ú resolve_toolset_tool_permissionsÚlistÚsetÚkeysrk   rO   rf   ÚitemsrE   Ú
model_copyÚ	Exceptionr   Údebug)r]   r^   r_   ra   rc   Útool_permissionsÚall_server_idsÚexisting_opÚmerged_tool_permsÚ	server_idÚ
tool_namesÚexisting_toolsÚ
updated_opÚ_es                 r7   Ú_apply_toolset_permissionsz4LiteLLM_Proxy_MCP_Handler._apply_toolset_permissionsŽ   sY  è ø€ õ 	Gð	%õð -F×,fÑ,fØ0ð -gó -÷ 'Ðô %)¬Ð-=×-BÑ-BÓ-DÓ)EÌÐL`ÓHaÑ)aÓ$bˆNØ!2×!DÑ!DˆKØÐ&Ü+/°×0PÑ0PÒ0VÐTVÓ+WÐ!Ø-=×-CÑ-CÓ-Eò _Ñ)�I˜zØ%6×%:Ñ%:¸9ÀbÓ%I�NÜ37¼¸NÓ8KÌcÐR\ËoÑ8]Ó3^Ð% iÒ0ð_ð )×3Ñ3à'5Ø0AØ(*ñð 4ó ‘
ñ ;Ø)8Ø .Ø)9ô�
ð
 %×/Ñ/Ð8KÈZÐ7XÐ/ÓYÐYð/'ùô0 ò 	%Ü× Ñ Ð!JÈBÔOØ$Õ$ûð	%üsE   ‚D2ŠD ¥D¦CD ÄD2ÄD Ä	D/ÄD*Ä$D/Ä%D2Ä*D/Ä/D2zUserAPIKeyAuth | NonerX   Úlitellm_trace_idÚmcp_auth_headerÚmcp_server_auth_headersÚrequest_tagsc           
   ƒ   óØ  K  — ddl m} ddlm}m} |xs dD �	�
cg c]_  }	t        |	t        «      r|	j                  dd«      nd}
t        |
t        «      r)|
j                  t        «      r|
j                  d«      d   ‘Œa }}	}
g }g }|D ]»  }|j                  |«      s—	 dd	lm} |�Ž|j                  ||«      ƒ d
{  –—† }|�r| �Tddlm}  || «      }|sD| j$                  }|rt'        |dd
«      nd
}|�|j(                  |vrt+        j,                  d|«       Œ�|j/                  |j(                  «       Œ«|j/                  |«       Œ½ |r"| � t2        j5                  ||| ¬«      ƒ d
{  –—† } |rd
n|xs d
} || |||dd||¬«      ƒ d
{  –—† }|j6                  }|j9                  | «      ƒ d
{  –—† }|j;                  |«      } |||¬«      ƒ d
{  –—† }|D ��cg c]A  }|�=t'        |dd
«      xs t'        |dd
«      xs t'        |dd
«      }t        |t        «      r|‘ŒC }}}||fS c c}
}	w 7 �Œr# t0        $ r"}t+        j,                  d||«       Y d
}~�Œ"d
}~ww xY w7 Œ÷7 Œ×7 Œ´7 Œ“c c}}w ­w)a  
        Get available tools from the MCP server manager.

        Args:
            user_api_key_auth: User authentication info for access control
            mcp_tools_with_litellm_proxy: ToolParam objects with server_url starting with "litellm_proxy"
            mcp_auth_header: Optional deprecated auth header for MCP servers
            mcp_server_auth_headers: Optional server-specific auth headers (e.g. from x-mcp-{alias}-*)

        Returns:
            List of MCP tools
            List names of allowed MCP servers
        r   rb   )Ú._get_allowed_mcp_servers_from_mcp_server_namesÚ_get_tools_from_mcp_serversr5   rL   rM   ú/éÿÿÿÿ)Úprisma_clientN)Ú_user_has_admin_viewrg   z3Key does not have access to toolset '%s', skipping.z%Could not resolve '%s' as toolset: %s)r]   r^   r_   TÚ	responses)r_   r�   re   r‚   Úlog_list_tools_to_spendlogsÚlist_tools_log_sourcer€   rƒ   )re   Úallowed_mcp_serversÚserver_nameÚaliasr/   )rm   rc   Ú-litellm.proxy._experimental.mcp_server.serverr…   r†   rN   rO   rE   r3   rP   r:   ÚsplitÚget_mcp_server_by_nameÚlitellm.proxy.proxy_serverr‰   Úget_toolset_by_name_cachedÚ/litellm.proxy.management_endpoints.common_utilsrŠ   rk   ÚgetattrÚ
toolset_idr   ru   rV   rt   r=   r   rH   Úget_allowed_mcp_serversÚget_mcp_servers_from_ids)r_   rX   r€   r�   r‚   rƒ   rc   r…   r†   Ú_toolrL   re   r^   r]   r/   r‰   ÚtoolsetrŠ   Úis_adminÚopÚgrantedr~   Úeffective_server_filterÚlistingrH   Úallowed_mcp_server_idsrŽ   Úserverr�   Úserver_namess                                 r7   Ú_get_mcp_tools_from_managerz5LiteLLM_Proxy_MCP_Handler._get_mcp_tools_from_manager¸   sÚ  è ø€ õ,	
÷	
ð 7Ò<¸"÷
àÜ>HÈÔPTÔ>U˜uŸy™y¨°rÔ:Ð[]�
Ü˜*¤cÔ*¨z×/DÑ/DÔEhÔ/ið ×Ñ˜SÓ! "Ó%ð
ˆñ 
ð 24ÐØ13ÐØò 	.ˆDØ,×CÑCÀDÔIð\ÝHà$Ð0Ø(A×(\Ñ(\Ð]jÐlpÓ(q×"q˜Ø"Ð.à0Ð<õ!"ñ ,@Ð@QÓ+R Ù'/Ø):×)LÑ)L BÙSU¬g°b¸.È$Ô.OÐ[_ Gð (/ ¸'×:LÑ:LÐT[Ñ:[Ü(6×(<Ñ(<Ø,aÐcgô)*ð )1Ø0×7Ñ7¸×8JÑ8JÔKð %ð !×'Ñ'¨Õ-ð?	.ñD  Ð$5Ð$AÜ&?×&ZÑ&ZØ%9Ø%9Ø"3ð '[ó '÷ !Ðñ 2F©ÐL`ÒLhÐdhÐá:Ø/Ø+Ø/Ø$;Ø(,Ø"-Ø-Ø%ô	 
÷ 	
ˆð —}‘}ˆà.G×._Ñ._Ð`qÓ.r×(rÐØ7×PÑPÐQgÓhÐá$RØ/Ø 3ô%
÷ 
Ðð .÷
àØÐ!ä˜ ¨tÓ4Òw¼ÀÈÐQUÓ8VÒwÔZaÐbhÐjpÐrvÓZwð ô ˜+¤sÔ+ò ð
ˆñ 
ð �lÐ"Ð"ùós
ð$ #rúô. !ò \Ü"×(Ñ(Ð)PÐRVÐXZ×[Ò[ûð\úð!øð	
øð )søð
úó

ùs¯   ‚I*šA$H%Á>I*ÂH.Â9H+Â:AH.ÄI*ÄH.Ä13I*Å$IÅ%!I*ÆIÆ$I*Æ+I Æ,"I*ÇI"Ç	I*ÇAI$ÈI*È+H.È.	IÈ7IÉI*ÉIÉI*ÉI*É I*É"I*É$I*Ú	mcp_toolsrŽ   c                 ó6  — t        «       }g }i }| D ]ƒ  }t        |t        «      r|j                  d«      }nt	        |dd«      }|sŒ5||vsŒ:|j                  |«       |j                  |«       t        |«      dk(  r	|d   ||<   Œst        |«      \  }||<   Œ… ||fS )a7  
        Deduplicate MCP tools by name, keeping the first occurrence of each tool.

        Args:
            mcp_tools: List of MCP tools that may contain duplicates

        Returns:
            List of deduplicated MCP tools
            The returned dictionary maps each tool_name to the server_name
        r/   NrU   r   )	rp   rN   rO   rE   r—   ÚaddrV   Úlenr   )r¦   rŽ   Ú
seen_namesÚdeduplicated_toolsÚtool_server_maprR   Ú	tool_nameÚ_s           r7   Ú_deduplicate_mcp_toolsz0LiteLLM_Proxy_MCP_Handler._deduplicate_mcp_tools1  s°   € ô '*£eˆ
Ø35ÐØ13ˆàò 	]ˆDÜ˜$¤Ô%Ø ŸH™H VÓ,‘	ä# D¨&°$Ó7�	â˜Y¨jÒ8Ø—‘˜yÔ)Ø"×)Ñ)¨$Ô/ÜÐ*Ó+¨qÒ0Ø1DÀQÑ1G�O IÒ.ä4QÐR[Ó4\Ñ1�A� yÒ1ð	]ð " ?Ð2Ð2r6   c           	      óz  — t        «       }|D ]L  }t        |t        «      sŒd|v sŒ|j                  dg «      }t        |t        «      sŒ<|j                  |«       ŒN |s| S | D ��cg c]H  }t        |t        «      r|j                  d«      nt        |dd«      }|r||v st        |«      d   |v r|‘ŒJ }}}|S c c}}w )zQFilter MCP tools based on allowed_tools parameter from the original tool configs.Úallowed_toolsr/   Nr   )rp   rN   rO   rE   ro   ri   r—   r   )r¦   rX   Úallowed_tool_namesÚtool_configr±   Úmcp_toolr­   Úfiltered_toolss           r7   Ú"_filter_mcp_tools_by_allowed_toolsz<LiteLLM_Proxy_MCP_Handler._filter_mcp_tools_by_allowed_toolsS  sÒ   € ô /2«eÐØ7ò 	=ˆKÜ˜+¤tÕ,°ÀKÒ1OØ +§¡°ÀÓ D�Ü˜m¬TÕ2Ø&×-Ñ-¨mÕ<ð		=ñ "ØÐð
 &÷!
àÜ6@ÀÌ4Ô6P˜hŸl™l¨6Ô2ÔV]Ð^fÐhnÐptÓVu�	ÙØÐ0Ñ0Ô4QÐR[Ó4\Ð]^Ñ4_ÐcuÑ4uò	 ð!
ˆñ !
ð Ðùó!
s   Á%AB7c              ƒ   óˆ   K  — t         j                  | |||¬«      ƒ d{  –—† \  }}t         j                  |«      }||fS 7 Œ ­w)a(  
        Centralized method to process MCP tools through the complete pipeline.

        Args:
            user_api_key_auth: User authentication info for access control
            mcp_tools_with_litellm_proxy: ToolParam objects with server_url starting with "litellm_proxy"
            litellm_trace_id: Optional trace ID for linking list_mcp_tools spend logs to parent request

        Returns:
            List of tools in OpenAI format ready to be sent to the LLM
            The returned dictionary maps each tool_name to the server_name
        )r€   rƒ   N)r=   Ú+_process_mcp_tools_without_openai_transformÚ_transform_mcp_tools_to_openai)r_   rX   r€   rƒ   Údeduplicated_mcp_toolsr¬   Úopenai_toolss          r7   Ú#_process_mcp_tools_to_openai_formatz=LiteLLM_Proxy_MCP_Handler._process_mcp_tools_to_openai_formato  s[   è ø€ ô, ,×WÑWØØ(Ø-Ø%ð	 Xó 
÷ 
ñ	
Ø"Øô 8×VÑVÐWmÓnˆà˜_Ð,Ð,ð
ús   ‚AŸA  !Ac              ƒ   óÒ   K  — |sg i fS | }t         j                  ||||||¬«      ƒ d{  –—† \  }}t         j                  ||¬«      }	t         j                  |	|«      \  }
}|
|fS 7 Œ;­w)a«  
        Process MCP tools through filtering and deduplication pipeline without OpenAI transformation.
        This is useful for cases where we need the original MCP tool objects (e.g., for events).

        Args:
            user_api_key_auth: User authentication info for access control
            mcp_tools_with_litellm_proxy: ToolParam objects with server_url starting with "litellm_proxy"
            mcp_auth_header: Optional deprecated auth header for MCP servers
            mcp_server_auth_headers: Optional server-specific auth headers (e.g. from x-mcp-{alias}-*)

        Returns:
            List of filtered and deduplicated MCP tools in their original format
        )r_   rX   r€   r�   r‚   rƒ   N)r¦   rX   )r=   r¥   r¶   r¯   )r_   rX   r€   r�   r‚   rƒ   Útyped_user_api_key_authÚmcp_tools_fetchedrŽ   Úfiltered_mcp_toolsrº   r¬   s               r7   r¸   zELiteLLM_Proxy_MCP_Handler._process_mcp_tools_without_openai_transform�  s¢   è ø€ ñ, ,Ø�r�6ˆMà@QÐô ,×GÑGØ5Ø)EØ-Ø+Ø$;Ø%ð Hó 
÷ 
ñ	
ØØô %>×$`Ñ$`Ø'Ø)Eð %aó %
Ðô &×<Ñ<Ð=OÐQdÓeñ	
Ø"Øð & Ð6Ð6ð+
ús   ‚'A'©A%ª<A'Útarget_formatr‹   c                  ó   — y ©Nr5   ©r¦   rÁ   s     r7   r¹   z8LiteLLM_Proxy_MCP_Handler._transform_mcp_tools_to_openaiÆ  s   € ð
 #&r6   Úchatc                  ó   — y rÃ   r5   rÄ   s     r7   r¹   z8LiteLLM_Proxy_MCP_Handler._transform_mcp_tools_to_openaiÍ  s   € ð
 ),r6   )r‹   rÅ   c                 ód   — ddl m}m} | D �cg c]  }|dk(  r ||«      n ||«      ‘Œ }}|S c c}w )z0Transform MCP tools to OpenAI-compatible format.r   )Ú/transform_mcp_tool_to_openai_responses_api_toolÚ!transform_mcp_tool_to_openai_toolrÅ   )Ú%litellm.experimental_mcp_client.toolsrÈ   rÉ   )r¦   rÁ   rÈ   rÉ   r´   r»   s         r7   r¹   z8LiteLLM_Proxy_MCP_Handler._transform_mcp_tools_to_openaiÔ  sR   € ÷	
ð &ö	
ð ð  Ò&ñ .¨hÔ7á@ÀÓJñKð
ˆð 
ð Ðùò
s   �-c                 ó    — t        | xs g «      }|sy|D ]7  }t        |t        «      r|j                  d«      nt	        |dd«      }|dk7  sŒ7 y y)af  Check if we should auto-execute tool calls.

        Auto-execution requires EVERY MCP reference to opt in with
        ``require_approval="never"``. A single reference that requires approval
        ("always", "manual", the object form, or an unset value) disables
        auto-execution for the whole request. This fails closed: when an
        approval-required reference shares a request with a "never" one, the
        model's tool calls are returned to the caller instead of being run, so
        an approval-gated tool can never be invoked without approval. Returns
        False for an empty list.
        FÚrequire_approvalNÚneverT)ro   rN   rO   rE   r—   )rX   Ú
referencesrR   Úapprovals       r7   Ú_should_auto_execute_toolsz4LiteLLM_Proxy_MCP_Handler._should_auto_execute_toolsè  sd   € ô !Ð!=Ò!CÀÓDˆ
ÙØØò 	ˆDä0:¸4ÄÔ0F�—‘Ð+Ô,ÌGÐTXÐZlÐnrÓLsð ð ˜7Ó"Ùð	ð r6   Úresponsec                 óô   — g }| j                   D ]f  }t        |t        «      r&|j                  d«      dk(  r|j	                  |«       Œ9t        |d«      sŒFt        |d«      dk(  sŒV|j	                  |«       Œh |S )z,Extract tool calls from the response output.rJ   Úfunction_call)ÚoutputrN   rO   rE   rV   Úhasattrr—   )rÑ   Ú
tool_callsÚoutput_items      r7   Ú!_extract_tool_calls_from_responsez;LiteLLM_Proxy_MCP_Handler._extract_tool_calls_from_response  ss   € ð +-ˆ
Ø#Ÿ?™?ò 	/ˆKä˜+¤tÔ,°·±ÀÓ1HÈOÒ1[Ø×!Ñ! +Õ.Ü˜ fÕ-´'¸+ÀvÓ2NÐRaÓ2aà×!Ñ! +Õ.ð	/ð Ðr6   c                 óB  — g }	 | j                   D ]f  }t        |dd«      }|€Œt        |dd«      }|sŒ#|D ]?  }t        |d«      r |j                  |j	                  «       «       Œ/|j                  |«       ŒA Œh 	 |S # t
        $ r t        j                  d«       Y |S w xY w)z3Extract tool calls from a chat completion response.ÚmessageNrÖ   Ú
model_dumpz:Failed to extract tool calls from chat completion response)Úchoicesr—   rÕ   rV   rÛ   rt   r   Ú	exception)rÑ   rÖ   ÚchoicerÚ   Útool_call_entriesÚ	tool_calls         r7   Ú&_extract_tool_calls_from_chat_responsez@LiteLLM_Proxy_MCP_Handler._extract_tool_calls_from_chat_response  sÀ   € ð +-ˆ
ð	cØ"×*Ñ*ò 9�Ü*1°&¸)ÀTÓ*J�Ø�?Øô ˜G \°4Ó8ð "ò %Ø%6ò 9˜	Ü" 9¨lÔ;Ø&×-Ñ-¨i×.BÑ.BÓ.DÕEà&×-Ñ-¨iÕ8ñ	9ñ9ð  Ðøô ò 	cÜ×$Ñ$Ð%aÕbàÐð	cús   „.A< ³AA< Á<BÂBrà   c                 óF  — t        | t        «      rž| j                  d«      xs | j                  d«      }| j                  d«      }t        |t        «      r#|j                  d«      }|j                  d«      }n¥| j                  d«      }| j                  d«      }|€�| j                  d«      }not        | dd«      xs t        | dd«      }t        | dd«      }|�t        |dd«      }t        |dd«      }n)t        | dd«      }t        | dd«      }|€t        | dd«      }|||fS )z;Extract tool name, arguments, and call_id from a tool call.Úcall_idÚidÚfunctionr/   Ú	argumentsNÚinput)rN   rO   rE   r—   )rà   r-   Úfunction_blockr­   Útool_argumentsÚfunction_objs         r7   Ú_extract_tool_call_detailsz4LiteLLM_Proxy_MCP_Handler._extract_tool_call_details(  s  € ô
 �i¤Ô&Ø$Ÿ=™=¨Ó3ÒJ°y·}±}ÀTÓ7JˆLð %.§M¡M°*Ó$=ˆNÜ˜.¬$Ô/Ø*×.Ñ.¨vÓ6�	Ø!/×!3Ñ!3°KÓ!@‘à%ŸM™M¨&Ó1�	à!*§¡¨{Ó!;�Ø!Ð)Ø%.§]¡]°7Ó%;‘Nä" 9¨i¸Ó>Ò`Ä'È)ÐUYÐ[_ÓB`ˆLä*1°)¸ZÈÓ*NˆLØÐ'Ü# L°&¸$Ó?�	Ü!(¨°{ÀDÓ!I‘ä# I¨v°tÓ<�	Ü!(¨°KÀÓ!F�Ø!Ð)Ü%,¨Y¸ÀÓ%F�Nà˜.¨,Ð6Ð6r6   ré   c                 óˆ   — ddl }t        | t        «      r	 |j                  | «      S | xs i S # |j                  $ r i cY S w xY w)z<Parse tool arguments, handling both string and dict formats.r   N)ÚjsonrN   r3   ÚloadsÚJSONDecodeError)ré   rí   s     r7   Ú_parse_tool_argumentsz/LiteLLM_Proxy_MCP_Handler._parse_tool_argumentsJ  sN   € ó 	ä�n¤cÔ*ðØ—z‘z .Ó1Ð1ð "Ò' RÐ'øð ×'Ñ'ò Ø’	ðús   –- ­AÁ Ar.   r'   c                 ó(  — | rt        | d«      r| j                  sy	 ddlm}m}m} | j                  D �cg c]$  }t        ||«      sŒt        |j                  «      ‘Œ& }}| j                  D �cg c]?  }t        ||«      s1t        ||«      rdn"t        ||«      rdnt        |«      j                  ‘ŒA }}|rdj                  |«      nd}|r*d	d
j                  |«      › d�}|› d|› �j                  «       }|xs dS # t        $ r Y yw xY wc c}w c c}w )z:Parse MCP tool call result and extract meaningful content.ÚcontentzTool executed successfullyr   )ÚEmbeddedResourceÚImageContentÚTextContentÚImageró   ú rM   z[Generated z, ú])rÕ   rò   Ú	mcp.typesró   rô   rõ   ÚImportErrorrN   r3   ÚtextrJ   r0   ÚjoinÚstrip)	r.   ró   rô   rõ   Úcontent_itemÚ
text_partsÚother_content_typesÚresult_textÚ
other_infos	            r7   Ú_parse_mcp_resultz+LiteLLM_Proxy_MCP_Handler._parse_mcp_resultW  s/  € ñ œW V¨YÔ7¸v¿~º~Ø/ð	0ßMÑMð 8>·~±~ö
Ø'3ÌÐT`ÐbmÕInŒC�×!Ñ!Õ"ð
ˆ
ð 
ð !'§¡ö&
ð Ü˜l¨KÔ8ô ˜,¨Ô5ñ ô ˜,Ð(8Ô9ñ $ä�lÓ#×,Ñ,ñ	-ð&
Ðð &
ñ /9�c—h‘h˜zÔ*¸bˆñ Ø"-¨d¯i©iÐ8KÓ.LÐ-MÈQÐ OˆJØ(˜M¨¨:¨,Ð7×=Ñ=Ó?ˆKàÒ:Ð:Ð:øô3 ò 	0á/ð	0üò
ùò&
s#   �
C; µD
ÁD
Á.ADÃ;	DÄDr¬   rÖ   Úoauth2_headersÚraw_headersÚlitellm_call_idc
              ƒ   óô  K  — ddl m}
 ddlm} ddlm}m} ddlm} ddl	m
} ddlm} g }d}t        «       }t        |«      }|}|D �](  }i }d}	 t        j!                  |«      \  }}}|st#        j$                  d	|«       Œ;t        j'                  |«      }ddlm} | |   }|j)                  |«      xs |j+                  |«      }|r
 |||g«      n|}t-        ||«      }t/        j0                  «       }d
||dœdœg} |xs t3        |j5                  «       «      }!||||dœ}"d|› �|"| t6        j8                  j:                  |!dd|||dœdœdœ}|r||d<   |	r|	|"d<   |�=ddlm}# |#jA                  ||d¬«       tC        |dd«      xs tC        |dd«      }$|$r|$|d<   d}%	 tE        dDd||dœ|¤Ž\  }%}&|%|d<   ||d <   |%r	 |%jK                  | d!¬"«       |||d$œ}(|rg|jN                  xs i })|)jQ                  d%«      xs tC        |d%d«      xs ||(d&<   |)jQ                  d'«      }*|*r|*|(d(<   |)jQ                  d)«      }+|+r|+|(d)<   |%r8|(|%jR                  d*<   d|› �|%_*        t6        j8                  j:                  |%_+        |jY                  ||||||||||%¬+«
      ƒ d{  –—† },|r,|j[                  |,|%r|%jR                  nd,|i|¬-«      ƒ d{  –—† },|%r{	 |%j]                  |,¬.«       |%j_                  |%jR                  |,|t/        j0                  «       ¬/«      ƒ d{  –—†  	 |%ja                  |,|t/        j0                  «       ¬1«      ƒ d{  –—†  t        jc                  |,«      }-|je                  ||-|d3œ«       �Œ+ |S # tF        $ r$}'t#        jH                  d||'«       d}%Y d}'~'�Œîd}'~'ww xY w# tF        $ r t#        jL                  d#«       Y �Œ÷w xY w7 �Œ47 �Œ	7 Œ½# tF        $ r t#        jL                  d0|«       Y ŒÜw xY w7 Œµ# tF        $ r t#        jL                  d2|«       Y ŒÔw xY w# |$ ry}.t        jg                  ||||.¬4«      ƒ d{  –—†7   t#        jh                  d5|.«       d6tC        |.d7d8«      › d9tC        |.d:d8«      › d;|.› �}/|je                  ||/|d3œ«       Y d}.~.�ŒPd}.~.w|$ rk}.t        jg                  ||||.¬4«      ƒ d{  –—†7   t#        jh                  d<|.«       d=tC        |.d:d8«      › d>|.› �}/|je                  ||/|d3œ«       Y d}.~.�Œ¾d}.~.w|
$ r‡}.t        jg                  ||||.¬4«      ƒ d{  –—†7   t#        jh                  d?|.«       d@tk        |.dA«      rt3        |.jl                  «      n
t3        |.«      › �}/|je                  ||/|d3œ«       Y d}.~.�ŒHd}.~.wtF        $ r[}.t        jg                  ||||.¬4«      ƒ d{  –—†7   t#        jL                  dB|.«       |je                  |dC|.› �|d3œ«       Y d}.~.�Œªd}.~.ww xY w­w)Ez&Execute tool calls and return results.r   )ÚHTTPException©Úuuid)ÚBlockedPiiEntityErrorÚGuardrailRaisedExceptionrb   )Ú!_resolve_display_name_to_original)Úproxy_logging_objNzTool call missing name: %srR   )r­   ræ   )Úrolerò   )r-   r­   r�   ÚheaderszMCP: z/mcp/tools/callÚPOST)r/   ræ   )ÚurlÚmethodr  Úbody)ÚmodelÚmetadatarç   Ú	call_typer  rC   r€   Útags)ÚLiteLLMProxyRequestSetupr  )ÚdataÚuser_api_key_dictÚ_metadata_variable_nameÚend_user_idÚuser_idÚuserÚcall_mcp_tool)Úoriginal_functionÚ	rules_objÚ
start_timez5Failed to initialize logging for MCP tool call %s: %sÚlitellm_logging_objræ   rM   )rç   Úapi_keyz+Failed to run pre_call for MCP tool logging)r/   ræ   Únamespaced_tool_namer�   Úmcp_server_nameÚlogo_urlÚmcp_server_logo_urlÚmcp_server_cost_infoÚmcp_tool_call_metadata)
r�   r/   ræ   r_   r�   r‚   r  r  r  r$  Úmcp_tool_name)rÑ   Úrequest_datar  )Úoriginal_response)r>   Úresponse_objr#  Úend_timez4Failed to run post-call logging for MCP tool call %s)r.   r#  r0  z*Failed to log MCP tool call success for %s)r-   r.   r/   )r  r_   r-  Úerrorz*BlockedPiiEntityError in MCP tool call: %szTool call blocked: PII entity 'Úentity_typeÚunknownz' detected by guardrail 'Úguardrail_namez'. z-GuardrailRaisedException in MCP tool call: %szTool call blocked: Guardrail 'z' violation. z"HTTPException in MCP tool call: %szTool call failed: Údetailz!Error executing MCP tool call: %szError executing tool: r5   )7Úfastapir  Úlitellm._uuidr
  Úlitellm.exceptionsr  r  rm   rc   r‘   r  r”   r  r%   r   r=   rë   r   Úwarningrð   r“   Ú_get_mcp_server_from_tool_namer   r   Únowr3   Úuuid4r   r   ÚvalueÚ$litellm.proxy.litellm_pre_call_utilsr  Ú)add_user_api_key_auth_to_request_metadatar—   r&   rt   ru   Úpre_callrÝ   Úmcp_inforE   Úmodel_call_detailsr  r  Ú	call_toolÚpost_mcp_call_hookÚ	post_callÚasync_post_mcp_tool_call_hookÚasync_success_handlerr  rV   Ú_log_mcp_tool_failurer1  rÕ   r5  )0r¬   rÖ   r_   r�   r‚   r  r  r  r€   rƒ   r  r
  r  r  rc   r  r  Útool_resultsr-   r"  Úlogging_safe_headersr¾   rà   Úlogging_request_datar­   ré   Úparsed_argumentsr�   Ú
mcp_serverÚresolved_tool_nameÚsanitized_tool_namer#  Úlogging_inputÚtool_logging_call_idÚlogging_metadatar  Úuser_identifierr$  r®   Úlogging_errorÚstandard_logging_mcp_tool_callrA  r(  Ú	cost_infor.   r  ÚeÚerror_messages0                                                   r7   Ú_execute_tool_callsz-LiteLLM_Proxy_MCP_Handler._execute_tool_calls{  s²  è ø€ õ 	*å&ßVõ	
õ	
õ 	Aà35ˆØ#'ˆÜ ›7ˆ	Ü&>¸{Ó&KÐØ@QÐØ#ó {	ˆIØ68Ð Ø$(ˆIðxô
 .×HÑHÈÓSñ	ØØ"Ø ñ !Ü"×*Ñ*Ð+GÈÔSØä#<×#RÑ#RÐSaÓ#bÐ õ Ià-¨iÑ8�à6×MÑMØóò Yà.×MÑMÈiÓXð ñ S]Ñ5°iÀ*ÀÔNÐbkð #ô '@Ð@RÐT^Ó&_Ð#ä%Ÿ\™\›^�
ð !'à)<Ø)9ñ$ñðA�ð (7Ò'K¼#¸d¿j¹j»lÓ:KÐ$à$0Ø!4Ø#.Ø3ñ	7Ð ð  % Y KÐ0Ø 0Ø*Ü!*×!8Ñ!8×!>Ñ!>Ø';ð  1Ø"(Ø#7à$7Ø)9ñ!ñ	-ñ(Ð$ñ" $Ø?OÐ(Ð);Ñ<ÙØ/;Ð$ VÑ,Ø*Ð6õð -×VÑVØ1Ø*AØ0:ð Wô ô
 '.Ð.EÀ}ÐVZÓ&[ò 'Ô_fØ/°¸Dó`�Oñ 'Ø7FÐ,¨VÑ4à@DÐ#ð/Ü-;ð .Ø*9Ø"+Ø#-ñ.ð /ñ	.Ñ*Ð'¨ð ?RÐ$Ð%:Ñ;Ø4DÐ$ [Ñ1á&ð`Ø+×4Ñ4Ø"/Ø$&ð 5ô ð 0Ø!1Ø,5ñNÐ.ñ
 Ø)×2Ñ2Ò8°b�Hà Ÿ™ ]Ó3Òn´w¸zÈ=ÐZ^Ó7_ÒnÐcnð 3Ð3DÑEð  (Ÿ|™|¨JÓ7�HÙØPXÐ6Ð7LÑMØ (§¡Ð-CÓ D�IÙ ØQZÐ6Ð7MÑNá&ØWuÐ'×:Ñ:Ð;SÑTØ27¸	°{Ð0CÐ'Ô-Ü4=×4KÑ4K×4QÑ4QÐ'Ô1à8×BÑBØ +Ø,Ø.Ø&=Ø$3Ø,CØ#1Ø +Ø&7Ø(;ð  Có  ÷ �ñ %Ø#4×#GÑ#GØ!'ñ  3ð 0×BÒBà"1°9Ð!=à*Að $Hó $÷ �Fñ 'ð	tØ+×5Ñ5ÈÐ5ÔOØ1×OÑOØ#6×#IÑ#IØ)/Ø'1Ü%-§\¡\£^ð	 Pó ÷ ð ðjØ1×GÑGØ#)Ø'1Ü%-§\¡\£^ð Hó ÷ ð ô 8×IÑIÈ&ÓQ�Ø×#Ñ#à(4Ø"-Ø )ñöðg{	ðz ÐøôE !ò /Ü"×(Ñ(ØOØ!Ø%ôð
 +/Ö'ûð/ûô" %ò `Ü&×0Ñ0Ð1^×_ð`úð2ùðùðùô %ò tÜ&×0Ñ0Ð1gÐirÖsðtúðùô
 %ò jÜ&×0Ñ0Ð1]Ð_hÖiðjûð )ò Ü/×EÑEØ&7Ø&=Ø!5Øð	 Fó ÷ ñ ô ×$Ñ$Ð%QÐSTÔUØ"AÄ'È!È]Ð\eÓBfÐAgð  hAô  BIð  JKð  M]ð  _hó  Bið  Ajð  jmð  noð  mpð  !q�Ø×#Ñ#à(4Ø"/Ø )ñ÷ò ûð ,ò Ü/×EÑEØ&7Ø&=Ø!5Øð	 Fó ÷ ñ ô ×$Ñ$Ð%TÐVWÔXà4´W¸QÐ@PÐR[Ó5\Ð4]Ð]jÐklÐjmÐnð ð ×#Ñ#à(4Ø"/Ø )ñ÷ò ûð !ò Ü/×EÑEØ&7Ø&=Ø!5Øð	 Fó ÷ ñ ô ×$Ñ$Ð%IÈ1ÔMØ"4ÄgÈaÐQYÔFZ´S¸¿¹´]Ô`cÐdeÓ`fÐ4gÐ h�Ø×#Ñ#à(4Ø"/Ø )ñ÷ò ûô ò Ü/×EÑEØ&7Ø&=Ø!5Øð	 Fó ÷ ñ ô ×(Ñ(Ð)LÈaÔPØ×#Ñ#à(4Ø$:¸1¸#Ð">Ø )ñ÷ò ûðüsz  ‚AW8Á1PÂ W8ÂDPÆM4Æ.PÆ;N$ÇCPÊO	Ê-PËOËPËAOÌOÌOÌ)O8Í O6ÍO8Í*PÍ/W8Í4	N!Í=NÎPÎN!Î!PÎ$OÏPÏOÏPÏPÏOÏO3Ï0PÏ2O3Ï3PÏ6O8Ï8PÐPÐPÐPÐW5Ð"RÐ>QÐ?ARÒW8ÒW5ÒTÒ:R=Ò;ATÓ>W8ÔW5ÔVÔ(T+Ô)AVÖW8ÖW5ÖW0Ö6V9Ö73W0×*W8×0W5×5W8Úoriginal_messagesrI  c           
      ó^  — ddl m} ddlm}  | || «      «      }|sg }d}	 |j                  d   }t        |t        «      rjt        |dd«      r]|j                  j                  d¬«      }|j                  d«      r0|d   D ](  }t        |t        «      sŒd	|v sŒd
|d	   vsŒ!d|d	   d
<   Œ* |r|j                  |«       |D ]F  }	|j                  d|	j                  d«      |	j                  d«      |	j                  dd«      dœ«       ŒH |S # t        $ r t        j                  d«       Y Œ€w xY w)zCCreate follow-up chat messages that include tool execution results.r   )Údeepcopy)Úconvert_list_message_to_dictNrÚ   T)Úexclude_nonerÖ   rå   ræ   ú{}z0Failed to convert assistant message for MCP flowrR   r-   r/   r.   rM   )r  r-   r/   rò   )Úcopyr\  Úlitellm.utilsr]  rÜ   rN   r!   r—   rÚ   rÛ   rE   rO   rt   r   rÝ   rV   )
rZ  rÑ   rI  r\  r]  Úfollow_up_messagesÚmessage_to_appendÚfirst_choicerà   Útool_results
             r7   Ú#_create_follow_up_messages_for_chatz=LiteLLM_Proxy_MCP_Handler._create_follow_up_messages_for_chat™  sL  € õ 	"å>á6RÑS[Ð\mÓSnÓ6oÐá!Ø!#Ðà)-Ðð	YØ"*×"2Ñ"2°1Ñ"5ˆLÜ˜,¬Ô0´W¸\È9ÐVZÔ5[Ø$0×$8Ñ$8×$CÑ$CÐQUÐ$CÓ$VÐ!à$×(Ñ(¨Ô6Ø%6°|Ñ%Dò J˜	Ü% i´Õ6¸:ÈÒ;RØ*°)¸JÑ2GÒGØEI 	¨*Ñ 5°kÒ BðJñ Ø×%Ñ%Ð&7Ô8à'ò 	ˆKØ×%Ñ%à"Ø$/§O¡O°NÓ$CØ'ŸO™O¨FÓ3Ø*Ÿ™¨x¸Ó<ñ	õð	ð "Ð!øô! ò 	YÜ×$Ñ$Ð%WÖXð	Yús$   ¢A1D ÂD ÂD Â!
D ÄD,Ä+D,Úoriginal_inputc                 ó®  — g }|rYt        |t        «      r|j                  dd|dœ«       n3t        |t        «      r|j	                  |«       n|j                  |«       g }g }| j
                  D �]  }t        |t        «      st        |d«      r|j                  «       }t        |t        «      sŒA|j                  d«      dk(  rc|j                  d«      xs |j                  d«      }|j                  d	«      }|j                  d
«      }	|sŒž|sŒ¡|j                  d|||	dœ«       Œ¸|j                  d«      dk(  sŒÍ|j                  dg «      }
t        |
t        «      r|j	                  |
«       �Œ|j                  |
«       �Œ |r|j                  dd|dœ«       |D ]  }|j                  |«       Œ |D ]  }|j                  d|d   |d   dœ«       Œ |S )z:Create follow-up input with tool results in proper format.rÚ   r  )rJ   r  rò   rÛ   rJ   rÓ   rã   rä   r/   ræ   )rJ   rã   r/   ræ   rò   Ú	assistantÚfunction_call_outputr-   r.   )rJ   rã   rÔ   )
rN   r3   rV   ro   ÚextendrÔ   rO   rÕ   rÛ   rE   )rÑ   rI  rg  Úfollow_up_inputÚassistant_message_contentÚfunction_callsr×   rã   r/   ræ   rò   rÓ   re  s                r7   Ú_create_follow_up_inputz1LiteLLM_Proxy_MCP_Handler._create_follow_up_inputÆ  sØ  € ð 02ˆñ Ü˜.¬#Ô.Ø×&Ñ&°	À6ÐVdÑ'eÕfÜ˜N¬DÔ1Ø×&Ñ& ~Õ6à×&Ñ& ~Ô6ð :<Ð!Ø9;ˆà#Ÿ?™?ó 	BˆKÜ˜k¬4Ô0´W¸[È,Ô5WØ)×4Ñ4Ó6�ä˜+¤tÕ,Ø—?‘? 6Ó*¨oÒ=Ø)Ÿo™o¨iÓ8ÒQ¸K¿O¹OÈDÓ<Q�GØ&Ÿ?™?¨6Ó2�DØ +§¡°Ó <�Iò ¢4Ø&×-Ñ-à(7Ø+2Ø(,Ø-6ñ	õð !—_‘_ VÓ,°	Ó9à)Ÿo™o¨i¸Ó<�GÜ! '¬4Ô0Ø1×8Ñ8¸ÖAà1×8Ñ8¸ÖAð5	Bñ> %Ø×"Ñ"à%Ø'Ø8ñôð ,ò 	2ˆMØ×"Ñ" =Õ1ð	2ð (ò 	ˆKØ×"Ñ"à2Ø*¨>Ñ:Ø)¨(Ñ3ñõð	ð Ðr6   rl  r  Ú	all_toolsÚresponse_idÚcall_paramsc              ‹   ó>   K  — t        d| |||dœ|¤Žƒ d{  –—† S 7 Œ­w)z3Make follow-up response API call with tool results.)rç   r  rH   Úprevious_response_idNr5   r   )rl  r  rp  rq  rr  s        r7   Ú_make_follow_up_callz.LiteLLM_Proxy_MCP_Handler._make_follow_up_call  s:   è ø€ ô  ð 
Ø!ØØØ!,ñ	
ð
 ñ
÷ 
ð 	
ð 
ús   ‚–—r  r*   r-  r1  c              ƒ   óÔ   K  — | �|€y	 t        j                  t        ¬«      }| j                  |||d|¬«      ƒ d{  –—†  y7 Œ# t        $ r t        j                  d«       Y yw xY w­w)z.Log MCP tool failures via proxy logging hooks.N)Úlimitz/responses/mcp/call_tool)r-  Úoriginal_exceptionr  ÚrouteÚtraceback_strz#Failed to log MCP tool call failure)Ú	tracebackÚ
format_excr   Úpost_call_failure_hookrt   r   rÝ   )r  r_   r-  r1  rz  s        r7   rH  z/LiteLLM_Proxy_MCP_Handler._log_mcp_tool_failure%  s{   è ø€ ð Ð$Ð(9Ð(AØð
	LÜ#,×#7Ñ#7Ô>\Ô#]ˆMØ#×:Ñ:Ø)Ø#(Ø"3Ø0Ø+ð ;ó ÷ ò ùô ò 	LÜ×$Ñ$Ð%JÖKð	Lüs8   ‚A(‰3A ¼A½A ÁA(ÁA ÁA%Á"A(Á$A%Á%A(rç   Úmcp_discovery_eventsrt  c           
      óÄ   — ddl m}	 t        j                  d| ||||dœ|¤Ž}
 |	d||||j	                  d«      xs! |j	                  di «      j	                  d«      |
¬«      S )	a,  
        Create MCP enhanced streaming response that handles the full MCP workflow.

        This creates a streaming iterator that:
        1. Immediately emits MCP discovery events
        2. Makes the LLM call and streams the response
        3. Handles tool execution and follow-up calls
        r   )ÚMCPEnhancedStreamingIterator)rç   r  rp  rr  rt  Nr_   Úlitellm_metadata)Úbase_iteratorÚ
mcp_eventsr¬   rX   r_   Úoriginal_request_paramsr5   )Ú,litellm.responses.mcp.mcp_streaming_iteratorr€  r=   Ú_build_request_paramsrE   )rç   r  rp  rX   r~  rr  rt  r¬   r>   r€  Úrequest_paramss              r7   Ú_create_mcp_streaming_responsez8LiteLLM_Proxy_MCP_Handler._create_mcp_streaming_response>  sƒ   € õ(	
ô
 !:× OÑ Oð !
ØØØØ#Ø!5ñ!
ð ñ!
ˆñ ,ØØ+Ø+Ø)EØ$Ÿj™jÐ)<Ó=ò KØ�z‰zÐ,¨bÓ1×5Ñ5Ð6IÓJØ$2ô
ð 	
r6   c                 ód   — | ||dœ}|�||d<   |j                  |«       |j                  |«       |S )zÃ
        Build a clean request parameters dictionary for MCP streaming.

        Combines input, model, tools with call_params and additional kwargs
        in a clean, maintainable way.
        )rç   r  rH   rt  rh   )rç   r  rp  rr  rt  r>   r‡  s          r7   r†  z/LiteLLM_Proxy_MCP_Handler._build_request_paramsk  sM   € ð" ØØñ4
ˆð  Ð+Ø5IˆNÐ1Ñ2ð 	×Ñ˜kÔ*ð 	×Ñ˜fÔ%àÐr6   c                 óx  — ddl m} ddlm} g }|D ]¦  }|j	                  dd«      }|j	                  dd«      }d}d}	| D ].  }
t
        j                  |
«      \  }}}||k(  sŒ"|xs d}|xs d}	 n  ||||	|d	|j                  «       j                  d
d › �t        |«      dz   ¬«      }|j                  |«       Œ¨ |S )a  
        Create MCP tool execution events for streaming.

        Args:
            tool_calls: List of tool calls from the LLM response
            tool_results: List of tool execution results

        Returns:
            List of MCP tool execution events for streaming
        r   r	  )Úcreate_mcp_call_eventsr-   r3  r.   rM   r_  Úmcp_Né   rU   )r­   r-   ræ   r.   Úbase_item_idÚsequence_start)r7  r
  r…  r‹  rE   r=   rë   r<  Úhexr©   rk  )rÖ   rI  r
  r‹  Útool_execution_eventsre  r-   r  r­   ré   rà   r/   Úargsrã   Úexecution_eventss                  r7   Ú_create_tool_execution_eventsz7LiteLLM_Proxy_MCP_Handler._create_tool_execution_events�  sö   € õ 	'ÝWàLNÐð (ò 	;ˆKØ&Ÿ?™?¨>¸9ÓEˆLØ%Ÿ/™/¨(°BÓ7ˆKð "ˆIØ!ˆNØ'ò 	�	ô
 .×HÑHÈÓSñ	ØØØà˜lÓ*Ø $Ò 1¨	�IØ%)¢\¨T�NÙð	ñ  6Ø#Ø)Ø(Ø"Ø# D§J¡J£L×$4Ñ$4°R°aÐ$8Ð#9Ð:Ü"Ð#8Ó9¸AÑ=ô Ðð "×(Ñ(Ð)9Õ:ð5	;ð8 %Ð$r6   Úshould_auto_executec                 ó4   — | j                  «       }|rd|d<   |S )zè
        Prepare call parameters for the initial LLM call.

        For auto-execute scenarios, we need to disable streaming for the initial call
        so we can process the tool calls before streaming the final response.
        FÚstream)r`  )rr  r•  Úinitial_paramss      r7   Ú_prepare_initial_call_paramsz6LiteLLM_Proxy_MCP_Handler._prepare_initial_call_params¿  s%   € ð !,× 0Ñ 0Ó 2ˆáà',ˆN˜8Ñ$àÐr6   Úoriginal_stream_settingc                 óT   — | j                  «       }||d<   |j                  dd«       |S )zî
        Prepare call parameters for the follow-up LLM call after tool execution.

        Restores the original streaming setting and removes tool_choice since
        we're now providing tool results, not requesting tool calls.
        r—  Útool_choiceN)r`  Úpop)rr  rš  Úfollow_up_paramss      r7   Ú_prepare_follow_up_call_paramsz8LiteLLM_Proxy_MCP_Handler._prepare_follow_up_call_paramsÏ  s8   € ð #.×"2Ñ"2Ó"4Ðð &=Ð˜Ñ"ð 	×Ñ˜]¨DÔ1àÐr6   r¿   c                 óú  — ddl }ddlm} ddlm}m}  |dd|j                  «       j                  dd › �dd	 |d
|j                  |dt        ¬«      g ¬«      g¬«      } |dd|j                  «       j                  dd › �dd	 |d
|j                  |dt        ¬«      g ¬«      g¬«      }| j                  j                  |j                  «       «       | j                  j                  |j                  «       «       | S )zHAdd custom output elements to the final response for MCP tool execution.r   Nr	  )ÚGenericResponseOutputItemÚ
OutputTextr¿   Ú
mcp_tools_r�  Ú	completedÚsystemÚoutput_texté   )ÚindentÚdefault)rJ   rû   Úannotations)rJ   rä   Ústatusr  rò   Útool_execution_resultsÚtool_results_)rí   r7  r
  Úlitellm.types.responses.mainr¡  r¢  r<  r�  Údumpsr3   rÔ   rV   rÛ   )	rÑ   r¿   rI  rí   r
  r¡  r¢  Úmcp_tools_outputÚtool_results_outputs	            r7   Ú$_add_mcp_output_elements_to_responsez>LiteLLM_Proxy_MCP_Handler._add_mcp_output_elements_to_responseá  sÿ   € ó 	å&ßVñ #<Ø$Ø˜DŸJ™J›L×,Ñ,¨R¨aÐ0Ð1Ð2ØØáØ&ØŸ™Ð$5¸aÌ˜ÓMØ "ôðô#
Ðñ &?Ø)Ø˜tŸz™z›|×/Ñ/°°Ð3Ð4Ð5ØØáØ&ØŸ™ L¸ÄC˜ÓHØ "ôðô&
Ðð 	�‰×ÑÐ/×:Ñ:Ó<Ô=Ø�‰×ÑÐ2×=Ñ=Ó?Ô@àˆr6   )NNNN)NN).)r‹   )NNNNNNNrÃ   )9r0   r1   r2   Ú__doc__ÚstaticmethodrO   r3   r   ro   rG   r   r   ÚboolrS   r   ÚobjectÚtupler\   r   ÚMCPToolr¥   r¯   r   r¶   r¼   r¸   r   r
   r   r¹   r   rÐ   r   rØ   r#   rá   rë   rð   r  r,   rY  rf  r   ro  ÚResponsesToolParamr   ru  r   rt   rH  r   rˆ  r†  r”  r™  rŸ  r²  r5   r6   r7   r=   r=   C   së	  „ ñð ð
¨¨c°3¨h©¸$Ñ)>ð 
À4ÈÁ9ò 
ó ð
ð ð¨x¸	Ñ/BÀTÑ/Ið Èdò ó ðð ð#9Ø˜  V Ñ,Ñ-°Ñ4ð#9à	ˆt�I‰  S¡	Ð)Ñ	*ò#9ó ð#9ðJ ð'%Ø" 3™ið'%à" 3™ið'%ð ,ð'%ð 
ò	'%ó ð'%ðR ð (,Ø&*ØDHØ)-ñv#Ø2ðv#à&.¨w°s¸F°{Ñ/CÑ&DÀtÑ&Kðv#ð  ™*ðv#ð ˜t™ð	v#ð
 "& c¨4°°S°©>Ð&9Ñ!:¸TÑ!Aðv#ð ˜3‘i $Ñ&ðv#ð 
ˆt�G‰}˜d 3™iÐ'Ñ	(òv#ó ðv#ðp ð3Ø˜‘=ð3Ø7;¸C±yð3à	ˆt�G‰}˜d 3¨ 8™nÐ,Ñ	-ò3ó ð3ðB ðØ˜‘=ðØ@HÈÐQTÐV\ÐQ\ÑI]Ñ@^ðà	ˆg‰òó ðð6 ð (,Ø)-ñ	-Ø2ð-à&.¨w°s¸F°{Ñ/CÑ&Dð-ð  ™*ð-ð ˜3‘i $Ñ&ð	-ð
 
ˆt�C‰y˜$˜s C˜x™.Ð(Ñ	)ò-ó ð-ð@ ð (,Ø&*ØDHØ)-ñ37Øð37à&.¨w°s¸F°{Ñ/CÑ&Dð37ð  ™*ð37ð ˜t™ð	37ð
 "& c¨4°°S°©>Ð&9Ñ!:¸TÑ!Að37ð ˜3‘i $Ñ&ð37ð 
ˆt�G‰}˜d 3¨ 8™nÐ,Ñ	-ò37ó ð37ðj Øð /2ñ&Ø˜GÑ$ð&à˜{Ñ+ð&ð 
ÐÑ	 ò&ó ó ð&ð
 Øð,Ø˜GÑ$ð,à˜v‘ð,ð 
Ð%Ñ	&ò,ó ó ð,ð
 ð 7BñØ˜GÑ$ðàÐ2Ñ3ðð 
Ð#Ð&=Ñ=Ñ	>òó ðð& ðØ&.¨w°s¸F°{Ñ/CÑ&Dðà	òó ðð2 ðÐ4Hð ÈTÐRXÉ\ò ó ðð ð¸ð È4ÐPVÉ<ò ó ðð. ð7Øð7à	ˆs�T‰z˜3 ™: s¨T¡zÐ1Ñ	2ò7ó ð7ðB ð
(¨c°D©jð 
(¸TÀ#ÀvÀ+Ñ=Nò 
(ó ð
(ð ð!;Ð"2ð !;°sò !;ó ð!;ðF ð
 '+ØDHØ04Ø-1Ø&*Ø'+Ø)-ñ[Ø˜c 3˜h™ð[à˜VÑ$ð[ð ð[ð ˜t™ð	[ð
 "& c¨4°°S°©>Ð&9Ñ!:¸TÑ!Að[ð ˜S #˜X™¨Ñ-ð[ð ˜#˜s˜(‘^ dÑ*ð[ð ˜t™ð[ð  ™*ð[ð ˜3‘i $Ñ&ð[ð 
ˆmÑ	ò[ó ð[ðz ð*"Ø ™<ð*"àð*"ð ˜w s¨F {Ñ3Ñ4ð*"ð 
�'˜#˜v˜+Ñ&Ñ	'ò	*"ó ð*"ðX ð ;?ñKØ&ðKà˜w s¨F {Ñ3Ñ4ðKð Ð0Ñ0°4Ñ7ðKð 
ˆf‰ò	Kó ðKðZ ð
Ø˜c™ð
àð
ð Ð.Ñ/°$Ñ6ð
ð ð	
ð
 ð
ð 
Ð AÑ	Aò
ó ð
ð  ðLà# NÑ3ðLð 3ðLð ˜3 ˜;Ñ'ð	Lð
 ðLð 
òLó ðLð0 ð*
ØÐ'Ñ'ð*
àð*
ð ˜FÑ# dÑ*ð*
ð '+¨7°3¸°;Ñ+?Ñ&@ð	*
ð
 #Ð#@ÑAð*
ð ˜S &˜[Ñ)ð*
ð " D™jð*
ð ˜c 3˜h™ð*
ð 
ò*
ó ð*
ðX ðØÐ'Ñ'ðàðð ˜FÑ# dÑ*ðð ˜S &˜[Ñ)ð	ð
 " D™jðð ðð 
ˆc�6ˆkÑ	òó ððB ð/%Ø˜VÑ$ð/%Ø4<¸]Ñ4Kð/%à	Ð+Ñ	,ò/%ó ð/%ðb ð°$°s¸C°x±.ð ÐW[ð Ð`dÐehÐjmÐemÑ`nò ó ðð ð °D¸¸c¸±Nð  Ð]að  ÐfjÐknÐpsÐksÑftò  ó ð ð" ð.Ø&ð.à# FÑ+ð.ð ˜w s¨F {Ñ3Ñ4ð.ð 
ò	.ó ñ.r6   r=   )EÚrer{  Úcollections.abcr   r   r   r   Útypingr   r   r	   r
   r   r   r   r   Úopenai.types.chatr   Ú*openai.types.responses.function_tool_paramr   Úlitellm._loggingr   Úlitellm.constantsr   rD   r   ÚLiteLLMLoggingObjÚ,litellm.proxy._experimental.mcp_server.utilsr   r   r   Úlitellm.responses.mainr   Ú$litellm.responses.streaming_iteratorr   Úlitellm.types.llms.openair   r   r   r   r¹  Úlitellm.types.utilsr   r   r    r!   r"   r#   r$   ra  r%   r&   rù   r'   r(   r¸  rl   r)   Úlitellm.proxy.utilsr*   r3   r¶  r4   r,   r9   r:   Úcompiler;   r=   r5   r6   r7   ú<module>rÉ     sÜ   ðÜ 	Û ß 7Ñ 7Ý ß _× _Ó _å 5Ý Hå +Ý <Ý S÷ñ õ
 .Ý R÷ñ õ
 F÷÷ ñ ÷ 0áÝ(Ý)å3Þ0à€Gð ˜s F˜{Ñ+€	ˆ9Ó +ô�Iô ð '6Ð ˜eÓ 5Ø0LÐ/MÈUÐ-SÐ # UÓ Sð '˜BŸJ™JÐ'CÓDÐ �EÓ D÷Mò Mr6   