
    6i                    (   d dl mZ d dlZd dlZd dl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Zd dlZd dlmZmZ d	d
lmZ d	dlmZ  edede
f         Z ede      Z  ed      Z!g dZ"g dZ#dgZ$ee%e%f   Z&ee&   Z' G d de      Z( G d de(d      Z) G d de      Z* G d de      Z+ G d de*      Z, G d  d!e      Z- G d" d#e-      Z. G d$ d%e-      Z/	 	 	 	 	 	 d*d&Z0	 	 	 	 d+d'Z1	 d,	 	 	 	 	 	 	 d-d(Z2	 d.	 	 	 d/d)Z3y)0    )annotationsN)MappingHashable)	lru_cache)AnyCallableLiteralOptionalUnion	TypedDictTypeVarcast)Path)urlparse)	BaseModelField   )MultimodalError)ModeF.)boundKV)z
image/jpegz	image/pngz	image/gifz
image/webp)	audio/aacz
audio/flacz	audio/mp3z	audio/m4az
audio/mpegz
audio/mpgaz	audio/mp4z
audio/opusz	audio/pcm	audio/wavz
audio/webmapplication/pdfc                  "    e Zd ZU ded<   ded<   y)ImageParamsBasezLiteral['image']typestrsourceN__name__
__module____qualname____annotations__     k/root/.openclaw/workspace/visionaryfx/venv/lib/python3.12/site-packages/instructor/processing/multimodal.pyr   r   2   s    
Kr(   r   c                      e Zd ZU ded<   y)ImageParamsCacheControlTypecache_controlNr"   r'   r(   r)   r+   r+   7   s    ##r(   r+   F)totalc                  >   e Zd ZU  ed      Zded<    ed      Zded<    edd	d
      Zded<   edd       Z	edd       Z
edd       Zedd       Zeddd       Zed d       Zeed!d              Zeed"d              Zeed#d              Zd$dZd%dZd Zy)&Imagez+URL, file path, or base64 data of the imagedescriptionUnion[str, Path]r!   zMIME type of the imager    
media_typeNzBase64 encoded image dataFr2   reprUnion[str, None]datac                   t        |t              r| j                  |      r| j                  |      S |j	                  d      r| j                  |      S |j	                  d      r| j                  |      S 	 t        |      }|j                         r| j                  |      S 	 | j                  |      S t        |t              r| j                  |      S y# t        $ r Y >w xY w)z<Attempt to autodetect an image from a source string or Path.http://https://gs://N)
isinstancer    	is_base64from_base64
startswithfrom_urlfrom_gs_urlr   is_file	from_pathOSErrorfrom_raw_base64clsr!   paths      r)   
autodetectzImage.autodetectD   s     fc"}}V$v..  !89||F++  )v..F|<<>==.. "
 &&v..fd#==(( $  s   8+C 	C$#C$c                Z    	 | j                  |      S # t        $ r t        |      cY S w xY w)a&  Safely attempt to autodetect an image from a source string or path.

        Args:
            source (Union[str,path]): The source string or path.
        Returns:
            An Image if the source is detected to be a valid image, otherwise
            the source itself as a string.
        rK   
ValueErrorr    rI   r!   s     r)   autodetect_safelyzImage.autodetect_safely\   /    	>>&)) 	v;	    **c                @    t        t        j                  d|            S )Nz^data:image/[a-zA-Z]+;base64,boolrematchrI   ss     r)   r?   zImage.is_base64k       BHH=qABBr(   c                    |j                  dd      \  }}|j                  d      d   j                  d      d   }|t        vr&t        d| ddj                  t               d	
       | |||      S )N,   :;r   Unsupported image format: z. Supported formats: , image)content_typer!   r4   r8   )splitVALID_MIME_TYPESr   joinrI   data_uriheaderencodedr4   s        r)   r@   zImage.from_base64o   s    "..a0\\#&q)//4Q7
--!,ZL8MdiiXhNiMjk$  !
 	
r(   c                   |j                  d      st        d      d|dd  }	 t        j                  ||      }|j	                          |j
                  j                  d      }|t        vrt        d|       t        j                  |j                        j                  d	      } | |||
      S # t        j                  $ r}t        d      |d}~ww xY w)z
        Create an Image instance from a Google Cloud Storage URL.

        Args:
            data_uri: GCS URL starting with gs://
            timeout: Request timeout in seconds (default: 30)
        r=   URL must start with gs://https://storage.googleapis.com/   NtimeoutContent-Typer`   utf-8rd   z6Failed to access GCS image (must be publicly readable))rA   rN   requestsgetraise_for_statusheadersrf   base64	b64encodecontentdecodeRequestExceptionrI   ri   rq   
