
    lKj<                         d Z ddlZddlZddlmZmZ ddlmZm	Z	 ddl
Z
ddlmZ ddlmZ ddlmZmZ  ee      Zd	ed
efdZ G d d      ZdgZy)zHRequest director using openapi-core for stateless HTTP request building.    N)AnyClassVar)quoteurljoin)
SchemaPath)
get_logger   )	HTTPRouteParameterInfovaluereturnc                 D    t        | t              r| rdS dS t        |       S )u   Convert a scalar to its query-string representation.

    Booleans are lowercased to match JSON/OpenAPI conventions (true/false)
    rather than Python's str(True) → "True".
    truefalse)
isinstanceboolstr)r   s    s/Users/ahmed/devFolder/Ultron/claude-voice/.venv/lib/python3.12/site-packages/fastmcp/utilities/openapi/director.py_query_scalar_to_strr      s%     %v+G+u:    c                      e Zd ZU dZdefdZ	 ddedeee	f   dede
j                  fdZdedeee	f   deeee	f   eee	f   eee	f   eee	f   e	f   fd	Zd
dddZeeeef      ed<   dedeee	f   deee	f   fdZdedeee	f   dedefdZy)RequestDirectorzMBuilds httpx.Request objects from HTTPRoute and arguments using openapi-core.specc                     || _         y)z+Initialize with a parsed SchemaPath object.N)_spec)selfr   s     r   __init__zRequestDirector.__init__    s	    
r   route	flat_argsbase_urlr   c                 .   t         j                  d|j                   d|j                   d|        | j	                  ||      \  }}}}}t         j                  d| d| d| d|        | j                  ||      }| j                  |j                  ||      }	|j                  j                         }
|r|nd}|r|nd}d}d}d}d}|j                  rn|j                  j                  rXt        t        |j                  j                              }|j                  d	      d
   j                         j                         }|r-|j                         D ci c]  \  }}|t!        |       c}}nd}d}d}||dk(  rzt#        |t$              rji }|j                         D ]T  \  }}t#        |t&              r|||<   t#        |t(        t*        j,                  z        rd|f||<   Edt!        |      f||<   V nz|dk(  rt#        |t$              r|}nbt#        |t$        t.        z        rI|D|dk7  r?d|v r;t1        j2                  |d      j5                  d      }|rt%        |      ni }||d<   n|}n|}t7        j8                  |
|	|||||||	      S c c}}w )a  
        Constructs a final httpx.Request object, handling all OpenAPI serialization.

        Args:
            route: HTTPRoute containing OpenAPI operation details
            flat_args: Flattened arguments from LLM (may include suffixed parameters)
            base_url: Base URL for the request

        Returns:
            httpx.Request: Properly formatted HTTP request
        zBuilding request for  z with args: zUnflattened - path: z	, query: z, headers: z, body: N;r   zmultipart/form-dataz!application/x-www-form-urlencodedzapplication/jsonjsonF)	allow_nanzutf-8zContent-Type)	methodurlparamsheadersr$   contentdatafilescookies)loggerdebugr&   path_unflatten_arguments_serialize_query_params
_build_urlupperrequest_bodycontent_schemanextitersplitstriploweritemsr   r   dicttuplebytesioIOBaselist_jsondumpsencodehttpxRequest)r   r   r   r    path_paramsquery_paramsheader_paramscookie_paramsbodyr'   r&   r(   r)   	json_bodyr*   raw_content_typedeclared_content_typekvr-   r,   r+   s                         r   buildzRequestDirector.build$   s   " 	#ELL>5::,l9+V	
 %%eY7 	F\=- 	";-ykR_Q``himhno	

 33E<H ooejj+x@ ll((*!-4#0-d7;	&*
 (,,0%"4"4"C"C#D););)J)J$KL$4$:$:3$?$B$H$H$J$P$P$R!  5B4G4G4IJ4IDAqQ$Q''4IJ 	 (,&*$(==*dC  JJLDAq!!U+#$a#Auryy'89 %)!9a$(*>q*A#Ba ) &)LLtT*D$+.)5-1CC"77 $kk$%@GGPG/6d7mBG.>GN+ $I }}

 
	
k Ks   Jc                 V   i }i }i }i }i }t        |d      r|j                  r|j                         D ]  \  }}	|		||j                  vr&t        j	                  d| d|j
                          =|j                  |   }
