Ë
    ãß²j!  ã                   óî  — U d Z ddlZddlZddlmZ ddlmZ ddlmZm	Z	m
Z
 ddlmZ  ej                  d«      ZdZd	Zg d
¢Zeed<   dZh d£Zdedefd„Zdedefd„Zdedefd„Zdedefd„Zd2ddœdedz  dedz  de	eef   fd„Zdede	ee
e   f   fd„Zdddddœdeded ed!edz  d"ed#ed$edefd%„Zdeddfd&„Z ded'edefd(„Z!	 d2d)dd*œd+ed,ed-ededz  d.ed/edz  defd0„Z"dede	ee
e   f   dz  fd1„Z#y)3a  Plugin-provided skill serving for ``skill_view`` (``plugin:skill`` names) plus the JSON /
file-serving helpers shared with the local-skill path. Helpers tests patch on the origin module
(``_is_skill_disabled``, ``_parse_frontmatter``, ``skill_matches_platform``) resolve lazily.é    N)Úsuppress)ÚPath)ÚAnyÚDictÚList)ÚSkillReadinessStatusztools.skills_toolé@   i   )	zignore previous instructionszignore all previouszyou are nowzdisregard yourzforget your instructionsznew instructions:zsystem prompt:z<system>z]]>Ú_INJECTION_PATTERNS)Ú
referencesÚ	templatesÚassetsÚscripts>   ú.mdú.pyú.shú.texú.ymlú.jsonú.yamlÚpayloadÚreturnc                 ó0   — t        j                  | d¬«      S )NF)Úensure_ascii)ÚjsonÚdumps)r   s    ú=/home/ubuntu/.hermes/hermes-agent/tools/skills_tool_plugin.pyÚ_jsonr      s   € Ü�:‰:�g¨EÔ2Ð2ó    Úerrorc                 ó"   — t        d| dœ|¥«      S )NF)Úsuccessr   )r   )r   Úextras     r   Ú_failr#      s   € Ü˜U¨UÑ<°eÐ<Ó=Ð=r   Úpathc                 ó(   — | j                  dd¬«      S )z¢utf-8-sig + errors="replace": user-authored SKILL.md may carry a Notepad BOM or stray
    bytes; pinning UTF-8 keeps skill_view deterministic across host locales.z	utf-8-sigÚreplace)ÚencodingÚerrors)Ú	read_text)r$   s    r   Ú_read_skill_textr*   !   s   € ð �>‰> ;°yˆ>ÓAÐAr   Údescriptionc                 óH   — t        | «      t        k  r| S | d t        dz
   dz   S )Né   z...)ÚlenÚMAX_DESCRIPTION_LENGTH)r+   s    r   Ú_truncate_descriptionr0   '   s/   € Ü