public_urlresponser4   r8   es           r)   rC   zImage.from_gs_url~   s     ""7+8996x|nE
	||J@H%%'!))--n=J!11 #=j\!JKK##H$4$45<<WEDh:DII(( 	H	   BB7 7C
CCc                   	 t        j                  |      }d }|j                  d      rd}nT|j                  d      rd}n@|j                  d      s|j                  d      rd}n|j                  d      r
|d	d
 dk(  rd}|rd| }|t        v r | |||      S t	        d|       # t
        $ r}t	        d      |d }~ww xY w)Ns   jpegs   PNG

pngs   GIF87as   GIF89agifs   RIFF      s   WEBPwebpzimage/rd   zUnsupported image type: z(Invalid or unsupported base64 image data)rx   	b64decoderA   rf   rN   	Exception)rI   r8   decodedimg_typer4   r   s         r)   rG   zImage.from_raw_base64   s    	Q&&t,G H!!/2!##$89 ##I.'2D2DY2O ##G,2'1I!%hZ0
!11##-! 
 7zBCC 	QGIqP	Qs   BB) B) )	C2B>>Cc                   |j                  d      r| j                  |      S | j                  |      r| j                  |      S t	        |      }t        j                  |j                        \  }}|s3	 t        j                  |d      }|j                  j                  d      }|t        vrt        d|        | ||d       S # t        j                  $ r}t        d      |d }~ww xY w)Nr=   Tallow_redirectsrr   zFailed to fetch image from URLr`   rd   )rA   rC   r?   r@   r   	mimetypes
guess_typerJ   rt   headrw   ru   r|   rN   rf   rI   url
parsed_urlr4   _r   r   s          r)   rB   zImage.from_url   s     >>'"??3''==??3''c]
!,,Z__=
AK#==dC%--11.A
 --9*FGG#*4@@ ,, K #ACJKs   52C C,C''C,c                   t        |      }|j                         st        d|       |j                         j                  dk(  rt        d      t        j                  t        |            \  }}|t        vrt        d|       t        j                  |j                               j                  d      } | |||      S )NzImage file not found: r   zImage file is emptyr`   rs   rd   )r   rD   FileNotFoundErrorstatst_sizerN   r   r   r    rf   rx   ry   
read_bytesr{   rI   rJ   r4   r   r8   s        r)   rE   zImage.from_path   s     Dz||~#&<TF$CDD99;!#233!,,SY7
A--9*FGG 1299'B$:DAAr(   c                    t        j                  |       }|j                          t        j                  |j
                        j                  d      }|S )zDCachable helper method for getting image url and encoding to base64.rs   )rt   ru   rv   rx   ry   rz   r{   )r   r   r8   s      r)   url_to_base64zImage.url_to_base64   sD     <<$!!# 0 0188Ar(   c                    t        | j                  t              rG| j                  j                  d      r,| j                  s | j                  | j                        | _        dd| j                  | j                  ddS )Nr:   rb   rx   r   r4   r8   r   r!   )r>   r!   r    rA   r8   r   r4   selfs    r)   to_anthropiczImage.to_anthropic   se    t{{C(&&'>?II**4;;7DI  "oo		
 	
r(   c                   |t         j                  t         j                  hv rdnd}t        | j                  t
              rx| j                  j                  d      r]| j                  | j                        sB|t         j                  t         j                  hv rd| j                  dS |d| j                  idS | j                  s$| j                  t        | j                              r| j                  xs( t        | j                        j                  dd      d   }|t         j                  t         j                  hv rdd| j                   d	| dS |dd| j                   d	| idS t        d
      )Ninput_image	image_urlr:   )r   r   r   r\   r]   data:;base64,*Image data is missing for base64 encoding.)r   RESPONSES_TOOLS"RESPONSES_TOOLS_WITH_INBUILT_TOOLSr>   r!   r    rA   r?   r8   re   r4   rN   )r   mode
