
    UAj                    t    S r SSKJr  SSKJr  SSKJr  SSKJr  \" S5      r	Sr
SrSS	 jr\
4SS
 jjrSS jrg)u  Read-only web project discovery and classification.

We classify a directory by the presence of marker files only. We NEVER read the
contents of wp-config.php, .env, composer.json secrets, etc. — only that the
files exist. SECURITY: no .env values, no credentials, no private keys.
    )annotations)Path)Any)
get_loggerzdiscovery.projects)z/var/wwwz/srv/wwwz/srv   c                l   U S-  R                  5       (       a  S[        U 5      SS.$ U S-  R                  5       (       a'  U S-  R                  5       (       a  S[        U 5      SS.$ U S-  R                  5       (       a  S	[        U 5      S	S.$ U S
-  R                  5       (       a  S[        U 5      SS.$ g)zEClassify a single directory. Returns None if it isn't a project root.zwp-config.php	wordpressphp)typepathruntimeartisanzcomposer.jsonlaravelzpackage.jsonnodez
index.htmlstaticN)existsstr)r   s    <D:\Programs\laragon\www\wolf\agent\src\discovery\projects.pyclassifyr      s    &&((#SY5IIy  ""(>'F'F'H'H!3t9GG~%%''D	fEE|##%% #d)II    c                B   / n[        5       nU  H  n[        U5      nUR                  5       (       d  M%  [        U[        5       HS  n[        U5      U;   a  M  [        U5      nU(       d  M(  UR                  [        U5      5        UR                  U5        MU     M     U$ )zDScan common web roots and classify each immediate project directory.)	setr   is_dir_candidate_dirs
_MAX_DEPTHr   r   addappend)rootsprojectsseenrootbase	candidateresults          r   find_projectsr%   "   s    %'HUDDz{{}}(z:I9~%i(FvY(' ;	  Or   c              #     #    U v   [        SUS-   5       HL  nSR                  S/U-  5      n U R                  U5       H  nUR                  5       (       d  M  Uv   M      MN     g! [         a     M^  f = f7f)z?Yield directories up to max_depth below base (and base itself).   /*N)rangejoinglobr   OSError)r"   	max_depthdepthpatternr   s        r   r   r   4   sn     
Jq)a-(((C55=)			'*;;==J + )  		s.   ,A8'A'A'"A8'
A51A84A55A8N)r   r   returnzdict[str, Any] | None)r   ztuple[str, ...]r1   zlist[dict[str, Any]])r"   r   r.   int)__doc__
__future__r   pathlibr   typingr   loggerr   log
_WEB_ROOTSr   r   r%   r    r   r   <module>r;      sA    #   %&-


 ,6 $
r   