
    5>qj@                       d Z ddlmZ ddlZddlZddlZddlZddlZddl	Z	ddl
Z
ddlZddl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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$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l0m1Z1 ddl2m3Z3 ddl4m5Z5 ddl6m7Z7 ddl8m9Z9m:Z:m;Z;  e	jx                  e=      Z>ee?e?f   Z@d5dZA G d deB      ZCd6dZD G d deB      ZEd7dZF	 d8	 	 	 	 	 	 	 d9dZGd:d ZH G d! d"      ZI G d# d$e      ZJd;d%ZKeKd<d'       ZL ed()       G d* d&             ZM G d+ d,e      ZN	 d=	 	 	 	 	 	 	 d>d-ZO	 d?	 	 	 	 	 d@d.ZPdd/	 	 	 	 	 	 	 dAd0ZQ G d1 d2e      ZR G d3 d4      ZSy)BzO
The main purpose of this module is to expose LinkCollector.collect_sources().
    )annotationsN)CallableIterableMutableMappingSequence)	dataclass)
HTMLParser)Values)
NamedTupleProtocol)canonicalize_name)Response)
RetryError)ConnectionFailedErrorConnectionTimeoutErrorNetworkConnectionErrorProxyConnectionErrorSSLMissingErrorSSLVerificationError)Link)SearchScope)
PipSession)raise_for_status)is_archive_fileredact_auth_from_url)url_to_path)vcs   )CandidatesFromPage
LinkSourcebuild_sourcec                    t         j                  D ]6  }| j                         j                  |      s#| t	        |         dv s4|c S  y)zgLook for VCS schemes in the URL.

    Returns the matched VCS scheme, or None if there's no match.
    z+:N)r   schemeslower
startswithlen)urlschemes     \/opt/rentech/trading_bot/.venv/lib/python3.12/site-packages/pip/_internal/index/collector.py_match_vcs_schemer+   4   sE    
 ++ 99;!!&)c#f+.>$.FM     c                        e Zd Zd fdZ xZS )_NotAPIContentc                B    t         |   ||       || _        || _        y N)super__init__content_typerequest_desc)selfr3   r4   	__class__s      r*   r2   z_NotAPIContent.__init__@   s"    |4((r,   )r3   strr4   r7   returnNone)__name__
__module____qualname__r2   __classcell__r6   s   @r*   r.   r.   ?   s    ) )r,   r.   c                    | j                   j                  dd      }|j                         }|j                  d      ryt	        || j
                  j                        )z
    Check the Content-Type header to ensure the response contains a Simple
    API Response.

    Raises `_NotAPIContent` if the content type is not a valid content-type.
    Content-TypeUnknown)z	text/htmlz#application/vnd.pypi.simple.v1+html#application/vnd.pypi.simple.v1+jsonN)headersgetr%   r&   r.   requestmethod)responser3   content_type_ls      r*   _ensure_api_headerrI   F   s[     ##''	BL!'')N  	
 	