image_typer8   s       r)   	to_openaizImage.to_openai   sO    ,,d.U.UVV  	 t{{C(&&'>?NN4;;/,,d.U.UVV -DKKHH *%9MNNYY$..T[[)9:99ADKK 0 6 6sA >q AD,,d.U.UVV)#((9$!H  '"'50A$)P!Q 
 IJJr(   c                r   	 ddl m} t        | j                  t
              rL| j                  j                  d      r1|j                  j                  | j                  | j                        S t        | j                  t
              ri| j                  j                  d      rN|j                  j                  t        j                  | j                        j                  | j                        S | j                  s$| j                  t        | j                              rp| j                  xs( t        | j                        j                  dd	      d	   }|j                  j                  t!        j"                  |      | j                        S t%        d
      # t        $ r}t        d      |d}~ww xY w)zJ
        Convert the Image instance to Google GenAI's API format.
        r   types^google-genai package is required for GenAI integration. Install with: pip install google-genaiNr=   r8   	mime_typer:   r\   r]   r   )google.genair   ImportErrorr>   r!   r    rA   Part
from_bytesr8   r4   rt   ru   rz   r?   re   rx   r   rN   r   r   errr8   s       r)   to_genaizImage.to_genai  s]   	* dkk3'DKK,B,B7,K::((YY// )   dkk3'DKK,B,B#-
 ::((\\$++.66// )  
 99s4;;'7899ADKK 0 6 6sA >q AD::((%%d+t )  
 IJJ9  	p	s   F 	F6%F11F6)r!   
str | Pathreturnr0   )r!   r3   r   zUnion[Image, str]rY   r    r   rU   )ri   r    r   r0      )ri   r    rq   intr   r0   )r8   r    r   r0   )r   r    r   r0   )rJ   r3   r   r0   )r   r    r   r    r   dict[str, Any]r   r   r   r   )r#   r$   r%   r   r!   r&   r4   r8   classmethodrK   rP   r?   r@   rC   rG   r   rB   rE   staticmethodr   r   r   r   r'   r(   r)   r0   r0   ;   s(   $A F  (@AJA"5ED
  ) ).   C C 
 
  8 Q Q8 A  A( B  B   
"K<"Kr(   r0   c                      e Zd ZU dZ ed      Zded<    eddd	      Zd
ed<    ed      Zded<   e	dd       Z
e	dd       Ze	dd       Ze	dd       Ze	dd       Ze	dd       Ze	dd d       Zd!dZd"dZd Zy)#Audioz?Represents an audio that can be loaded from a URL or file path.zURL or file path of the audior1   r3   r!   NzBase64 encoded audio dataFr5   r7   r8   zMIME type of the audior    r4   c                   t        |t              r| j                  |      r| j                  |      S |j	                  d      r| j                  |      S |j	                  d      r| j                  |      S 	 t        |      }|j                         r| j                  |      S 	 t        d      t        |t              r| j                  |      S y# t        $ r Y t        d      w xY w)z<Attempt to autodetect an audio from a source string or Path.r:   r=   z Unable to determine audio sourceN)r>   r    r?   r@   rA   rB   rC   r   rD   rE   rF   rN   rH   s      r)   rK   zAudio.autodetectE  s     fc"}}V$v..  !89||F++  )v..F|<<>==.. "
 ?@@fd#==(( $  ?@@s   8+C 	C('C(c                Z    	 | j                  |      S # t        $ r t        |      cY S w xY w)a&  Safely attempt to autodetect an audio from a source string or path.

        Args:
            source (Union[str,path]): The source string or path.
        Returns:
            An Audio if the source is detected to be a valid audio, otherwise
            the source itself as a string.
        rM   rO   s     r)   rP   zAudio.autodetect_safely]  rQ   rR   c                @    t        t        j                  d|            S )Nz"^data:audio/[a-zA-Z0-9+-]+;base64,rT   rX   s     r)   r?   zAudio.is_base64l  s    BHHBAFGGr(   c                    |j                  dd      \  }}|j                  d      d   j                  d      d   }|t        vrt        d|        | |||      S )Nr\   r]   r^   r_   r   Unsupported audio format: rd   )re   VALID_AUDIO_MIME_TYPESrN   rh   s        r)   r@   zAudio.from_base64p  sk    "..a0\\#&q)//4Q7
339*FGG!
 	
r(   c                b   |j                  d      r| j                  |      S t        j                  |      }|j                  j                  d      }|t
        v sJ ddj                  t
                      t        j                  |j                        j                  d      } | |||      S )z$Create an Audio instance from a URL.r=   zcontent-type&Invalid audio format. Must be one of: ra   rs   r!   r8   r4   )rA   rC   rt   ru   rw   r   rg   rx   ry   rz   r{   )rI   r   r   rc   r8   s        r)   rB   zAudio.from_url|  s     >>'"??3''<<$''++N;55 	
