
    [dN                     8   d 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 ddlmZ ddlmZmZmZmZmZm
Z
mZmZmZmZmZmZ ddlmZ d ej        ej        fD             Z	 i Z	 d	ej        d
efdZ 	 d0de
e         de
e         dee!         d
eedf         fdZ"de
e         d
ee         fdZ#ded
e!fdZ$	 	 d1deeef         dee         dee!         d
ed         fdZ%dededeeef         dede!d
ed         fdZ&	 	 d1deeef         dee         dee!         d
ee         fdZ'd1dZ(ded
eegef         fd Z)de
e         d!ed
e!fd"Z*de
e         de
e         d
ee         fd#Z+	 d0d!eeef         d$eee                  d
efd%Z,	 d0de
eeef                  d$eee                  d
eeeeeef                  f         fd&Z-	 d0ded'eegef         d(ee!         d
dfd)Z. G d* d+e/          Z0 G d, d-e/          Z1 G d. de2          Z3 G d/ de2          Z4dS )2zC
This module provides utility methods for dealing with path-specs.
    N)
CollectionIterable)PathLike)AnyAnyStrCallabler   Dictr   IteratorListOptionalSequenceSetUnion   )Patternc                 6    g | ]}||t           j        k    |S  )	posixpathsep).0__seps     -lib/python3.11/site-packages/pathspec/util.py
<listcomp>r   !   s?       
	 y}$      pathreturnc                 j    t          |           }|                                 r|t          j        z  }|S )a5  
	Appends the path separator to the path if the path is a directory.
	This can be used to aid in distinguishing between directories and
	files on the file-system by relying on the presence of a trailing path
	separator.

	*path* (:class:`pathlib.path`) is the path to use.

	Returns the path (:class:`str`).
	)stris_dirosr   )r   str_paths     r   append_dir_sepr"   4   s0     IIKKMM 
bf(r   patternsfilesall_matchesMatchDetailc                 X   t          |t                    r|nt          |          }i }| D ]~}|j        u|                    |          }|j        rQ|D ]M}||v r4|r!||         j                            |           )|||         j        d<   :t          |g          ||<   Nv|D ]}||= |S )a  
	Matches the files to the patterns, and returns which patterns matched
	the files.

	*patterns* (:class:`~collections.abc.Iterable` of :class:`~pathspec.pattern.Pattern`)
	contains the patterns to use.

	*files* (:class:`~collections.abc.Iterable` of :class:`str`) contains
	the normalized file paths to be matched against *patterns*.

	*all_matches* (:class:`boot` or :data:`None`) is whether to return all
	matches patterns (:data:`True`), or only the last matched pattern
	(:data:`False`). Default is :data:`None` for :data:`False`.

	Returns the matched files (:class:`dict`) which maps each matched file
	(:class:`str`) to the patterns that matched in order (:class:`.MatchDetail`).
	Nr   )
isinstanceCollectionTypelistincludematchr#   appendr&   )	r#   r$   r%   	all_filesreturn_filespatternresult_filesresult_filefiles	            r   detailed_match_filesr4   F   s    , !77HUUT%[[  W_ --	**<o # 9 9|# 9	 7K )009999/6|K )!,,"-wi"8"8l;9   	d		r   c                     d | D             S )z
	Filters out null-patterns.

	*patterns* (:class:`Iterable` of :class:`.Pattern`) contains the
	patterns.

	Returns the patterns (:class:`list` of :class:`.Pattern`).
	c                      g | ]}|j         	|S N)r+   )r   __pats     r   r   z$_filter_patterns.<locals>.<listcomp>}   s0     	 	 	
]		 	 	r   r   r#   s    r   _filter_patternsr:   t   s#    	 		 	 	 r   valuec                 f    t          | t                    ot          | t          t          f           S )z
	Check whether the value is an iterable (excludes strings).

	*value* is the value to check,

	Returns whether *value* is a iterable (:class:`bool`).
	)r(   IterableTyper   bytes)r;   s    r   _is_iterabler?      s*     	5,''O