x'7'7'>'>
??r,   c                      e Zd Zy)_NotHTTPN)r:   r;   r<    r,   r*   rK   rK   \   s    r,   rK   c                    t         j                  j                  |       \  }}}}}|dvr
t               |j	                  | d      }t        |       t        |       y)z
    Send a HEAD request to the URL, and ensure the response contains a simple
    API Response.

    Raises `_NotHTTP` if the URL is not available for a HEAD request, or
    `_NotAPIContent` if the content type is not a valid content type.
    >   httphttpsT)allow_redirectsN)urllibparseurlsplitrK   headr   rI   )r(   sessionr)   netlocpathqueryfragmentresps           r*   _ensure_api_responser[   `   sV     -3LL,A,A#,F)FFD%&&j<<T<2DTtr,   Fc                   t        t        |       j                        rt        | |       t        j                  dt        |              ddj                  g d      i}|rt        j                  d       d|d<   |j                  | |	      }t        |       t        |       t        j                  d
t        |       |j                  j                  dd             |S )aY  Access an Simple API response with GET, and return the response.

    This consists of three parts:

    1. If the URL looks suspiciously like an archive, send a HEAD first to
       check the Content-Type is HTML or Simple API, to avoid downloading a
       large file. Raise `_NotHTTP` if the content type cannot be determined, or
       `_NotAPIContent` if it is not HTML or a Simple API.
    2. Actually perform the request. Raise HTTP exceptions on network failures.
    3. Check the Content-Type header to make sure we got a Simple API response,
       and raise `_NotAPIContent` otherwise.
    )rU   zGetting page %sAcceptz, )rB   z*application/vnd.pypi.simple.v1+html; q=0.1ztext/html; q=0.01z"Refreshing package index response.z	max-age=0zCache-Control)rC   zFetched page %s as %sr@   rA   )r   r   filenamer[   loggerdebugr   joinrD   r   rI   rC   )r(   rU   force_revalidaterC   rZ   s        r*   _get_simple_responserc   r   s    " tCy))*S'2
LL"$8$=> 	$))
G  	9:#. ;;sG;,DT t
LLS!3 Kr,   c                    | rHd| v rDt         j                  j                         }| d   |d<   |j                  d      }|rt	        |      S y)z=Determine if we have any encoding information in our headers.r@   zcontent-typecharsetN)emailmessageMessage	get_paramr7   )rC   mre   s      r*   _get_encoding_from_headersrk      sK    >W,MM!!##N3.++i(w<r,   c                  $    e Zd ZddZddZddZy)CacheablePageContentc                .    |j                   sJ || _        y r0   )cache_link_parsingpager5   rp   s     r*   r2   zCacheablePageContent.__init__   s    &&&&	r,   c                    t        |t        |             xr- | j                  j                  |j                  j                  k(  S r0   )
isinstancetyperp   r(   )r5   others     r*   __eq__zCacheablePageContent.__eq__   s-    %d,P%**..1PPr,   c                @    t        | j                  j                        S r0   )hashrp   r(   r5   s    r*   __hash__zCacheablePageContent.__hash__   s    DIIMM""r,   N)rp   IndexContentr8   r9   )ru   objectr8   bool)r8   int)r:   r;   r<   r2   rv   rz   rL   r,   r*   rm   rm      s    Q#r,   rm   c                      e Zd ZddZy)
ParseLinksc                     y r0   rL   rq   s     r*   __call__zParseLinks.__call__   s    r,   Nrp   r{   r8   zIterable[Link])r:   r;   r<   r   rL   r,   r*   r   r      s    Ar,   r   c                z     t         j                  d fd       t        j                         d fd       }|S )z
    Given a function that parses an Iterable[Link] from an IndexContent, cache the
    function's result (keyed by CacheablePageContent), unless the IndexContent
    `page` has `page.cache_link_parsing == False`.
    c                :    t         | j                              S r0   )listrp   )cacheable_pagefns    r*   wrapperz*with_cached_index_content.<locals>.wrapper   s    B~**+,,r,   c                `    | j                   r t        |             S t         |             S r0   )ro   rm   r   )rp   r   r   s    r*   wrapper_wrapperz2with_cached_index_content.<locals>.wrapper_wrapper   s+    ""/566BtH~r,   )r   rm   r8   