ˆ;ÓÔ1Ò1ØÐØÐ3Ô/°!Ñ3Ð4°uÑ<Ð<r   ©Úcontentr2   c                óœ   — ddl m} t        t        «      5  |j	                  |€t        | «      n|«      d   cddd«       S # 1 sw Y   i S xY w)zŸFrontmatter of *path* (or of *content*), ``{}`` on any read/parse failure.
    Parses via ``tools.skills_tool._parse_frontmatter`` so test patches are honored.r   ©Úskills_toolN)Útoolsr5   r   Ú	ExceptionÚ_parse_frontmatterr*   )r$   r2   Ú_sts      r   Ú_safe_frontmatterr:   -   sN   € õ )Ü	”)Ó	ñ aØ×%Ñ%ÀÀÔ&6°tÔ&<ÐU\Ó]Ð^_Ñ`÷a÷ añ aà€Iús   –!AÁAÚ	skill_dirc                 ó¶  — i }| j                  d«      D ]�  }|j                  «       r|j                  dk(  rŒ#t        |j	                  | «      «      }d|v r|j                  dd«      d   nd}|t        v s|j                  t        v sŒs|j                  |t        v r|ndg «      j                  |«       ŒŸ g t        ¢d‘­D �ci c]  }||v sŒ|||   “Œ c}S c c}w )zvNon-SKILL.md files grouped by support dir (+ "other" for known source extensions
    elsewhere); empty groups dropped.Ú*zSKILL.mdú/é   r   NÚother)ÚrglobÚis_fileÚnameÚstrÚrelative_toÚsplitÚ_SUPPORT_DIRSÚsuffixÚ_SKILL_FILE_EXTSÚ
setdefaultÚappend)r;   ÚgroupsÚfÚrelÚtopÚks         r   Ú_available_skill_filesrQ   6   sÑ   € ð $&€FØ�_‰_˜SÓ!ò XˆØ�y‰yŒ{˜aŸf™f¨
Ò2ØÜ�!—-‘- 	Ó*Ó+ˆØ&)¨S¡jˆc�i‰i˜˜QÓ Ò"°dˆØ”-Ñ 1§8¡8Ô/?Ò#?Ø×Ñ S¬MÑ%9™c¸wÈÓK×RÑRÐSVÕWðXð #<¤MÐ";°7Ñ";ÖK˜Q¸qÀFº{ˆAˆv�a‰y‰LÒKÐKùÒKs   Ã	CÃCF)ÚhintÚlist_availableÚread_error_prefixÚ	mark_readÚ
skill_rootÚ	file_pathÚlabelrR   rS   rT   rU   c                óB  — ddl m}m} |rd|ini }	 ||«      rt        di |	¤ŽS | |z  }
 ||
| «      x}rt        |fi |	¤ŽS |
j	                  «       s%|si nt        | «      ddœ}t        d|› d|› d�fi |¤ŽS 	 t        |
«      }|rt        |
«       t        d	||||
j                  t        |
«      dœ«      S # t        $ r= t        d	||d	d
|
j                  › d|
j                  «       j                  › d�dœ«      cY S t        $ r}|s‚ t        d|› d|› �«      cY d}~S d}~ww xY w)a<  Serve one linked file from a skill directory as a skill_view JSON result. ``hint``
    decorates traversal/containment errors; ``list_available`` adds the available-files listing
    on not-found (local); ``read_error_prefix`` wraps non-decode read errors (plugin) instead
    of propagating to the caller's handler.r   )Úhas_traversal_componentÚvalidate_within_dirrR   z0Use one of the available file paths listed above)Úavailable_filesrR   zFile 'z' not found in skill 'z'.Tz[Binary file: z, size: z bytes])r!   rC   ÚfileÚ	is_binaryr2   zFailed to read 'ú': N)r!   rC   r]   r2   Ú	file_typeÚ_source_path)z%Path traversal ('..') is not allowed.)Útools.path_securityrZ   r[   r#   rB   rQ   r*   ÚUnicodeDecodeErrorr   rC   ÚstatÚst_sizer7   Ú_mark_background_review_readrH   rD   )rV   rW   rX   rR   rS   rT   rU   rZ   r[   r"   ÚtargetÚ
path_errorÚlistingr2   Úexcs                  r   Ú_serve_skill_filerk   D   s`  € ÷ QÙ"ˆV�T‰N¨€EÙ˜yÔ)ÜÑFÀÑFÐFØ˜)Ñ#€FÙ(¨°Ó<Ð<€zÐ<Ü�ZÑ) 5Ñ)Ð)à�>‰>ÔÙ*‘"Ü5°jÓAØFñ1Hˆô �v˜i˜[Ð(>¸u¸gÀRÐHÑTÈGÑTÐTð	=Ü" 6Ó*ˆñ Ü$ VÔ,ÜØ °	ÀgØ—]‘]´C¸³KñAó Bð Bøô ò ^ÜØ U°IÈDØ'¨¯© }°H¸V¿[¹[»]×=RÑ=RÐ<SÐSZÐ[ñ]ó ^ò 	^ô ò =Ù ØÜÐ'¨	 {°#°c°UÐ;Ó<Õ<ûð=ús%   Á6B3 Â3ADÃ8DÄ DÄDÄDc                 óp   — 	 ddl m}  || «       y # t        $ r t        j	                  d| d¬«       Y y w xY w)Nr   )Ú!mark_background_review_skill_readz4Could not record background-review skill read for %sT)Úexc_info)Útools.skill_manager_guardsrm   r7   ÚloggerÚdebug)r$   rm   s     r   rf   rf   i   s8   € ðbÝPÙ)¨$Õ/øÜò bÜ�‰ÐKÈTÐ\`ˆÖaðbús   ‚ ‘!5´5Ú	debug_msgc                 óz   — 	 ddl m}  || ||¬«      S # t        $ r t        j                  |g|¢­ddiŽ | cY S w xY w)zJApply the configured SKILL.md preprocessing; on failure log and serve raw.r   )Úpreprocess_skill_content)Ú
session_idrn   T)Úagent.skill_preprocessingrt   r7   rp   rq   )r2   r;   ru   rr   Úargsrt   s         r   Ú_preprocess_skillrx   q   sC   € ðÝFÙ'¨°ÀzÔRÐRøÜò Ü�‰�YÐ5 Ò5°Ò5ØŠðús   ‚ “$:¹:T)Ú
preprocessru   Úskill_mdÚ	namespaceÚbarery   ru   c                ó(  ‡— ddl m}m} ddlm} | |«       v rt        d|› d|› �«      S |› d|› �}		 t        | «      Št        ‰¬
«      }|j                  |	«      rt        d|	› d�«      S |j                  |«      s)t        d|	› d�t        j                  j                  ¬«      S |rt        | j                  ||	d¬«      S t!        ˆfd„t"        D «       «      rt$        j'                  d||«       d}t)        t        «      5   |«       j+                  |«      D �cg c]
  }||k7  sŒ	|‘Œ }}d|› d�|rddj-                  |«      › d|› d|d   › d�ndz   dz   }d	d	d	«       |s‰nt/        ‰| j                  |d||«      }t1        d|	||z   t3        t5        |j7                  dd«      «      «      t9        | j                  «      t        j:                  j                  dœ«      S # t        $ r}