53,0O0O,OOr   rooton_errorfollow_links	TreeEntryc              #      K   |"t          |          st          d|d          |d}t          t          j                            |           di ||          E d{V  dS )a  
	Walks the specified directory for all files and directories.

	*root* (:class:`str` or :class:`os.PathLike`) is the root directory to
	search.

	*on_error* (:class:`~collections.abc.Callable` or :data:`None`)
	optionally is the error handler for file-system exceptions. It will be
	called with the exception (:exc:`OSError`). Reraise the exception to
	abort the walk. Default is :data:`None` to ignore file-system
	exceptions.

	*follow_links* (:class:`bool` or :data:`None`) optionally is whether
	to walk symbolic links that resolve to directories. Default is
	:data:`None` for :data:`True`.

	Raises :exc:`RecursionError` if recursion is detected.

	Returns an :class:`~collections.abc.Iterator` yielding each file or
	directory entry (:class:`.TreeEntry`) relative to *root*.
	Nz	on_error: is not callable.T )callable	TypeError_iter_tree_entries_nextr    r   abspathr@   rA   rB   s      r   iter_tree_entriesrL      s      4  =(!3!3 =;h;;;<<< ,#BGOOD$9$92r8\ZZZZZZZZZZZr   	root_fulldir_relmemoc           	   #     K   t           j                            | |          }t           j                            |          }||vr|||<   nt	          |||         |          t          j        |          5 }|D ]>}t           j                            ||j                  }		 |                    d          }
n$# t          $ r}| ||           Y d}~\d}~ww xY w|	                                r:	 |                                }n&# t          $ r}| ||           Y d}~d}~ww xY w|
}|
                    |          r3t          |j        |	|
|          V  t          | |	|||          E d{V  |                                s|	                                rt          |j        |	|
|          V  @	 ddd           n# 1 swxY w Y   ||= dS )aq  
	Scan the directory for all descendant files.

	*root_full* (:class:`str`) the absolute path to the root directory.

	*dir_rel* (:class:`str`) the path to the directory to scan relative to
	*root_full*.

	*memo* (:class:`dict`) keeps track of ancestor directories
	encountered. Maps each ancestor real path (:class:`str`) to relative
	path (:class:`str`).

	*on_error* (:class:`~collections.abc.Callable` or :data:`None`)
	optionally is the error handler for file-system exceptions.

	*follow_links* (:class:`bool`) is whether to walk symbolic links that
	resolve to directories.

	Yields each entry (:class:`.TreeEntry`).
	)	real_path
first_pathsecond_pathF)follow_symlinksN)r    r   joinrealpathRecursionErrorscandirnamestatOSError
is_symlinkr   rC   rI   is_file)rM   rN   rO   rA   rB   dir_fulldir_real	scan_iternode_entnode_rel
node_lstate	node_stats                r   rI   rI      s     6 GLLG,,GX&&
 D [$x..d8nRYZZZZj !Di D Dhgll7HM228u55JJ
    Xa[[[HHHH
  	YY    hqkkkXXXX
 Ioolo33 	D HM8Z
C
CCCC&y(D(LYYYYYYYYYY Dh1133 D
HM8Z
C
CCCC?D!D !D !D !D !D !D !D !D !D !D !D !D !D !D !DP 
(^^^sg   8+G$B;:G;
CCGCG4D	G	
D*D% G%D**BGGGc              #   p   K   t          | ||          D ] }|                    |          s	|j        V  !dS )a  
	Walks the specified directory for all files.

	*root* (:class:`str` or :class:`os.PathLike`) is the root directory to
	search for files.

	*on_error* (:class:`~collections.abc.Callable` or :data:`None`)
	optionally is the error handler for file-system exceptions. It will be
	called with the exception (:exc:`OSError`). Reraise the exception to
	abort the walk. Default is :data:`None` to ignore file-system
	exceptions.

	*follow_links* (:class:`bool` or :data:`None`) optionally is whether
	to walk symbolic links that resolve to directories. Default is
	:data:`None` for :data:`True`.

	Raises :exc:`RecursionError` if recursion is detected.

	Returns an :class:`~collections.abc.Iterator` yielding the path to
	each file (:class:`str`) relative to *root*.
	rA   rB   N)rL   r   r   )r@   rA   rB   entrys       r   iter_tree_filesri     sS      4  xlSSS  U	l	#	# 	 r   c                 ^    t          j        dt          d           t          | ||          S )zg
	DEPRECATED: The :func:`.iter_tree` function is an alias for the
	:func:`.iter_tree_files` function.
	zCutil.iter_tree() is deprecated. Use util.iter_tree_files() instead.   
stacklevelrg   )warningswarnDeprecationWarningri   rK   s      r   	iter_treerq   "  s<    
 
G1& & & & 	xlKKKKr   rY   c                     t           |          S )z
	Lookups a registered pattern factory by name.

	*name* (:class:`str`) is the name of the pattern factory.

	Returns the registered pattern factory (:class:`~collections.abc.Callable`).
	If no pattern factory is registered, raises :exc:`KeyError`.
	)_registered_patterns)rY   s    r   lookup_patternrt   -  s     	T""r   r3   c                 Z    d}| D ]%}|j         |                    |          |j         }&|S )a7  
	Matches the file to the patterns.

	*patterns* (:class:`~collections.abc.Iterable` of :class:`~pathspec.pattern.Pattern`)
	contains the patterns to use.

	*file* (:class:`str`) is the normalized file path to be matched
	against *patterns*.

	Returns :data:`True` if *file* matched; otherwise, :data:`False`.
	F)r+   