list[Link])rp   r{   r8   r   )	functoolscachewraps)r   r   r   s   ` @r*   with_cached_index_contentr      s@     __- - __R 
 r,   r{   c              #  T  K   | j                   j                         }|j                  d      r^t        j                  | j
                        }|j                  dg       D ])  }t        j                  || j                        }|&| + yt        | j                        }| j                  xs d}|j                  | j
                  j                  |             | j                  }|j                  xs |}|j                  D ]!  }	t        j                   |	||      }|| # yw)z\
    Parse a Simple API's Index Content, and yield its anchor elements as Link objects.
    rB   filesNzutf-8)page_urlbase_url)r3   r%   r&   jsonloadscontentrD   r   	from_jsonr(   HTMLLinkParserencodingfeeddecoder   anchorsfrom_element)
rp   rH   datafilelinkparserr   r(   r   anchors
             r*   parse_linksr      s      &&,,.N  !FGzz$,,'HHWb) 	D>>$1D|J		
 	DHH%F}}'H
KK##H-.
((C%#H..   #I<
	s   D&D(T)frozenc                  P    e Zd ZU dZded<   ded<   ded<   ded<   d	Zd
ed<   ddZy)r{   a  Represents one response (or page), along with its URL.

    :param encoding: the encoding to decode the given content.
    :param url: the URL from which the HTML was downloaded.
    :param cache_link_parsing: whether links parsed from this page's url
                               should be cached. PyPI index urls should
                               have this set to False, for example.
    bytesr   r7   r3   
str | Noner   r(   Tr}   ro   c                ,    t        | j                        S r0   )r   r(   ry   s    r*   __str__zIndexContent.__str__
  s    #DHH--r,   N)r8   r7   )r:   r;   r<   __doc____annotations__ro   r   rL   r,   r*   r{   r{      s/     N	H##.r,   c                  4     e Zd ZdZd fdZddZddZ xZS )r   zf
    HTMLParser that keeps the first base HREF and a list of all anchor
    elements' attributes.
    c                P    t         |   d       || _        d | _        g | _        y )NT)convert_charrefs)r1   r2   r(   r   r   )r5   r(   r6   s     r*   r2   zHTMLLinkParser.__init__  s(    $/$(46r,   c                    |dk(  r(| j                   | j                  |      }||| _         y y |dk(  r%| j                  j                  t	        |             y y )Nbasea)r   get_hrefr   appenddict)r5   tagattrshrefs       r*   handle_starttagzHTMLLinkParser.handle_starttag  sT    &=T]]2=='D $  CZLLU, r,   c                *    |D ]  \  }}|dk(  s|c S  y )Nr   rL   )r5   r   namevalues       r*   r   zHTMLLinkParser.get_href#  s&      	KD%v~	 r,   )r(   r7   r8   r9   )r   r7   r   list[tuple[str, str | None]]r8   r9   )r   r   r8   r   )r:   r;   r<   r   r2   r   r   r=   r>   s   @r*   r   r     s    
7-r,   r   c                <    |t         j                  } |d| |       y )Nz%Could not fetch URL %s: %s - skipping)r_   r`   )r   reasonmeths      r*   _handle_get_simple_failr   *  s    
 |||	0$?r,   c                    t        | j                        }t        | j                  | j                  d   || j                  |      S )Nr@   )r   r(   ro   )rk   rC   r{   r   r(   )rG   ro   r   s      r*   _make_index_contentr   4  sE     *(*:*:;H(LL- r,   )rb   c               v   | j                   j                  dd      d   }t        |      }|rt        j	                  d||        y |j                  d      rtt        j                  j                  t        |            rL|j                  d      s|dz  }t        j                  j                  |d      }t        j                  d|       	 t        |||	      }t!        || j"                  
      S # t$        $ r t        j	                  d|        Y y t&        $ r6}t        j	                  d| |j(                  |j*                         Y d }~y d }~wt,        t.        f$ r}t1        | |       Y d }~y d }~wt2        t4        f$ r5}d|j6                   }t1        | |t        j8                         Y d }~y d }~wt:        $ r#}t1        | d|j6                          Y d }~y d }~wt<        $ r#}t1        | d|j6                          Y d }~y d }~wt>        $ r)}t1        | tA        |j6                               Y d }~y d }~ww xY w)N#r   r   zICannot look at %s URL %s because it does not support lookup as web pages.zfile:/z