4TYY?U5V4WX	
5  0 0188A#D\BBr(   c                   t        |      }|j                         s
J d|        t        j                  t	        |            d   }|dk(  rd}|dk(  rd}|t
        v sJ ddj                  t
                      t        j                  |j                               j                  d	      } | t	        |      ||
      S )z*Create an Audio instance from a file path.zAudio file not found: r   zaudio/x-wavr   zaudio/vnd.dlna.adtsr   r   ra   rs   r   )r   rD   r   r   r    r   rg   rx   ry   r   r{   )rI   rJ   r   r8   s       r)   rE   zAudio.from_path  s     Dz||~>!7v>>~((T3A6	%#I ..#I22 	
4TYY?U5V4WX	
2  1299'B#d)$9EEr(   c                   |j                  d      st        d      d|dd  }	 t        j                  ||      }|j	                          |j
                  j                  d      }|t        vrt        d|       t        j                  |j                        j                  d	      } | |||
      S # t        j                  $ r}t        d      |d}~ww xY w)z
        Create an Audio instance from a Google Cloud Storage URL.

        Args:
            data_uri: GCS URL starting with gs://
            timeout: Request timeout in seconds (default: 30)
        r=   rm   rn   ro   Nrp   rr   r   rs   rd   z6Failed to access GCS audio (must be publicly readable))rA   rN   rt   ru   rv   rw   r   rx   ry   rz   r{   r|   r}   s           r)   rC   zAudio.from_gs_url  s     ""7+8996x|nE
	||J@H%%'!))--n=J!77 #=j\!JKK##H$4$45<<WEDh:DII(( 	H	r   c                    |t         j                  t         j                  hv rt        d      d| j                  dddS )z2Convert the Audio instance to OpenAI's API format.z&OpenAI Responses doesn't support audioinput_audiowav)r8   format)r   r   )r   r   r   rN   r8   )r   r   s     r)   r   zAudio.to_openai  sB    D(($*Q*QRREFF "$(II?
 	
r(   c                    t        d      )NzAnthropic is not supported yet)NotImplementedErrorr   s    r)   r   zAudio.to_anthropic  s    !"BCCr(   c                    	 ddl m} |j                  j	                  t        j                  | j                        | j                        S # t        $ r}t        d      |d}~ww xY w)zJ
        Convert the Audio instance to Google GenAI's API format.
        r   r   r   Nr   )	r   r   r   r   r   rx   r   r8   r4   )r   r   r   s      r)   r   zAudio.to_genai  sf    	* zz$$!!$)),oo % 
 	
  	p	s   A 	A&A!!A&)r!   r   r   r   )r!   r3   r   zUnion[Audio, str]r   )ri   r    r   r   )r   r    r   r   )rJ   r3   r   r   r   )ri   r    rq   r   r   r   r   r   )r#   r$   r%   __doc__r   r!   r&   r8   r4   r   rK   rP   r?   r@   rB   rE   rC   r   r   r   r'   r(   r)   r   r   <  s    I$1PQFQ"5ED
  (@AJA) ).   H H 	
 	
 C C F F,  8
D
r(   r   c                  V     e Zd ZU dZ edd      Zded<   ed	d       Zd
 fdZ	 xZ
S )ImageWithCacheControlz,Image with Anthropic prompt caching support.Nz&Optional Anthropic cache control imager1   OptionalCacheControlTyper-   c                    |d   }|j                  d      }t        j                  |      } | |j                  |j                  |j
                  |      S )Nr!   r-   )r!   r4   r8   r-   )ru   r0   rK   r!   r4   r8   )rI   image_paramsr!   r-   
base_images        r)   from_image_paramsz'ImageWithCacheControl.from_image_params  sU    h'$((9%%f-
$$!,,'	
 	
r(   c                Z    t         |          }| j                  r| j                  |d<   |S )-Override Anthropic return with cache_control.r-   )superr   r-   r   result	__class__s     r)   r   z"ImageWithCacheControl.to_anthropic  s.    %'&*&8&8F?#r(   )r   r+   r   r0   r   )r#   r$   r%   r   r   r-   r&   r   r   r   __classcell__r   s   @r)   r   r     s<    6.3B/M+  	
 	
 r(   r   c                  6   e Zd ZU  ed      Zded<    edd      Zded	<    ed
dd      Zded<   edd       Z	edd       Z
edd       Zed d       Zeed!d              Zed"d       Zed#d$d       Zeed%d              Zd&dZd'dZd&dZd Zd(d)dZy
)*PDFz)URL, file path, or base64 data of the PDFr1   r   r!   zMIME type of the PDFr   )r2   defaultr    r4   NzBase64 encoded PDF dataFr5   
str | Noner8   c                   t        |t              r| j                  |      r| j                  |      S |j	                  d      r| j                  |      S |j	                  d      r| j                  |      S 	 t        |      j                         r| j                  |      S 	 | j                  |      S t        |t              r| j                  |      S y# t        $ r}t        ddt        |            |d}~wt        $ rD}|j                  dk(  rt        ddt        |            |t        d	dt        |            |d}~ww xY w)
a:  Attempt to autodetect a PDF from a source string or Path.
        Args:
            source (Union[str,path]): The source string or path.
        Returns:
            A PDF if the source is detected to be a valid PDF.
        Raises:
            ValueError: If the source is not detected to be a valid PDF.
        r:   r=   zPDF file not foundpdf)rc   	file_pathN?   zPDF file name too longzUnable to read PDF file)r>   r    r?   r@   rA   rB   rC   r   rD   rE   r   r   rF   errnorG   )rI   r!   r   r   s       r)   rK   zPDF.autodetect  sE    fc"}}V$v..""#:;||F++""7+v..<'')==00 ** &&v..%==(( &) % %(!&!&k 	
  77b=)0%*"%f+ 	
 &-!&!&k 	s$   8)C 	EC77E?EEc                Z    	 | j                  |      S # t        $ r t        |      cY S w xY w)a  Safely attempt to autodetect a PDF from a source string or path.

        Args:
            source (Union[str,path]): The source string or path.
        Returns:
            A PDF if the source is detected to be a valid PDF, otherwise
            the source itself as a string.
        rM   rO   s     r)   rP   zPDF.autodetect_safely*  rQ   rR   c                @    t        t        j                  d|            S )Nz^data:application/pdf;base64,rT   rX   s     r)   r?   zPDF.is_base649  rZ   r(   c                    |j                  dd      \  }}|j                  d      d   j                  d      d   }|t        vrt        d|        | |||      S )Nr\   r]   r^   r_   r   Unsupported PDF format: rd   )re   VALID_PDF_MIME_TYPESrN   rh   s        r)   r@   zPDF.from_base64=  sk    "..a0\\#&q)//4Q7