|
d   }|
d   }|dk(  r|	||<   a|dk(  r|	||<   l|d	k(  r|	||<   w|d
k(  r|	||<   |dk(  r|	||<   t        j	                  d| d|         nt        j                  d       i }|j                  D ]  }|j                  ||j                  <    |j                         D ]  \  }}	|		d|v rE|j                  dd      \  }}|dv r,|dk(  r|	||<   n |dk(  r|	||<   n|d	k(  r|	||<   n
|d
k(  r|	||<   R||v r2||   }|dk(  r|	||<   f|dk(  r|	||<   q|d	k(  r|	||<   ||d
k(  s|	||<   |	||<    d}|r|j                  r|j                  j                  rt        |j                  j                        dkD  rt        t        |j                  j                              }|j                  j                  |   }t!        |t"              r|j%                  d      dk(  r|}n6t        |      dk(  r#t        t        |j'                                     }n|}n|}|||||fS )aU  
        Maps flat arguments back to their OpenAPI locations using the parameter map.

        Args:
            route: HTTPRoute with parameter_map containing location mappings
            flat_args: Flat arguments from LLM call

        Returns:
            Tuple of (path_params, query_params, header_params, cookie_params, body)
        parameter_mapNz
Argument 'z!' not found in parameter map for locationopenapi_namer0   queryheadercookierL   zUnknown parameter location 'z' for z2No parameter map available, using fallback mapping__r	   )r0   rW   rX   rY   r   typeobject)hasattrrT   r<   r.   warningoperation_idr/   
parametersrU   namersplitr5   r6   lenr7   r8   r   r=   getvalues)r   r   r   rH   rI   rJ   rK   
body_propsarg_namer   mappingrU   rV   param_locationsparam	base_namerL   content_typebody_schemas                      r   r1   z$RequestDirector._unflatten_arguments   s&    
 5/*u/B/B#,??#4%=5#6#66NN$XJ.OPUPbPbOcd --h7":.&~6v%05K-(16L.)27M,/)27M,/'/4J|,NN6xjxjQ3 $5< LLMN !O)).3nn

+ * $-??#4%= 8#*2//$*B'Ix#HH#v-5:K	2%06;L3%17<M)4%17<M)4  ..x8H6)05H-!W,16X.!X-27h/!X-27h/ ,1Jx(? $5D  ""&&55**99:Q>#D););)J)J$KL#00??M {D1#/8;%D_)  Z%6%6%8 9:D &D!L-LLr   ,r"   |)formspaceDelimitedpipeDelimited_STYLE_DELIMITERSrI   c                    |s|S |j                   D ci c]  }|j                  dk(  s|j                  |! }}i }|j                         D ]m  \  }}|j	                  |      }|N|j
                  |j
                  nd}	t        |t              r|sH|	r0|j                         D ]  \  }
}t        |      |t        |
      <    n|j                  xs d}| j                  j	                  |d      }g }|j                         D ]9  \  }
}|j                  t        |
             |j                  t        |             ; |j                  |      ||<   
|	s]|j                  xs d}| j                  j	                  |d      }t        |t              r!|sL|j                  d |D              ||<   i|||<   p |S c c}w )a  
        Serialize query parameter values according to their OpenAPI style/explode settings.

        By default (style=form, explode=true), list values are passed through as-is
        so httpx repeats the key (e.g. values=a&values=b). When explode=false,
        list values are joined with the style-appropriate delimiter:
          - form (default): comma  (values=a,b)
          - pipeDelimited:  pipe   (values=a|b)
          - spaceDelimited: space  (values=a%20b)
        rW   Trp   rn   c              3   2   K   | ]  }t        |        y w)N)r   ).0rQ   s     r   	<genexpr>z:RequestDirector._serialize_query_params.<locals>.<genexpr>T  s      9=B03Us   )r`   rU   ra   r<   rd   exploder   r=   r   stylers   appendjoinrB   )r   r   rI   pparam_lookup
serializedkeyr   
param_inforx   rP   rQ   ry   	delimiterpartss                  r   r2   z'RequestDirector._serialize_query_params  s      %//2
/!1::3HAFFAI/ 	 2
 &(
&,,.JC%))#.J%0:0B0B0N*,,TXeT*   %*KKMDAqBV !CJ';A'>? %2
 !+ 0 0 :F$($:$:$>$>uc$J	 ,.$)KKMDAq!LL)=a)@A!LL)=a)@A %2 +4..*?
3&,,6E $ 6 6 : :5# FI!%.$$*3.. 9=B9 +
3 !#JsOI /J U2
s
   F>F>path_templaterH   c                    |}|j                         D ]H  \  }}d| d}||v st        t        |      d      j                  dd      }|j                  ||      }J t	        |j                  d      dz   |j                  d            S )aG  
        Build URL by substituting path parameters in the template.

        Args:
            path_template: OpenAPI path template (e.g., "/users/{id}")
            path_params: Path parameter values
            base_url: Base URL to prepend

        Returns:
            Complete URL with path parameters substituted
        {} )safe.z%2E/)r<   r   r   replacer   rstriplstrip)	r   r   rH   r    url_path
param_nameparam_valueplaceholder
safe_values	            r   r3   zRequestDirector._build_url[  s      !'2'8'8':#Jzl"-Kh&"3{#3"=EEc5Q
#++KD	 (; xs+c18??33GHHr   N)zhttp://localhost)__name__
__module____qualname____doc__r   r   r
   r=   r   r   rF   rG   rR   r>   r1   rs   r   __annotations__r2   r3    r   r   r   r      s<   WZ  +	v
v
 S>v
 	v

 
v
pwMwM+/S>wM	tCH~tCH~tCH~tCH~sR	SwMv 3xS#X/ == 38n= 
c3h	=~I I/3CH~IILI	Ir   r   )r   r@   r$   rC   typingr   r   urllib.parser   r   rF   jsonschema_pathr   fastmcp.utilities.loggingr   modelsr
   r   r   r.   r   r   r   __all__r   r   r   <module>r      sV    N 	    '  & 0 ,	H	  VI VIt
 
r   