match_file)r#   r3   matchedr0   s       r   rv   rv   9  sE       W_  oGr   c                     t          j        dt          d           t          |           }t	                      }|D ]'}t          ||          r|                    |           (|S )a  
	DEPRECATED: This is an old function no longer used. Use the :func:`.match_file`
	function with a loop for better results.

	Matches the files to the patterns.

	*patterns* (:class:`~collections.abc.Iterable` of :class:`~pathspec.pattern.Pattern`)
	contains the patterns to use.

	*files* (:class:`~collections.abc.Iterable` of :class:`str`) contains
	the normalized file paths to be matched against *patterns*.

	Returns the matched files (:class:`set` of :class:`str`).
	zWutil.match_files() is deprecated. Use util.match_file() with a loop for better results.rk   rl   )rn   ro   rp   r:   setrv   add)r#   r$   use_patternsr/   r3   s        r   match_filesr|   N  s{    $ 
1& & & &
 !**  Td## Dr   
separatorsc                     |t           }t          |           }|D ]"}|                    |t          j                  }#|                    d          r|dd         }n|                    d          r
|dd         }|S )a  
	Normalizes the file path to use the POSIX path separator (i.e.,
	:data:`'/'`), and make the paths relative (remove leading :data:`'/'`).

	*file* (:class:`str` or :class:`os.PathLike`) is the file path.

	*separators* (:class:`~collections.abc.Collection` of :class:`str`; or
	:data:`None`) optionally contains the path separators to normalize.
	This does not need to include the POSIX path separator (:data:`'/'`),
	but including it will not affect the results. Default is :data:`None`
	for :data:`NORMALIZE_PATH_SEPS`. To prevent normalization, pass an
	empty container (e.g., an empty tuple :data:`()`).

	Returns the normalized file path (:class:`str`).
	N/r   z./rk   )NORMALIZE_PATH_SEPSr   replacer   r   
startswith)r3   r}   	norm_filer   s       r   normalize_filer   o  s    (  #"* YY 4 4SY]33)) m))4   m)r   c                     t          j        dt          d           i }| D ]9}t          ||          }||v r||                             |           3|g||<   :|S )a  
	DEPRECATED: This function is no longer used. Use the :func:`.normalize_file`
	function with a loop for better results.

	Normalizes the file paths to use the POSIX path separator.

	*files* (:class:`~collections.abc.Iterable` of :class:`str` or
	:class:`os.PathLike`) contains the file paths to be normalized.

	*separators* (:class:`~collections.abc.Collection` of :class:`str`; or
	:data:`None`) optionally contains the path separators to normalize.
	See :func:`normalize_file` for more information.

	Returns a :class:`dict` mapping each normalized file path (:class:`str`)
	to the original file paths (:class:`list` of :class:`str` or
	:class:`os.PathLike`).
	z_util.normalize_files() is deprecated. Use util.normalize_file() with a loop for better results.rk   rl   )r}   )rn   ro   rp   r   r-   )r$   r}   