117
|DEE!
 	
r(   c                   t        |      }|j                         st        d|       |j                         j                  dk(  rt        d      t        j                  t        |            \  }}|t        vrt        d|       t        j                  |j                               j                  d      } | |||      S )NzPDF file not found: r   zPDF file is emptyr   rs   rd   )r   rD   r   r   r   rN   r   r   r    r   rx   ry   r   r{   r   s        r)   rE   zPDF.from_pathI  s     Dz||~#&:4&$ABB99;!#011!,,SY7
A117
|DEE 1299'B$:DAAr(   c                    	 t        j                  |      }|j                  d      r | |d|      S t        d      # t        $ r}t        d      |d }~ww xY w)Ns   %PDF-r   rd   zInvalid PDF formatz&Invalid or unsupported base64 PDF data)rx   r   rA   rN   r   )rI   r8   r   r   s       r)   rG   zPDF.from_raw_base64Z  sj    	N&&t,G!!(+0 
 122 	NEFAM	Ns   0> > 	AAAc                   |j                  d      st        d      d|dd  }	 t        j                  ||      }|j	                          |j
                  j                  dd      }|t        vrt        d	|       t        j                  |j                        j                  d
      } | |||      S # t        j                  $ r}t        d      |d}~ww xY w)z
        Create a PDF instance from a Google Cloud Storage URL.

        Args:
            data_uri: GCS URL starting with gs://
            timeout: Request timeout in seconds (default: 30)
        r=   rm   rn   ro   Nrp   rr   r   r   rs   rd   z4Failed to access GCS PDF (must be publicly readable))rA   rN   rt   ru   rv   rw   r   rx   ry   rz   r{   r|   r}   s           r)   rC   zPDF.from_gs_urli  s     ""7+8996x|nE
	||J@H%%'!))--n>OPJ!55 #;J<!HII##H$4$45<<WEDh:DII(( 	F	s   BB8 8CCCc                   |j                  d      r| j                  |      S t        |      }t        j                  |j
                        \  }}|s3	 t        j                  |d      }|j                  j                  d      }|t        vrt        d|        | ||d       S # t        j                  $ r}t        d      |d }~ww xY w)Nr=   Tr   rr   zFailed to fetch PDF from URLr   rd   )rA   rC   r   r   r   rJ   rt   r   rw   ru   r|   rN   r   r   s          r)   rB   zPDF.from_url  s     >>'"??3''c]
!,,Z__=
AH#==dC%--11.A
 117