index.htmlz# file: URL is directory, getting %srU   rb   )ro   z`Skipping page %s because it looks like an archive, and cannot be checked by a HTTP HEAD request.zSkipping page %s because the %s request got Content-Type: %s. The only supported Content-Types are application/vnd.pypi.simple.v1+json, application/vnd.pypi.simple.v1+html, and text/htmlz4There was a problem confirming the ssl certificate: )r   zconnection error: zproxy connection error: )!r(   splitr+   r_   warningr&   osrW   isdirr   endswithrQ   rR   urljoinr`   rc   r   ro   rK   r.   r4   r3   r   r   r   r   r   contextinfor   r   r   r7   )r   rU   rb   r(   
vcs_schemerZ   excr   s           r*   _get_index_contentr   A  s    ((..a
 
#C #3'JW	

  ~~g277==S1A#B ||C 3JC
 ll""35:C@U#3C
< #4D<S<STT7  
1	
6 -  
A 	
 	
*  ./ +c**  !/2 @G}Uf6;;??  ! J(:3;;-&HII    P(@&NOO
 	 " 8c#++&677 	8sZ   C0 0H8H8,E

H8E--H8?+F//H8;GH8%HH8H33H8c                  "    e Zd ZU ded<   ded<   y)CollectedSourceszSequence[LinkSource | None]
find_links
index_urlsN)r:   r;   r<   r   rL   r,   r*   r   r     s    ++++r,   r   c                      e Zd ZdZ	 	 	 	 	 	 ddZe	 d		 	 	 	 	 	 	 d
d       Zedd       Z	 d	 	 	 	 	 ddZ		 	 	 	 	 	 ddZ
y)LinkCollectorz
    Responsible for collecting Link objects from all configured locations,
    making network requests as needed.

    The class's main method is its collect_sources() method.
    c                     || _         || _        y r0   )search_scoperU   )r5   rU   r   s      r*   r2   zLinkCollector.__init__  s    
 )r,   c                0   |j                   g|j                  z   }|j                  r0|s.t        j	                  ddj                  d |D                     g }|j                  xs g }t        j                  |||j                        }t        ||      }|S )z
        :param session: The Session to use to make requests.
        :param suppress_no_index: Whether to ignore the --no-index option
            when constructing the SearchScope object.
        zIgnoring indexes: %s,c              3  2   K   | ]  }t        |        y wr0   r   ).0r(   s     r*   	<genexpr>z'LinkCollector.create.<locals>.<genexpr>  s     Is-c2Is   )r   r   no_index)rU   r   )
	index_urlextra_index_urlsr   r_   r`   ra   r   r   creater   )clsrU   optionssuppress_no_indexr   r   r   link_collectors           r*   r   zLinkCollector.create  s     ''(7+C+CC
$5LL&IjII J ''-2
"))!!%%

 '%
 r,   c                .    | j                   j                  S r0   )r   r   ry   s    r*   r   zLinkCollector.find_links  s      +++r,   Nc                    | j                   j                  }d|v xs |duxr t        |      |v }t        || j                   |      S )z>
        Fetch an HTML page containing package links.
        z:all:Nr   )rU   refresh_packager   r   )r5   locationpackage_namerb   should_force_revalidates        r*   fetch_responsezLinkCollector.fetch_response  s_      <<77")-="= #
$ D!,/3CC 	  "LL4
 	
r,   c                    t        j                   fd j                  j                        D              j	                         }t        j                   fd j
                  D              j	                         }t        j                  t        j                        rwt        j                  ||      D cg c]  }||j                  d|j                   ! }}t        |       d dg|z   }t        j                  dj                  |             t!        t#        |      t#        |            S c c}w )Nc           	   3  h   K   | ])  }t        |j                  j                  d d        + yw)Fcandidates_from_pagepage_validator
expand_dirro   project_nameNr"   rU   is_secure_originr   locr   r   r5   s     r*   r   z0LinkCollector.collect_sources.<locals>.<genexpr>  sA      
4
  %9#||<< #() 
4
   /2c           	   3  h   K   | ])  }t        |j                  j                  d d        + yw)Tr   Nr   r   s     r*   r   z0LinkCollector.collect_sources.<locals>.<genexpr>  sA      
5
  %9#||<<#') 
5
r   z* z' location(s) to search for versions of :
)r   r   )collectionsOrderedDictr   get_index_urls_locationsvaluesr   r_   isEnabledForloggingDEBUG	itertoolschainr   r'   r`   ra   r   r   )r5   r   r   index_url_sourcesfind_links_sourcessliness   ```    r*   collect_sourceszLinkCollector.collect_sources  s2    (33 
4
 ((AA,O
4
 

 &( 	 )44 
5
 
5
 

 &( 	 w}}- #);=NO=QVV%7 QVVHE  u:, ##/.3 E LL5)*./-.
 	
s   >$D<)rU   r   r   r   r8   r9   F)rU   r   r   r
   r   r}   r8   r   )r8   z	list[str]r0   )r   r   r   r   r8   IndexContent | None)r   r7   r   r    r8   r   )r:   r;   r<   r   r2   classmethodr   propertyr   r   r  rL   r,   r*   r   r     s     " 
	 
 #(	   	
 
 B , , :>

,6
	
(,
,
 1,
 
	,
r,   r   )r(   r7   r8   r   )rG   r   r8   r9   )r(   r7   rU   r   r8   r9   r  )r(   r7   rU   r   rb   r}   r8   r   )rC   ResponseHeadersr8   r   )r   r   r8   r   r   r0   )r   r   r   zstr | Exceptionr   zCallable[..., None] | Noner8   r9   )T)rG   r   ro   r}   r8   r{   )r   r   rU   r   rb   r}   r8   r  )Tr   
__future__r   r   email.messagerf   r   r  r   r  r   urllib.parserQ   collections.abcr   r   r   r   dataclassesr   html.parserr	   optparser
   typingr   r   pip._vendor.packaging.utilsr   pip._vendor.requestsr   pip._vendor.requests.exceptionsr   pip._internal.exceptionsr   r   r   r   r   r   pip._internal.models.linkr   !pip._internal.models.search_scoper   pip._internal.network.sessionr   pip._internal.network.utilsr   pip._internal.utils.filetypesr   pip._internal.utils.miscr   pip._internal.utils.urlsr   pip._internal.vcsr   sourcesr    r!   r"   	getLoggerr:   r_   r7   r  r+   	Exceptionr.   rI   rK   r[   rc   rk   rm   r   r   r   r{   r   r   r   r   r   r   rL   r,   r*   <module>r(     s   #       	  H H ! " 
 : ) 6  + 9 4 8 9 9 0 ! A A			8	$ c*)Y )@,	y 	* #8	88 8 	8v	# 	#B B(  8 $. . .(Z > (,@
@@ %@ 
	@ 48

,0

" #	?
? ? 	?
 ?D,z ,
v
 v
r,   