norm_filesr   r   s        r   normalize_filesr     s    * 
$1& & & &
  " "TTj999)* "i%%%% 6:ir   pattern_factoryoverridec                     t          | t                    st          d| d          t          |          st          d|d          | t          v r|st          | t          |                    |t          | <   dS )aE  
	Registers the specified pattern factory.

	*name* (:class:`str`) is the name to register the pattern factory
	under.

	*pattern_factory* (:class:`~collections.abc.Callable`) is used to
	compile patterns. It must accept an uncompiled pattern (:class:`str`)
	and return the compiled pattern (:class:`.Pattern`).

	*override* (:class:`bool` or :data:`None`) optionally is whether to
	allow overriding an already registered pattern under the same name
	(:data:`True`), instead of raising an :exc:`AlreadyRegisteredError`
	(:data:`False`). Default is :data:`None` for :data:`False`.
	zname:z is not a string.zpattern_factory:rE   N)r(   r   rH   rG   rs   AlreadyRegisteredError)rY   r   r   s      r   register_patternr     s    ( 	4 53$333444!! KI_IIIJJJ   A At%9$%?@@@-dr   c                        e Zd ZdZdedeegef         ddf fdZe	defd            Z
e	defd            Ze	deegef         fd	            Z xZS )
r   z|
	The :exc:`AlreadyRegisteredError` exception is raised when a pattern
	factory is registered under a name already in use.
	rY   r   r   Nc                 Z    t          t          |                               ||           dS )z
		Initializes the :exc:`AlreadyRegisteredError` instance.

		*name* (:class:`str`) is the name of the registered pattern.

		*pattern_factory* (:class:`~collections.abc.Callable`) is the
		registered pattern factory.
		N)superr   __init__)selfrY   r   	__class__s      r   r   zAlreadyRegisteredError.__init__  s,     %%..t_EEEEEr   c                 D    d                     | j        | j                  S )4
		*message* (:class:`str`) is the error message.
		zG{name!r} is already registered for pattern factory:{pattern_factory!r}.)rY   r   )formatrY   r   r   s    r   messagezAlreadyRegisteredError.message  s.    
 
S	Y	Y	' 
Z 
 
 r   c                     | j         d         S )zB
		*name* (:class:`str`) is the name of the registered pattern.
		r   argsr   s    r   rY   zAlreadyRegisteredError.name  s    
 
1r   c                     | j         d         S )za
		*pattern_factory* (:class:`~collections.abc.Callable`) is the
		registered pattern factory.
		r   r   r   s    r   r   z&AlreadyRegisteredError.pattern_factory       
1r   )__name__
__module____qualname____doc__r   r   r   r   r   propertyr   rY   r   __classcell__r   s   @r   r   r     s         
FF VHg-.F 	F F F F F F c    ( 3    ( hx'89    (    r   r   c                        e Zd ZdZdedededdf fdZedefd            Zedefd	            Zedefd
            Z	edefd            Z
 xZS )rW   zN
	The :exc:`RecursionError` exception is raised when recursion is
	detected.
	rQ   rR   rS   r   Nc                 \    t          t          |                               |||           dS )a+  
		Initializes the :exc:`RecursionError` instance.

		*real_path* (:class:`str`) is the real path that recursion was
		encountered on.

		*first_path* (:class:`str`) is the first path encountered for
		*real_path*.

		*second_path* (:class:`str`) is the second path encountered for
		*real_path*.
		N)r   rW   r   )r   rQ   rR   rS   r   s       r   r   zRecursionError.__init__  s-    $ &&y*kJJJJJr   c                     | j         d         S )zx
		*first_path* (:class:`str`) is the first path encountered for
		:attr:`self.real_path <RecursionError.real_path>`.
		r   r   r   s    r   rR   zRecursionError.first_path%  r   r   c                 P    d                     | j        | j        | j                  S )r   zDReal path {real!r} was encountered at {first!r} and then {second!r}.)realfirstsecond)r   rQ   rR   rS   r   s    r   r   zRecursionError.message-  s3    
 
P	V	V	

 
W 
 
 r   c                     | j         d         S )zV
		*real_path* (:class:`str`) is the real path that recursion was
		encountered on.
		r   r   r   s    r   rQ   zRecursionError.real_path8  r   r   c                     | j         d         S )zz
		*second_path* (:class:`str`) is the second path encountered for
		:attr:`self.real_path <RecursionError.real_path>`.
		rk   r   r   s    r   rS   zRecursionError.second_path@  r   r   )r   r   r   r   r   r   r   rR   r   rQ   rS   r   r   s   @r   rW   rW     s        