t        d|	› d|
› �«      cY d	}
~
S d	}
~
ww xY wc c}w # 1 sw Y   ŒµxY w)z8Read a plugin-provided skill, apply guards, return JSON.r   )Ú_get_disabled_pluginsÚget_plugin_managerr4   zPlugin 'z5' is disabled. Re-enable with: hermes plugins enable ú:zFailed to read skill 'r_   Nr1   zSkill 'z' is disabled.z$' is not supported on this platform.)Úreadiness_statusT)rT   c              3   óB   •K  — | ]  }|‰j                  «       v –— Œ y ­w©N)Úlower)Ú.0Úpr2   s     €r   ú	<genexpr>z&_serve_plugin_skill.<locals>.<genexpr>�   s   øè ø€ Ò
= Aˆ1�—‘“ÔÑ
=ùs   ƒzIPlugin skill '%s:%s' contains patterns that may indicate prompt injectionÚ z,[Bundle context: This skill is part of the 'z	' plugin.z
Sibling skills: z, z..
Use qualified form to invoke siblings (e.g. z).z]

z'Could not preprocess plugin skill %s:%sr+   )r!   rC   r2   r+   Úlinked_filesr�   )Úhermes_cli.pluginsr~   r   r6   r5   r#   r*   r7   r:   Ú_is_skill_disabledÚskill_matches_platformr   ÚUNSUPPORTEDÚvaluerk   ÚparentÚanyr
   rp   Úwarningr   Úlist_plugin_skillsÚjoinrx   r   r0   rD   ÚgetÚ_plugin_skill_linked_filesÚ	AVAILABLE)rz   r{   r|   rW   ry   ru   r~   r   r9   Úqualified_nameÚeÚparsed_frontmatterÚbannerÚsÚsiblingsÚrendered_contentr2   s                   @r   Ú_serve_plugin_skillrž   {   sO  ø€ ÷ MÝ(ØÑ)Ó+Ñ+Ü�x 	˜{Ð*_Ð`iÐ_jÐkÓlÐlØ!�{ ! D 6Ð*€NðFÜ" 8Ó,ˆô +°7Ô;ÐØ
×Ñ˜nÔ-Ü�w˜~Ð.¨nÐ=Ó>Ð>Ø×%Ñ%Ð&8Ô9Ü�w˜~Ð.Ð.RÐSÜ&:×&FÑ&F×&LÑ&LôNð 	NáÜ  §¡°)¸^Ð_cÔdÐdÜ
Ó
=Ô)<Ô
=Ô=Ü�‰ØWÐYbÐdhô	jà€FÜ	”)Ó	ñ PÙ1Ó3×FÑFÀyÓQÖ_˜!ÐUVÐZ^ÓU^’AÐ_ˆÐ_Ø?À	¸{È)ÐTá4<ð ! §¡¨8Ó!4Ð 5ð 6Ø�K˜q ¨!¡ ¨Rñ1ØBDñFàHOñPˆ÷Pñ
 '1‘wÔ6GØ�—‘ *Ð.WØ�4ó7Ðô Ø ¸FÐEUÑ<UÜ,¬SÐ1C×1GÑ1GÈÐWYÓ1ZÓ-[Ó\Ü2°8·?±?ÓCÜ0×:Ñ:×@Ñ@ñ	Bó Cð Cøô- ò FÜÐ-¨nÐ-=¸SÀÀÐDÓEÕEûðFüò `÷Pð PúsA   ²G Ã>HÄ
HÄ"HÄ&.HÇ	H Ç%G;Ç5H Ç;H ÈHÈHc           	      ó  — ddl m} i }t        D ]e  }t        | |z  j	                  d«      «      D �cg c]5  }|j                  «       r# ||| «      €t        |j                  | «      «      ‘Œ7 }}|sŒa|||<   Œg |xs d S c c}w )Nr   )r[   r=   )rb   r[   rG   ÚsortedrA   rB   rD   rE   )rV   r[   ÚlinkedÚcategoryr$   Úfiless         r   r•   r•   £   s–   € Ý7Ø#%€FÜ!ò %ˆä:@À*ÈxÑBW×A^ÑA^Ð_bÓAcÓ:döQØ26Ø�|‰|Œ~Ñ"5°d¸JÓ"GÐ"Oô �× Ñ  Ó,Õ-ðQˆð Qò Ø$ˆF�8Òð%ð Š>�TÐùòQs   ±:A=rƒ   )$Ú__doc__r   ÚloggingÚ
contextlibr   Úpathlibr   Útypingr   r   r   Útools.skills_tool_setupr   Ú	getLoggerrp   ÚMAX_NAME_LENGTHr/   r
   ÚlistÚ__annotations__rG   rI   ÚdictrD   r   r#   r*   r0   r:   rQ   Úboolrk   rf   rx   rž   r•   © r   r   ú<module>r±      s  ðò`ó Û Ý Ý ß "Ñ "å 8à	ˆ×	Ñ	Ð.Ó	/€à€ØÐ ò)Ð �Tó )ð A€ÚJÐ ð3�4ð 3˜Có 3ð>�ð > #ó >ðB˜4ð B Có Bð= sð =¨só =ðÈò ˜D 4™Kð ¸CÀ$¹Jð ÐRVÐWZÐ\_ÐW_ÑR`ó ðL dð L¨t°C¸¸c¹°NÑ/Có Lð IMØ ¸EÐUZò"BØð"BØ!$ð"BØ-0ð"BØ;>À¹:ð"Bàð"Bà59ð"BàNRð"Bà_bó"BðJb tð b°ó bð˜sð Àcð ÐUXó ð HLð%Cà°dò%CØð%CØ"ð%CØ*-ð%CØ:=À¹*ð%Càð%Cà),¨t©ð%Cà?Bó%CðP	¨4ð 	°D¸¸dÀ3¹i¸Ñ4HÈ4Ñ4Oô 	r   