|DEE#*4@@ ,, H !?@aGHs   2B& &C
9CC
c                    t        | j                  t              r6| j                  j                  d      r| j                  sd| j                  dS t        d      )Nr:   document_url)r   r   z+Mistral only supports document URLs for now)r>   r!   r    rA   r8   rN   r   s    r)   
to_mistralzPDF.to_mistral  sN    t{{C(&&'>?II ' $  FGGr(   c                   |t         j                  t         j                  hv rdnd}t        | j                  t
              r| j                  j                  d      r| j                  st        j                  | j                        }t        j                  |j                        j                  d      }|t         j                  t         j                  hv r || j                  d| j                   d| dS || j                  d| j                   d| dd	S | j                  s$| j                  t        | j                              r| j                  xs( t        | j                        j!                  d
d      d   }|t         j                  t         j                  hv rO|t        | j                  t
              r| j                  nt        | j                        d| j                   d| dS |t        | j                  t
              r| j                  nt        | j                        d| j                   d| dd	S t#        d      )z$Convert to OpenAI's document format.
input_filefiler:   rs   r   r   )r   filename	file_data)r  r  )r   r  r\   r]   z(PDF data is missing for base64 encoding.)r   r   r   r>   r!   r    rA   r8   rt   ru   rx   ry   rz   r{   r4   r?   re   rN   )r   r   input_file_typer8   s       r)   r   zPDF.to_openai  s    ,,d.U.UVV  	 t{{C(&&'>?II <<,D##DLL188AD,,d.U.UVV+ $#((9$!H  ,$(KK',T__,=XdV%L  YY$..T[[)9:99ADKK 0 6 6sA >q AD,,d.U.UVV+ &dkk37  -#((9$!H  ,  *$++s; !KK!$T[[!1',T__,=XdV%L
 
 GHHr(   c                   t        | j                  t              r9| j                  j                  d      r| j                  sdd| j                  ddS | j                  sjt        j                  t        | j                              j                  | _        t        j                  | j                        j                  d      | _        dd| j                  | j                  ddS )	z'Convert to Anthropic's document format.r:   documentr   )r   r   r   rs   rx   r   )r>   r!   r    rA   r8   rt   ru   rz   rx   ry   r{   r4   r   s    r)   r   zPDF.to_anthropic  s     t{{C(&&'>?II #!;;  99$LLT[[)9:BB	",,TYY7>>wG	 #$"&// II r(   c                   	 ddl m} t        | j                  t
              r| j                  j                  d      r| j                  st        j                  | j                        j                  }t        j                  |      j                  d      }|j                  j                  t        j                   |      | j"                        S | j                  rD|j                  j                  t        j                   | j                        | j"                        S t%        d      # t        $ r}t        d      |d }~ww xY w)Nr   r   r   r:   rs   r   zUnsupported PDF format)r   r   r   r>   r!   r    rA   r8   rt   ru   rz   rx   ry   r{   r   r   r   r4   rN   r   s       r)   r   zPDF.to_genai  s   	* t{{C(&&'>?II <<,44D##D)009D::((%%d+// )  
 99::((%%dii0// )  
 1221  	p	s   D+ +	E4E  Ec                   |t        | j                  t              r| j                  j                  }nt        | j                  t              r| j                  j                  d      r7t        t        | j                        j                        j                  xs d}nGt        | j                        j                         rt        | j                        j                  nd}nd}t        j                  dd|      }t        j                  dd|      }|j                         }t        | j                  t              r| j                  j                  d      rrt        j                  d| j                        }|st        d	| j                         |j                  d
      }|j                  d      }dd|dd| j                  iidiS | j                  st        | j                  t              rW| j                  j                  d      r<t!        j"                  | j                        }|j%                          |j&                  }nt        | j                  t              s=t        | j                  t              rGt        | j                        j                         r$t        | j                        j)                         }n*t        d      t+        j,                  | j                        }dd|d|idiS )z%Convert to Bedrock's document format.)r;   r<   r=   r  z[^\w\s\-\(\)\[\]] z\s+ zs3://zs3://([^/]+)/(.*)zInvalid S3 URI format: r]   r   r   
s3Locationuri)r   namer!   r:   z/PDF data is missing and source cannot be loadedbytes)r>   r!   r   r  r    rA   r   rJ   existsrV   substriprW   rN   groupr8   rt   ru   rv   rz   r   rx   r   )r   r  s3_matchbucketkeyr   	pdf_bytess          r)   
to_bedrockzPDF.to_bedrock  sO    <$++t,{{''DKK-;;))*JK 5 : :;@@NJD  ,335 T[[)..'  " vv*B5vvfc4(zz| dkk3'DKK,B,B7,Kxx 4dkkBH #:4;;-!HII^^A&F..#C # $!4;;'	  yy$++s+0F0F'1 $<<4))+$,,	DKK.4;;,dkk1B1I1I1K -88:	 !RSS ((3I 5$7IBVW
 	
r(   )r!   r   r   r   )r!   r3   r   zUnion[PDF, str]r   )ri   r    r   r   )rJ   r   r   r   )r8   r    r   r   r   )ri   r    rq   r   r   r   )r   r    r   r   r   r   )N)r  r   r   r   )r#   r$   r%   r   r!   r&   r4   r8   r   rK   rP   r?   r@   r   rE   rG   rC   rB   r   r   r   r   r  r'   r(   r)   r   r     s   +VWFJW*4EJ  T/HuUD*U)) ))V   C C 	
 	
 B  B N N  8 A  A"
