
    7j                        d Z ddlmZ ddlZddlmZ ddlmZ ddlm	Z	 ddl
mZ  ed      Zd	Zd
ZddZddZddZefddZddZy)zRead-only Git repository discovery.

For every repository found we collect only non-sensitive metadata. Remote URLs
are sanitized to strip any embedded credentials/tokens. We never read git
config secrets, stored credentials, or commit contents.
    )annotationsN)Path)Any)run_readonly)
get_loggerzdiscovery.git)z/var/wwwz/srvz/homez/opt   c                R    | syt        j                  dd| j                               S )zStrip credentials from a remote URL.

    https://user:token@github.com/x/y.git -> https://github.com/x/y.git
    Leaves SSH-style remotes (git@host:repo) untouched, as they carry no secret.
    Nz(https?://)[^/@]*@z\1)resubstrip)urls    G/var/www/downloads.wolfpanel.net/public_html/agent/src/discovery/git.pysanitize_remoter      s$     66'		<<    c                \    t        ddt        |       g|      }|r|j                         S d S )Ngitz-C)r   strr   )repoargsoutputs      r   _gitr   $   s/    5$D	9D9:F#6<<>--r   c           	         | j                   }t        |g d      }t        |ddg      }t        |      t        |      t        |g d      t        |g d      t        |g d      t	        |      dS )z:Collect the allow-listed metadata for a single repository.)configz--getzremote.origin.urlstatusz--porcelain)z	rev-parsez--abbrev-refHEAD)log-1z--format=%H)r   r   z--format=%cI)path
remote_urlcurrent_branchlast_commit_hashlast_commit_datedirty_state)parentr   r   r   bool)repo_dirr   remoter   s       r   inspect_repor(   )   sj    ??D$@AF$=12FD	%f-t%JK 'CD 'DEF| r   c                v   g }t               }| D ]z  }t        |      }|j                         st        |dt              D ]H  }t        |j                        }||v r|j                  |       	 |j                  t        |             J | |S # t        $ r!}t        j                  d||       Y d}~td}~ww xY w)z;Find .git directories under the scan roots (bounded depth).z.gitzfailed to inspect %s: %sN)setr   is_dir_bounded_glob
_MAX_DEPTHr   r$   addappendr(   OSErrorr   debug)rootsreposseenrootbasegit_dirkeyexcs           r   find_repositoriesr:   8   s    "$EUD DDz{{}$T6:> 	DGgnn%Cd{HHSMD\'23	D	D L  D		4gsCCDs   .B	B8B33B8c              #     K   t        |dz         D ]9  }|rdj                  dg|z  |gz         n|}	 | j                  |      E d{    ; y7 # t        $ r Y Jw xY ww)z;Yield paths named `name` up to max_depth levels below base.   /*N)rangejoinglobr0   )r6   name	max_depthdepthpatterns        r   r,   r,   L   sj     y1}% 6;#((C55=D612	yy))) * 		s:   /AAAAAA	AAAA)r   
str | NonereturnrF   )r   r   r   z	list[str]rG   rF   )r&   r   rG   zdict[str, Any])r2   ztuple[str, ...]rG   zlist[dict[str, Any]])r6   r   rB   r   rC   int)__doc__
__future__r   r
   pathlibr   typingr   discovery.systemr   loggerr   r   _SCAN_ROOTSr-   r   r   r(   r:   r,    r   r   <module>rQ      sR    # 	   ) ! 4
	=.
 0; (r   