ó
    ¥-EjO  ã                  óÒ   • S r SSKJr  SSKrSSKJrJr  SSKJr  SSKJ	r	  SSK
Jr  SSKJrJrJrJrJrJr  SS	KJr  \" S
5      rSSKrSrSrSS jrSS jrSS jrSS jrSSS jjrg)u  Full discovery: the complete read-only inventory.

Orchestrates the individual discovery modules, writes the snapshot to
/var/lib/wolfpanel/discovery/last.json, and optionally uploads it to the
Central API. Strictly read-only â€” no server state is changed.
é    )ÚannotationsN)ÚdatetimeÚtimezone)ÚPath)ÚAny)ÚConfig)ÚgitÚprojectsÚservicesÚsystemÚsftpÚ	databases)Ú
get_loggerzdiscovery.full)z/etc/nginx/sites-enabledz/etc/nginx/conf.dz/etc/apache2/sites-enabled)z/etc/letsencrypt/livez/etc/ssl/certsc                ó€  • SnSnU R                  5        GH#  nSU;   a  UR                  SS5      S   nUR                  5       nU(       d  M8  U(       d=  [        R                  " SU5      nU(       a  UR                  S5      R                  5       nU(       a  M…  [        R                  " SU5      nU(       d  M¥  UR                  S5      R                  5       nUR                  S5      (       a  UR                  S5      (       d,  UR                  S5      (       a  UR                  S5      (       a  USS	 nUnGM&     X4$ )
zOParse server_name and root from a config file using simple regex/string checks.NÚ#é   r   z^server_name\s+([^;]+);z^root\s+([^;]+);Ú"Ú'éÿÿÿÿ)Ú
splitlinesÚsplitÚstripÚreÚmatchÚgroupÚ
startswithÚendswith)ÚcontentÚserver_nameÚ	root_pathÚlineÚmÚvals         Ú8D:\Programs\laragon\www\wolf\agent\src\discovery\full.pyÚ_parse_nginx_configr%      s  € à€KØ€IØ×"Ñ"×$ˆØ�$‹;Ø—:‘:˜c 1Ó% aÑ(ˆDØ�z‰z‹|ˆÞÙæÜ—’Ð3°TÓ:ˆAÞØŸg™g a›j×.Ñ.Ó0�çˆyÜ—’Ð,¨dÓ3ˆAßˆqØ—g‘g˜a“j×&Ñ&Ó(�Ø—N‘N 3×'Ñ'¨C¯L©L¸×,=Ñ,=À3Ç>Á>ÐRU×CVÑCVÐ[^×[gÑ[gÐhk×[lÑ[lØ˜a ˜)�CØ“	ñ% %ð( Ð!Ð!ó    c            	     ól  • / n [          H—  n[        U5      nUR                  5       (       d  M%  UR                  S5       H]  nUR	                  5       (       d  M  [        U5      nSnSn UR                  SSS9n[        U5      u  pVU R                  SUUUS.5        M_     M™     U $ ! [         a     N,f = f)z=List vhost config file paths and parse server_name/root_path.Ú*Núutf-8Úignore)ÚencodingÚerrorsÚvhosts)ÚcategoryÚpathr   r    )
Ú_VHOST_DIRSr   Úis_dirÚglobÚis_fileÚstrÚ	read_textr%   Ú	ExceptionÚappend)ÚfoundÚ	directoryÚbaseÚpÚpath_strr   r    r   s           r$   Ú_vhost_filesr=   7   s³   € à"$€Eß ˆ	Ü�I‹ˆØ�;‰;�=‹=Ø—Y‘Y˜s–^�Ø—9‘9—;“;Ü" 1›v�HØ"&�KØ $�IðØ"#§+¡+°wÀx +Ð"P˜Ü1DÀWÓ1MÑ.˜ð —L‘LØ$,Ø (Ø'2Ø%.ñ	"ö ó $ñ !ð& €Løô %ó Ùðús   Á)B&Â&
B3Â2B3c                 ó$  • / n [          GH‚  n[        U5      nUR                  5       (       d  M&  [        UR	                  S5      5      SS [        UR	                  S5      5      -    GH  nSUR
                  ;   d  SUR
                  R                  5       ;   a  M4  [        R                  " SSS	S
S[        U5      /5      n[        R                  " SSS
SS[        U5      /5      nSn/ nU(       aƒ  [        R                  " SU5      nU(       aN  UR                  S5      n	[        R                  " SU	5      n
U
(       a  U
R                  S5      R                  5       n[        R                  " SU5      n/ nU(       a  UR                  U5        U H  nXË;  d  M
  UR                  U5        M     U(       a  SR!                  U5      OSnS[        U5      R#                  SS5      ;   a  SOSnSnUS:X  aH  [        R                  " S[        U5      R#                  SS5      5      nU(       a  UR                  S5      nU R                  S[        U5      U(       a#  UR                  5       R%                  SS5      S   OSUUUS.5        GM"     GM…     U $ )u”   Locate certificate files and read their details via openssl if present.

SECURITY: only certificates (public) are inspected â€” never private keys.
z**/*.pemNéÈ   z**/fullchain*ÚprivkeyÚkeyÚopensslÚx509z-enddatez-nooutz-inz-textzSubject:\s*(.*?)(?:\n|$)r   z\bCN\s*=\s*([^,\/\n]+)zDNS:([a-zA-Z0-9.*-]+)Ú,z/etc/letsencrypt/Ú\Ú/ÚletsencryptÚcustomz/etc/letsencrypt/live/([^/]+)Ússl_certificatesÚ=r   )r.   r/   Ú	not_afterÚdomainsÚproviderÚ	cert_name)Ú
_CERT_DIRSr   r1   Úlistr2   ÚnameÚlowerr   Úrun_readonlyr4   r   Úsearchr   r   Úfindallr7   ÚjoinÚreplacer   )Úcertsr9   r:   ÚcertÚenddateÚcert_detailsÚcnÚ	dns_namesÚ	subject_mÚsubject_lineÚcn_mÚall_domainsrQ   Údomains_strrM   rN   r"   s                    r$   Ú_ssl_certificatesrc   P   s.  € ð
 #%€Eß�Zˆ	Ü�I‹ˆØ�{‰{�}‰}ÙÜ˜Ÿ™ :Ó.Ó/°°Ð5¼¸T¿Y¹YÀÓ=WÓ8XÕXˆDØ˜DŸI™IÓ%¨°$·)±)·/±/Ó2CÓ)CÙÜ×)Ò)Ø˜F J°¸%ÄÀTÃÐKóˆGô "×.Ò.Ø˜F H¨g°u¼cÀ$»iÐHóˆLð ˆBØˆIÞÜŸIšIÐ&AÀ<ÓP�	ÞØ#,§?¡?°1Ó#5�LÜŸ9š9Ð%>ÀÓM�DÞØ!ŸZ™Z¨›]×0Ñ0Ó2˜ÜŸJšJÐ'?ÀÓN�	àˆKÞØ×"Ñ" 2Ô&Û!�ØÕ*Ø×&Ñ& tÖ,ñ "ö 4?˜#Ÿ(™( ;Ô/ÀDˆKà(;¼sÀ4»y×?PÑ?PÐQUÐWZÓ?[Ó([‘}ÐaiˆHØˆIØ˜=Ó(Ü—I’IÐ>ÄÀDÃ	×@QÑ@QÐRVÐX[Ó@\Ó]�ÞØ !§¡¨£
�Ià�L‰Là 2Ü ›IÞFM §¡£×!6Ñ!6°s¸AÓ!>¸rÒ!BÐSWØ*Ø (Ø!*ñ÷	ôI Yñ	  ðd €Lr&   c            	     óè  • [         R                  " 5       n 0 S[        R                  " 5       _S[        R                  " 5       _S[        R
                  " 5       _S[        R                  " 5       _S[        R                  " 5       _S[        R                  " 5       _S[        R                  " 5       _S[        R                  " 5       _S	[        R                  " 5       _S
[        R                  " 5       _S[        R                  " 5       _S[         R                  " 5       _SU _S[         R                  " 5       _S[         R                   " 5       _S[         R"                  " 5       _S[         R$                  " 5       _['        5       [)        5       [*        R,                  " 5       [.        R0                  " 5       [2        R4                  " 5       ["        R6                  " 5       ["        R8                  " 5       S.E$ )z$Build the full inventory dictionary.ÚosÚkernelÚ	cpu_countÚmemoryÚdiskÚload_averageÚuptimeÚprivate_ipsÚ	public_ipÚnetwork_interfacesÚ
open_portsÚsystemd_servicesÚweb_serversÚlanguage_runtimesÚ
containersr   Ú	cron_jobs)r-   rI   Úgit_repositoriesr
   Ú
sftp_usersÚdatabase_schemasÚdatabase_users)r   rq   r   Úos_inforf   rg   Úmemory_usageÚ
disk_usagerj   Úuptime_secondsrl   rm   rn   ro   rp   rr   rs   r   rt   r=   rc   r	   Úfind_repositoriesr
   Úfind_projectsr   Údiscover_sftp_usersÚdiscover_database_schemasÚdiscover_database_users)Úwebs    r$   Úcollectrƒ   ‹   s»  € ä
×
Ò
Ó
 €CðØŒf�nŠnÓðà”&—-’-“/ðð 	”V×%Ò%Ó'ðð 	”&×%Ò%Ó'ð	ð
 	”×!Ò!Ó#ðð 	œ×+Ò+Ó-ðð 	”&×'Ò'Ó)ðð 	”v×)Ò)Ó+ðð 	”V×%Ò%Ó'ðð 	œf×7Ò7Ó9ðð 	”f×'Ò'Ó)ðð 	œH×5Ò5Ó7ðð 	�sðð 	œX×7Ò7Ó9ðð 	”h×)Ò)Ó+ðð  	”X×'Ò'Ó)ð!ð" 	”X×'Ò'Ó)ð#ô$ “.Ü-Ó/Ü×1Ò1Ó3Ü×*Ò*Ó,Ü×.Ò.Ó0Ü%×?Ò?ÓAÜ#×;Ò;Ó=ò1ð r&   c                ó  • [        5       nU R                  U R                  [        R                  " [
        R                  5      R                  5       US.nU R                  R                  SSS9  U R                  S-  nUR                  [        R                  " USS9SS9  [        R                  S	U5        U(       a  S
SKJnJn   U" U USU" U5      5        U$ U$ ! [$         a!  n[        R'                  SU5         SnAU$ SnAff = f)z�Collect, persist the snapshot, and optionally upload it.

Returns the snapshot dict. Upload failures are logged but never fatal.
)Ú	server_idÚagent_versionÚcollected_atÚ	discoveryT)ÚparentsÚexist_okz	last.jsoné   )Úindentr)   )r+   z discovery snapshot written to %sr   )Úcategories_from_inventoryÚupload_inventoryÚfullz9discovery upload failed (will rely on local snapshot): %sN)rƒ   r…   r†   r   Únowr   ÚutcÚ	isoformatÚdiscovery_dirÚmkdirÚ
write_textÚjsonÚdumpsÚlogÚinfoÚdiscovery.uploadr�   rŽ   r6   Úwarning)	ÚconfigÚ
api_clientÚuploadÚ	inventoryÚsnapshotÚsnapshot_pathr�   rŽ   Úexcs	            r$   Úrunr£   ª   sô   € ô
 “	€Ià×%Ñ%Ø×-Ñ-Ü Ÿš¤X§\¡\Ó2×<Ñ<Ó>Øñ	€Hð ×Ñ×Ñ t°dÐÑ;Ø×(Ñ(¨;Ñ6€MØ×ÑœTŸZšZ¨¸Ñ;ÀgÐÑNÜ‡H�HÐ/°Ô?æßPð	ZÙØØØÙ)¨)Ó4ô	ð €Oˆ8€Oøô ó 	ZÜ�K‰KÐSÐUX×YÐYà€Oûð	Zús   ÃC Ã
DÃ'DÄD)r   r4   Úreturnztuple[str | None, str | None])r¤   zlist[dict[str, Any]])r¤   údict[str, Any])T)rœ   r   rž   Úboolr¤   r¥   )Ú__doc__Ú
__future__r   r–   r   r   Úpathlibr   Útypingr   rœ   r   rˆ   r	   r
   r   r   r   r   Úloggerr   r˜   r   r0   rO   r%   r=   rc   rƒ   r£   © r&   r$   Ú<module>r­      s\   ðñõ #ã ß 'Ý Ý å ß F× FÝ áÐ!Ó"€ã 	ð ^€Ø8€
ô"ô6ô28ôv÷> r&   