KK K 	K
 K K K K K K(     ( c    (     ( #    (    r   rW   c                   2    e Zd ZdZdZdee         ddfdZdS )r&   z>
	The :class:`.MatchDetail` class contains information about
	r9   r#   r   Nc                     || _         dS )z
		Initialize the :class:`.MatchDetail` instance.

		*patterns* (:class:`~collections.abc.Sequence` of :class:`~pathspec.pattern.Pattern`)
		contains the patterns that matched the file in the order they were
		encountered.
		Nr9   )r   r#   s     r   r   zMatchDetail.__init__Q  s     $- r   )r   r   r   r   	__slots__r   r   r   r   r   r   r&   r&   I  sL         
 hw/ D      r   c            
           e Zd ZdZdZdededej        dej        ddf
d	Zdd
e	e
         de
fdZdd
e	e
         de
fdZde
fdZdd
e	e
         dej        fdZdS )rC   zR
	The :class:`.TreeEntry` class contains information about a file-system
	entry.
	_lstatrY   r   _statrY   r   lstatrZ   r   Nc                 D    || _         	 || _        	 || _        	 || _        dS )aP  
		Initialize the :class:`.TreeEntry` instance.

		*name* (:class:`str`) is the base name of the entry.

		*path* (:class:`str`) is the relative path of the entry.

		*lstat* (:class:`os.stat_result`) is the stat result of the direct
		entry.

		*stat* (:class:`os.stat_result`) is the stat result of the entry,
		potentially linked.
		Nr   )r   rY   r   r   rZ   s        r   r   zTreeEntry.__init__k  s?    * !&$+
 $) $)  $$* r   rB   c                 \    |d}|r| j         n| j        }t          j        |j                  S )a<  
		Get whether the entry is a directory.

		*follow_links* (:class:`bool` or :data:`None`) is whether to follow
		symbolic links. If this is :data:`True`, a symlink to a directory
		will result in :data:`True`. Default is :data:`None` for :data:`True`.

		Returns whether the entry is a directory (:class:`bool`).
		NT)r   r   rZ   S_ISDIRst_moder   rB   re   s      r   r   zTreeEntry.is_dir  6      <(9djjdk)	i'	(	((r   c                 \    |d}|r| j         n| j        }t          j        |j                  S )aE  
		Get whether the entry is a regular file.

		*follow_links* (:class:`bool` or :data:`None`) is whether to follow
		symbolic links. If this is :data:`True`, a symlink to a regular file
		will result in :data:`True`. Default is :data:`None` for :data:`True`.

		Returns whether the entry is a regular file (:class:`bool`).
		NT)r   r   rZ   S_ISREGr   r   s      r   r]   zTreeEntry.is_file  r   r   c                 >    t          j        | j        j                  S )zC
		Returns whether the entry is a symbolic link (:class:`bool`).
		)rZ   S_ISLNKr   r   r   s    r   r\   zTreeEntry.is_symlink  s     
dk)	*	**r   c                 *    |d}|r| j         n| j        S )a9  
		Get the cached stat result for the entry.

		*follow_links* (:class:`bool` or :data:`None`) is whether to follow
		symbolic links. If this is :data:`True`, the stat result of the
		linked file will be returned. Default is :data:`None` for :data:`True`.

		Returns that stat result (:class:`os.stat_result`).
		NT)r   r   )r   rB   s     r   rZ   zTreeEntry.stat  s$      <#	44r   r7   )r   r   r   r   r   r   r    stat_resultr   r   boolr   r]   r\   rZ   r   r   r   rC   rC   b  s         1)) 	) 
	)
 	) ) ) ) )V) ) )$ ) ) ) ) ) )$ )4 ) ) ) ) + + + + +5 5htn 5 5 5 5 5 5 5r   r7   )NN)5r   r    os.pathpathlibr   rZ   rn   collections.abcr   r)   r   r=   r   typingr   r   r   r	   r
   r   r   r   r   r   r0   r   r   altsepr   rs   Pathr   r"   r   r4   r:   r?   rL   rI   ri   rq   rt   rv   r|   r   r   r   	Exceptionr   rW   objectr&   rC   r   r   r   <module>r      s    
			                                               
 
 
 
 
 
 vry!   
   #    *  $+ +G++ tn+ 
#}
	+ + + +\x0 T']     P P P P P P !% $ [  [S(] [H [ ~ [ k	 [  [  [  [FNN
N CH~N 	N
 N kN N N Nf !% $ S(]H ~ c]	   >L L L L	# 	#6(G*;!< 	# 	# 	# 	#'* # $    *G 	X   F *.% %S(]%jo&% 	% % % %T *." "sH}%&"jo&" 
#tE#x-()
)*" " " "P !. .
.F8W,-. D>. 
	. . . .@, , , , ,Y , , ,^; ; ; ; ;Y ; ; ;|    &   2g5 g5 g5 g5 g5 g5 g5 g5 g5 g5r   