H7Ir83:F
r(   r   c                  $     e Zd ZdZd fdZ xZS )PDFWithCacheControlz*PDF with Anthropic prompt caching support.c                2    t         |          }ddi|d<   |S )r   r   	ephemeralr-   )r   r   r   s     r)   r   z PDFWithCacheControl.to_anthropicc  s$    %'#);"7r(   r   )r#   r$   r%   r   r   r   r   s   @r)   r  r  `  s    4 r(   r  c                  T     e Zd Ze	 d	 	 	 	 	 	 	 dd       Zedd       Z fdZ xZS )PDFWithGenaiFilec                   ddl m} ddl}ddlm}  |       }|j
                  j                  |      }|j                  |j                  k7  rg|j                  |       |j
                  j                  |j                        }|dkD  r|dz  }nt        d      |j                  |j                  k7  rg | |j                  |j                  d	      S )
z/Create a new PDFWithGenaiFile from a file path.r   	FileStateNClient)r  r  r]   zFMax retries reached. File upload has been started but is still pendingrd   )google.genai.typesr"  timer   r$  filesuploadstateACTIVEsleepru   r  r   r  r   )	rI   r   retry_delaymax_retriesr"  r'  r$  clientr  s	            r)   from_new_genai_filez$PDFWithGenaiFile.from_new_genai_filek  s    
 	1'||""	"2jjI,,,JJ{#<<###3DQq \  jjI,,, $((t~~DIIr(   c                8   ddl m} ddlm} ddl m}  |       }|j
                  j                  |      }|j                  |j                  j                  k(  r8|j                  |j                  k(  r | |j                  |j                  d      S t        d      )	z.Create a new PDFWithGenaiFile from a file URL.r   r   r!  r#  r%  Nrd   z%We only support uploaded PDFs for now)r   r   r&  r"  r$  r(  ru   r!   
FileSourceUPLOADEDr*  r+  r  r   rN   )rI   	file_namer   r"  r$  r/  r  s          r)   from_existing_genai_filez)PDFWithGenaiFile.from_existing_genai_file  s     	'0'||Y/;;%**333

iFVFV8Vxx>>  DEEr(   c                2   	 ddl m} | j                  rYt	        | j                  t
              r?d| j                  v r1|j                  j                  | j                  | j                        S t        | )         S # t        $ r}t        d      |d }~ww xY w)Nr   r   r   z7https://generativelanguage.googleapis.com/v1beta/files/)file_urir   )r   r   r   r!   r>   r    r   from_urir4   r   r   )r   r   r   r   s      r)   r   zPDFWithGenaiFile.to_genai  s    	* KK4;;,IT[[X::&&// '  
 w!!  	p	s   A< <	BBB)
      )r   r    r-  r   r.  r   r   r  )r4  r    r   r  )r#   r$   r%   r   r0  r5  r   r   r   s   @r)   r  r  j  s^    GIJJ*-JADJ	J J, F F"" "r(   r  c                   t        | t              r| S t        | t        t        t        f      st        | t
              r| g} g }|t        j                  t        j                  hv rdnd}| D ]m  }t        |t              r|j                  ||d       )t        |t
              r|j                  |       Kt        |t        t        t        f      r|t        j                  t        j                  t        j                  hv r |j                  |j                                |t        j                  t        j                  hv rt!        d      |t        j"                  t        j$                  hv r1t        |t              r!|j                  |j'                                7|j                  |j)                  |             Yt+        dt-        |              |S )zLConvert content items to the appropriate format based on the specified mode.
input_texttext)r   r=  zGemini is not supported yetUnsupported content type: )r>   r    r0   r   r   dictr   r   r   appendANTHROPIC_JSONANTHROPIC_TOOLSANTHROPIC_REASONING_TOOLSr   GEMINI_JSONGEMINI_TOOLSr   MISTRAL_STRUCTURED_OUTPUTSMISTRAL_TOOLSr   r   rN   r   )contentsr   converted_contentstext_file_typerz   s        r)   convert_contentsrK    s    (C (UE3/0Jx4N:=? D(($*Q*QRR 	 
  Kgs#%%~w&OP&%%g.%!45##$$.. 
 #))'*>*>*@A$**D,=,=>>)*GHH//""  Ws,"))'*<*<*>?"))'*;*;D*AB9$w-IJJ-K. r(   c                   t        | t        t        t        f      r| S t	        |       } | j                  d      rt        j                  |       S | j                  d      rt        j                  |       S | j                  d      rt        j                  |       S t        j                  |       \  }}|t        v rt        j                  |       S |t        v rt        j                  |       S |t        v rt        j                  |       S t        t        t        fD ]'  }|j                  |       }t        |t              r%|c S  | S )a  Autodetect images, audio, or PDFs from a given source.

    Args:
        source: URL, file path, Path, or data URI to inspect.

    Returns:
        The detected :class:`Image`, :class:`Audio`, or :class:`PDF` instance.
        If detection fails, the original source is returned.
    zdata:image/zdata:audio/zdata:application/pdf)r>   r0   r   r   r    rA   rP   r   r   rf   r   r   )r!   r4   r   rI   items        r)   autodetect_mediarN    s!    &5%-. [F'&&v..'&&v../0$$V,,((0MJ%%&&v..++&&v..))$$V,,uc" $$V,$$K Mr(   c           
     D   g }d	d}| D ]  }d|v r*|d   dv r|j                  |       nt        d|d          |d   }|d   xs g }|j                         D 	ci c]  \  }}	|dvs||	 }
}}	|rt        |t              rg }|D ]y  }t        |t
              r|j                  t        |             . ||      r3|j                  t        j                  t        t        |                   i|j                  |       { |}nGt        |t
              rt        |      }n+ ||      r#t        j                  t        t        |            }t        |t
              r|j                  ||d|
       lt        ||      }|j                  ||d|
        |S c c}	}w )
zGConvert messages to the appropriate format based on the specified mode.c                Z    t        | t              xr | j                  d      dk(  xr d| v S )Nr   rb   r!   )r>   r?  ru   )xs    r)   is_image_paramsz)convert_messages.<locals>.is_image_params  s+    !T"QquuV}'?QHPQMQr(   r   >   audiorb   zUnsupported message type: rolerz   )rT  rz   r   )rT  rz   )rQ  r   r   rU   )r@  rN   itemsr>   listr    rN  r   r   r   r+   rK  )messagesr   autodetect_imagesconverted_messagesrR  messagerT  rz   kvother_kwargsnew_contentrM  converted_contents                 r)   convert_messagesr`    s   $ R  )Wv"44"))'2 #=gfo=N!OPPv)$*$]]_
Q9T0TAqD
 
 '4(PR# 
1D!$,#**+;D+AB(.#**1CC $[$ 7 $**40
1 &GS)*73 )/AAg. gs#%%'B\B
 !1$ ?%%*;L|LO)T E
s   F)Fc                   ddl m} g }| D ]F  }t        ||j                        r|j	                  |       ,t        ||j
                        st        dt        |       d      t        |j
                  |      }g }|j                  st        d      |j                  D ]  }|j                  rd|rbt        |j                        }t        |t        t        t        f      r |j	                  |j                                a|j	                  |       s|j	                  |        |j	                  |j                  ||j                                I |S )zL
    Convert Typed Contents to the appropriate format for Google GenAI.
    r   r   r>  z/. This should only be used for the Google typeszContent parts are empty)partsrT  )r   r   r>   Filer@  ContentrN   r   r   rb  r=  rN  r0   r   r   r   rT  )rH  rX  r   r   rz   rI  content_partconverted_items           r)    extract_genai_multimodal_contentrg  E  s3    #57F Rguzz*MM'" '5==1,T']O;jk  u}}g./1}}677 $MM 
	8L  %6!1,2C2C!DnueS.AB&--n.E.E.GH")),7")),7
	8 	emm*<7<<mPQ?RB Mr(   )rH  zXUnion[str, dict[str, Any], Image, Audio, list[Union[str, dict[str, Any], Image, Audio]]]r   r   r   z Union[str, list[dict[str, Any]]])r!   z str | Path | Image | Audio | PDFr   zImage | Audio | PDF | str)F)rW  zslist[dict[str, Union[str, dict[str, Any], Image, Audio, PDF, list[Union[str, dict[str, Any], Image, Audio, PDF]]]]]r   r   rX  rU   r   zlist[dict[str, Any]])T)rH  z	list[Any]rX  rU   )4
__future__r   rx   rV   collections.abcr   r   	functoolsr   typingr   r   r	   r
   r   r   r   r   pathlibr   urllib.parser   r   rt   pydanticr   r   core.exceptionsr   r   r   r   r   r   rf   r   r   r    r,   r   r   r+   r0   r   r   r   r  r  rK  rN  r`  rg  r'   r(   r)   <module>rp     s   "  	 - 	 	 	  !   % - CxS)*Cx CL J   ** 38$ #$45 i 
$/ $~KI ~KB]
I ]
@E 6f
) f
R# <"s <"~-- - &-`%,%%n $AA A A  !AL #+++r(   