§
    øžyj¨  ã                   ó  — U 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mZmZm	Z	m
Z
mZ ddlmZmZmZmZmZmZ ddlmZmZ ddlmZ ddlmZ ddlmZmZ  ej        e¦  «        Z ej         d	¦  «        Z!d
d
dgdœiZ"ee#ee#ef         f         e$d<   de#fd„Z%de#fd„Z&de#fd„Z'de#fd„Z(dBde#de)de)fd„Z*dddœde#de)de#de#fd„Z+dCde
e,         dee#e,f         fd„Z-de#d e,de)fd!„Z.de#de)fd"„Z/d#ee#e,f         dee)e	e#         f         fd$„Z0de#de#fd%„Z1d&e#de#fd'„Z2de#dee#e#f         fd(„Z3de#d&e#dee#e#f         fd)„Z4d*e
e	e#                  dee#e#f         fd+„Z5de#d,e
e#         d-e
e#         d.e
e#         d/e	e#         d ee#ef         de6e
e#         e
e#         e	e#         e)f         fd0„Z7de,de,fd1„Z8	 dCdd2œde#de,d3e
e9         d4e
e,         de	ee#e#f                  f
d5„Z:de#de)fd6„Z;d7e<de=fd8„Z>d9„ Z?d:„ Z@dCd;„ZAd<„ ZBde#d e,de)fd=„ZCd>„ ZDd?„ ZEd@„ ZFdA„ ZGdS )Du@  
MCP Server Management CLI â€” ``hermes mcp`` subcommand.

Implements ``hermes mcp add/remove/list/test/configure`` for interactive
MCP server lifecycle management (issue #690 Phase 2).

Relies on tools/mcp_tool.py for connection/discovery and keeps
configuration in ~/.hermes/config.yaml under the ``mcp_servers`` key.
é    N)ÚAnyÚDictÚListÚOptionalÚTuple)Úcfg_getÚload_configÚsave_configÚget_env_valueÚsave_env_valueÚget_hermes_home)ÚColorsÚcolor)Údisplay_hermes_home)Úvalidate_mcp_server_entry)Ú_ENV_VAR_PATTERNÚ_env_ref_namez^[A-Za-z_][A-Za-z0-9_]*$Úcodexz
mcp-server)ÚcommandÚargsÚ_MCP_PRESETSÚtextc                 óZ   — t          t          d| › �t          j        ¦  «        ¦  «         d S )Nú  )Úprintr   r   ÚDIM©r   s    ú;/home/ragecks/.hermes/hermes-agent/hermes_cli/mcp_config.pyÚ_infor   .   s(   € Ý	�%��T���VœZÑ
(Ô
(Ñ)Ô)Ð)Ð)Ð)ó    c                 óZ   — t          t          d| › �t          j        ¦  «        ¦  «         d S )Nu     âœ“ )r   r   r   ÚGREENr   s    r   Ú_successr#   1   s(   € Ý	�%�˜��¥¤Ñ
.Ô
.Ñ/Ô/Ð/Ð/Ð/r    c                 óZ   — t          t          d| › �t          j        ¦  «        ¦  «         d S )Nu     âš  )r   r   r   ÚYELLOWr   s    r   Ú_warningr&   4   s(   € Ý	�%�˜��¥¤Ñ
/Ô
/Ñ0Ô0Ð0Ð0Ð0r    c                 óZ   — t          t          d| › �t          j        ¦  «        ¦  «         d S )Nu     âœ— )r   r   r   ÚREDr   s    r   Ú_errorr)   7   s(   € Ý	�%�˜��¥¤Ñ
,Ô
,Ñ-Ô-Ð-Ð-Ð-r    TÚquestionÚdefaultÚreturnc           	      ó  — |rdnd}	 t          t          d| › d|› d�t          j        ¦  «        ¦  «                             ¦   «                              ¦   «         }n'# t          t          f$ r t          ¦   «          |cY S w xY w|s|S |dv S )NzY/nzy/Nr   z [z]: >   ÚyÚyes)	Úinputr   r   r%   ÚstripÚlowerÚKeyboardInterruptÚEOFErrorr   )r*   r+   Údefault_strÚvals       r   Ú_confirmr7   ;   s¨   € Ø"Ð-�%�%¨€KðÝ•EÐ;˜xÐ;Ð;¨;Ð;Ð;Ð;½V¼]ÑKÔKÑLÔL×RÒRÑTÔT×ZÒZÑ\Ô\ˆˆøÝ�xÐ(ð ð ð Ý‰ŒˆØˆˆˆðøøøð ð ØˆØ�,ÐÐs   ˆAA Á!A?Á>A?FÚ )Úpasswordr+   r9   c                ó*   — ddl m}  || ||¬¦  «        S )Nr   )Úprompt)r+   r9   )Úhermes_cli.cli_outputr;   )r*   r9   r+   Ú_shared_prompts       r   Ú_promptr>   G   s+   € Ø>Ð>Ð>Ð>Ð>Ð>Øˆ>˜(¨G¸hÐGÑGÔGÐGr    Úconfigc                 ó‚   — | €t          ¦   «         } |                      d¦  «        }|rt          |t          ¦  «        si S |S )z;Return the ``mcp_servers`` dict from config, or empty dict.NÚmcp_servers)r	   ÚgetÚ
isinstanceÚdict)r?   Úserverss     r   Ú_get_mcp_serversrF   N   sD   € à€~Ý‘”ˆØ�jŠj˜Ñ'Ô'€GØð �* W­dÑ3Ô3ð Øˆ	Ø€Nr    ÚnameÚserver_configc                 óè   — t          | |¦  «        }|r)|D ]}t          |¦  «         Œt          d| › d�¦  «         dS t          ¦   «         }||                     di ¦  «        | <   t	          |¦  «         dS )a  Add or update a server entry in config.yaml.

    Returns False when a high-signal exfiltration-shaped stdio command is
    rejected. MCP stdio servers are user-chosen local commands, so this blocks
    shell+egress payloads rather than whitelisting command families.
    úServer 'ú0' was NOT saved due to suspicious configuration.FrA   T)r   r&   r	   Ú
setdefaultr
   )rG   rH   ÚissuesÚissuer?   s        r   Ú_save_mcp_serverrO   X   sŒ   € õ ' t¨]Ñ;Ô;€FØð Øð 	ð 	ˆEÝ�U‰OŒOˆOˆOÝÐR˜DÐRÐRÐRÑSÔSÐSØˆuÝ‰]Œ]€FØ1>€F×Ò�m RÑ(Ô(¨Ñ.Ý�ÑÔÐØˆ4r    c                 ó®   — t          ¦   «         }|                     di ¦  «        }| |vrdS || = |s|                     dd¦  «         t          |¦  «         dS )z>Remove a server from config.yaml.  Returns True if it existed.rA   FNT)r	   rB   Úpopr
   )rG   r?   rE   s      r   Ú_remove_mcp_serverrR   k   sd   € å‰]Œ]€FØ�jŠj˜¨Ñ+Ô+€GØ�7ÐÐØˆuØ�ˆØð (Ø�
Š
�= $Ñ'Ô'Ð'Ý�ÑÔÐØˆ4r    rE   c                 ó‚  — g }|                       ¦   «         D ]W\  }}t          |t          ¦  «        s|                     d|› d�¦  «         Œ4|                     t          ||¦  «        ¦  «         ŒX|rd|fS t          ¦   «         }| rt          | ¦  «        |d<   n|                     dd¦  «         t          |¦  «         dg fS )uÊ  Replace the WHOLE ``mcp_servers`` map in config.yaml.

    Unlike ``_save_mcp_server`` (per-key upsert), this sets the entire map so
    the GUI's mcp.json editor can delete servers, drop an ``enabled: false``
    flag (re-enable), or remove nested fields and have those *removals* land on
    disk.  A plain ``/api/config`` deep-merge can only add/override keys, never
    delete them â€” which is why edits appeared to succeed but the old entry
    survived (see MCP tab persistence bug).

    Every entry is validated up front; on any suspicious command/args the whole
    save is rejected (returns ``(False, issues)``) so a bad paste can't be
    partially applied.  An empty map removes the key entirely.
    rJ   z': expected an objectFrA   NT)	ÚitemsrC   rD   ÚappendÚextendr   r	   rQ   r
   )rE   rM   rG   Úcfgr?   s        r   Ú_replace_mcp_serversrX   x   sØ   € ð €FØ—]’]‘_”_ð <ð <‰	ˆˆcÝ˜#�tÑ$Ô$ð 	Ø�MŠMÐ@ TÐ@Ð@Ð@ÑAÔAÐAØØ�ŠÕ/°°cÑ:Ô:Ñ;Ô;Ð;Ð;àð Ø�fˆ}Ðå‰]Œ]€FØð (Ý $ W¡¤ˆˆ}ÑÐà�
Š
�= $Ñ'Ô'Ð'Ý�ÑÔÐØ�ˆ8€Or    c                 ó„   — t          j        dd|                      ¦   «         ¦  «                             d¦  «        }d|› d�S )zDConvert server name to an env-var key like ``MCP_MYSERVER_API_KEY``.z[^A-Za-z0-9_]Ú_ÚMCP_Ú_API_KEY)ÚreÚsubÚupperr1   )rG   Úsuffixs     r   Ú_env_key_for_serverra   ™   s=   € åŒVÐ$ c¨4¯:ª:©<¬<Ñ8Ô8×>Ò>¸sÑCÔC€FØ"�&Ð"Ð"Ð"Ð"r    Útokenc                 óÔ   — t          | t          ¦  «        s| S |                      ¦   «         }|dd…                              ¦   «         dk    r|dd…                              ¦   «         S |S )u#  Strip a leading ``Bearer `` from a pasted token.

    The header template stores ``Authorization: Bearer ${MCP_X_API_KEY}``, so
    if a user pastes a token that already includes the ``Bearer `` prefix the
    server receives ``Bearer Bearer <jwt>`` â†’ 401. Normalize on save. (#37792)
    Né   zbearer )rC   Ústrr1   r2   )rb   Ústrippeds     r   Ú_strip_bearer_prefixrg   Ÿ   sf   € õ �e�SÑ!Ô!ð ØˆØ�{Š{‰}Œ}€HØ���„|×ÒÑÔ˜yÒ(Ð(Ø˜˜˜Œ|×!Ò!Ñ#Ô#Ð#Ø€Or    c                 ó0   — t          | ¦  «        }dd|› d�iS )a  Build the persisted Authorization header for a named MCP server.

    The secret itself lives in the active profile's ``.env`` file. Keeping
    this template construction beside ``_env_key_for_server`` ensures the CLI
    and Dashboard produce byte-equivalent MCP configuration.
    ÚAuthorizationz	Bearer ${Ú})ra   )rG   Úenv_keys     r   Ú_bearer_auth_headersrl   ®   s(   € õ " $Ñ'Ô'€GØÐ5¨'Ð5Ð5Ð5Ð6Ð6r    c                 óÊ   — t          |¦  «        }|r|                     ¦   «         dk    rt          d¦  «        ‚t          t	          | ¦  «        |¦  «         t          | ¦  «        S )zúPersist a Bearer token in the active profile and return safe headers.

    ``token`` is a one-time provisioning value. It is normalized and written
    only to ``.env``; callers persist the returned interpolation template in
    ``config.yaml``.
    ÚbearerzBearer token is required)rg   r2   Ú
ValueErrorr   ra   rl   )rG   rb   Ú
normalizeds      r   Ú_save_bearer_auth_tokenrq   ¹   se   € õ & eÑ,Ô,€JØð 5˜×)Ò)Ñ+Ô+¨xÒ7Ð7ÝÐ3Ñ4Ô4Ð4ÝÕ& tÑ,Ô,¨jÑ9Ô9Ð9Ý Ñ%Ô%Ð%r    Úraw_envc                 óz  — i }| pg D ]³}t          |pd¦  «                             ¦   «         }|sŒ(d|vrt          d|› d�¦  «        ‚|                     dd¦  «        \  }}|                     ¦   «         }|st          d|› d�¦  «        ‚t                               |¦  «        st          d|› d�¦  «        ‚|||<   Œ´|S )	z;Parse ``KEY=VALUE`` strings from CLI args into an env dict.r8   Ú=zInvalid --env value 'z' (expected KEY=VALUE)é   z' (missing variable name)zInvalid --env variable name 'ú')re   r1   ro   ÚsplitÚ_ENV_VAR_NAME_REÚmatch)rr   ÚparsedÚitemr   ÚkeyÚvalues         r   Ú_parse_env_assignmentsr~   Ç   së   € à€FØ�˜2ð ð ˆÝ�4�:˜2‰Œ×$Ò$Ñ&Ô&ˆØð 	ØØ�dˆ?ˆ?ÝÐQ°TÐQÐQÐQÑRÔRÐRØ—Z’Z  QÑ'Ô'‰
ˆˆUØ�iŠi‰kŒkˆØð 	VÝÐT°TÐTÐTÐTÑUÔUÐUÝ×%Ò% cÑ*Ô*ð 	EÝÐC¸SÐCÐCÐCÑDÔDÐDØˆˆs‰ˆØ€Mr    Úpreset_nameÚurlr   Úcmd_argsc                óT  — |s|||dfS t                                |¦  «        }|st          d|› �¦  «        ‚|s|r|||dfS |                     d¦  «        }|                     d¦  «        }t          |                     d¦  «        pg ¦  «        }|r||d<   |r||d<   |r||d<   |||dfS )z=Apply a known MCP preset when transport details were omitted.FzUnknown MCP preset: r€   r   r   T)r   rB   ro   Úlist)rG   r   r€   r   r�   rH   Úpresets          r   Ú_apply_mcp_presetr…   Ú   sð   € ð ð -Ø�G˜X uÐ,Ð,å×Ò˜kÑ*Ô*€FØð ?ÝÐ=°Ð=Ð=Ñ>Ô>Ð>à
ð -ˆgð -Ø�G˜X uÐ,Ð,à
�*Š*�UÑ
Ô
€CØ�jŠj˜Ñ#Ô#€GÝ�F—J’J˜vÑ&Ô&Ð,¨"Ñ-Ô-€Hà
ð #Ø"ˆ�eÑØð +Ø#*ˆ�iÑ Øð )Ø (ˆ�fÑà�˜ 4Ð'Ð'r    c                 óˆ   — ddl m} ddlm}  |¦   «         €"	 ddlm}  |¦   «          n# t          $ r Y nw xY w || ¦  «        S )u,  Resolve ``${ENV}`` placeholders in a server config before connecting.

    Mirrors ``_load_mcp_config()`` in ``tools/mcp_tool.py``: load
    ``~/.hermes/.env`` into ``os.environ`` and recursively interpolate any
    ``${VAR}`` placeholders. The CLI builds header templates like
    ``Authorization: Bearer ${MCP_X_API_KEY}`` but the probe path never
    resolved them, so the discovery probe sent the literal placeholder and
    auth-requiring servers (e.g. n8n) returned 401 â€” while runtime tool
    loading worked because it interpolates. (#37792)
    r   )Ú_interpolate_env_vars)Úcurrent_secret_scopeN)Úload_hermes_dotenv)Útools.mcp_toolr‡   Úagent.secret_scoperˆ   Úhermes_cli.env_loaderr‰   Ú	Exception)r?   r‡   rˆ   r‰   s       r   Ú_resolve_mcp_server_configrŽ   þ   s‘   € ð 5Ð4Ð4Ð4Ð4Ð4à7Ð7Ð7Ð7Ð7Ð7àÐÑÔÐ%ð	Ø@Ð@Ð@Ð@Ð@Ð@ØÐÑ Ô Ð Ð øÝð 	ð 	ð 	ØˆDð	øøøà Ð  Ñ(Ô(Ð(s   ˜) ©
6µ6)ÚdetailsÚconnect_timeoutr�   c                ó2  ‡ ‡‡‡‡‡‡— t          ‰ ‰¦  «        }|r"t          d                     |¦  «        ¦  «        ‚ddlm}m}mŠm}mŠ t          ‰¦  «        Š‰€N‰ 
                    dd¦  «        }	 t          dt          |¦  «        ¦  «        Šn# t          t          f$ r dŠY nw xY w |¦   «          g Šˆˆˆˆˆˆ ˆfd	„}		  | |	¦   «         ‰d
z   ¬¦  «         n"# t          $ r}
t          |
¦  «        d‚d}
~
ww xY w	  |¦   «          n#  |¦   «          w xY w‰S )ua  Temporarily connect to one MCP server, list its tools, disconnect.

    Returns list of ``(tool_name, description)`` tuples.
    Raises on connection failure.

    ``details``: optional dict the probe fills with extra capability counts
    (``prompts``, ``resources``) â€” an out-param so the return shape stays
    stable for existing CLI callers.
    z; r   )Ú_ensure_mcp_loopÚ_run_on_mcp_loopÚ_connect_serverÚ_stop_mcp_loop_if_idleÚ_parse_boolishNr�   é   g      ð?g      >@c               “   óð  •‡K  — t          j         ‰	‰‰¦  «        ‰¬¦  «        ƒ d {V —†} 	 | j        D ]Q}t          |dd¦  «        pd}t	          |¦  «        dk    r|d d…         dz   }‰                     |j        |f¦  «         ŒR‰��5‰                     d¦  «        pi } ‰
|                     d¦  «        d	¬
¦  «        } ‰
|                     d¦  «        d	¬
¦  «        }t          t          | dd ¦  «        dd ¦  «        Šdt          dt          fˆfd„}|rS |d¦  «        rH	 | j
                             ¦   «         ƒ d {V —†}t	          |j        ¦  «        ‰d<   n# t          $ r Y nw xY w|rS |d¦  «        rH	 | j
                             ¦   «         ƒ d {V —†}t	          |j        ¦  «        ‰d<   n# t          $ r Y nw xY w|                      ¦   «         ƒ d {V —† d S # |                      ¦   «         ƒ d {V —† w xY w)N©ÚtimeoutÚdescriptionr8   éP   éM   ú...ÚtoolsÚpromptsT©r+   Ú	resourcesÚinitialize_resultÚcapabilitiesÚcap_attrr,   c                 ó2   •— ‰€dS t          ‰| d ¦  «        d uS )NT)Úgetattr)r¥   Úadvertised_capss    €r   Ú_advertisesz9_probe_single_server.<locals>._probe.<locals>._advertises[  s'   ø€ ð 'Ð.Ø#˜tÝ" ?°H¸dÑCÔCÈ4ÐOÐOr    )ÚasyncioÚwait_forÚ_toolsr§   ÚlenrU   rG   rB   re   ÚboolÚsessionÚlist_promptsr    r�   Úlist_resourcesr¢   Úshutdown)ÚserverÚtÚdescÚtools_filterÚprompts_enabledÚresources_enabledr©   Úresultr¨   r”   r–   r?   r�   r�   rG   Útools_founds           @€€€€€€€r   Ú_probez$_probe_single_server.<locals>._probe9  sÏ  øøè è € ÝÔ'ØˆO˜D &Ñ)Ô)°?ð
ñ 
ô 
ð 
ð 
ð 
ð 
ð 
ð 
ˆð4	$Ø”]ð 3ð 3�Ý˜q -°Ñ4Ô4Ð:¸�å�t‘9”9˜r’>�>Ø   œ9 uÑ,�DØ×"Ò" A¤F¨D >Ñ2Ô2Ð2Ð2ØÑ"ð  &Ÿzšz¨'Ñ2Ô2Ð8°b�Ø"0 .Ø ×$Ò$ YÑ/Ô/¸ð#ñ #ô #�ð %3 NØ ×$Ò$ [Ñ1Ô1¸4ð%ñ %ô %Ð!õ #*Ý˜FÐ$7¸Ñ>Ô>Ø"Øñ#ô #�ðP­#ð Pµ$ð Pð Pð Pð Pð Pð Pð #ð  { {°9Ñ'=Ô'=ð ðØ'-¤~×'BÒ'BÑ'DÔ'DÐ!DÐ!DÐ!DÐ!DÐ!DÐ!D˜Ý-0°´Ñ-@Ô-@˜ 	Ñ*Ð*øÝ$ð ð ð Ø˜ðøøøà$ð ¨¨°[Ñ)AÔ)Að ðØ'-¤~×'DÒ'DÑ'FÔ'FÐ!FÐ!FÐ!FÐ!FÐ!FÐ!F˜Ý/2°6Ô3CÑ/DÔ/D˜ Ñ,Ð,øÝ$ð ð ð Ø˜ðøøøð —/’/Ñ#Ô#Ð#Ð#Ð#Ð#Ð#Ð#Ð#Ð#Ð#ø�&—/’/Ñ#Ô#Ð#Ð#Ð#Ð#Ð#Ð#Ð#Ð#øøøsT   ¬C4G Ä!6E ÅG Å
E%Å"G Å$E%Å%G Å66F- Æ,G Æ-
F:Æ7G Æ9F:Æ:G ÇG5é
   r™   )r   ro   ÚjoinrŠ   r’   r“   r”   r•   r–   rŽ   rB   ÚmaxÚfloatÚ	TypeErrorÚBaseExceptionÚ_unwrap_exception_group)rG   r?   r�   r�   rM   r’   r“   r•   Úraw_timeoutr»   Úexcr”   r–   rº   s   ````       @@@r   Ú_probe_single_serverrÅ     sÎ  øøøøøøø€ õ ' t¨VÑ4Ô4€FØð ,Ý˜Ÿš 6Ñ*Ô*Ñ+Ô+Ð+ðð ð ð ð ð ð ð ð ð ð ð ð ð õ (¨Ñ/Ô/€FØÐØ—j’jÐ!2°BÑ7Ô7ˆð	#Ý! #¥u¨[Ñ'9Ô'9Ñ:Ô:ˆOˆOøÝ�:Ð&ð 	#ð 	#ð 	#Ø"ˆOˆOˆOð	#øøøð ÐÑÔÐØ)+€Kð8$ð 8$ð 8$ð 8$ð 8$ð 8$ð 8$ð 8$ð 8$ð 8$ð 8$ðt!ØÐ˜˜™œ¨?¸RÑ+?Ð@Ñ@Ô@Ð@Ð@øÝð 5ð 5ð 5Ý% cÑ*Ô*°Ð4øøøøð5øøøð 	Að 	ÐÑ Ô Ð Ð øÐÐÑ Ô Ð Ð øøøàÐs<   Á2B ÂB&Â%B&ÃC ÃD Ã
C9Ã$C4Ã4C9Ã9D ÄDc                 ó²   — 	 ddl m}  || ¦  «                             ¦   «         S # t          $ r'}t                               d| |¦  «         Y d}~dS d}~ww xY w)a  Return True if an OAuth token file exists on disk for ``name``.

    Used after ``hermes mcp login`` to distinguish a genuine authentication
    from a probe that succeeded only because the server allowed
    initialize/tools-list without auth (so no token was ever acquired).
    r   )ÚHermesTokenStoragez)Could not check OAuth tokens for '%s': %sNT)Útools.mcp_oauthrÇ   Úhas_cached_tokensr�   ÚloggerÚdebug)rG   rÇ   rÄ   s      r   Ú_oauth_tokens_presentrÌ   }  sy   € ðØ6Ð6Ð6Ð6Ð6Ð6Ø!Ð! $Ñ'Ô'×9Ò9Ñ;Ô;Ð;øÝð ð ð Ý�ŠÐ@À$ÈÑLÔLÐLàˆtˆtˆtˆtˆtøøøøðøøøs   ‚"% ¥
A¯AÁArÄ   c                 óò   — t          | t          ¦  «        r0| j        r)| j        d         } t          | t          ¦  «        r| j        °)t          | t          ¦  «        r| S t	          t          | ¦  «        ¦  «        S )aB  Extract the root-cause exception from anyio TaskGroup wrappers.

    The MCP SDK uses anyio task groups, which wrap errors in
    ``BaseExceptionGroup`` / ``ExceptionGroup``.  This makes error
    messages opaque ("unhandled errors in a TaskGroup").  We unwrap
    to surface the real cause (e.g. "401 Unauthorized").
    r   )rC   ÚBaseExceptionGroupÚ
exceptionsr�   ÚRuntimeErrorre   )rÄ   s    r   rÂ   rÂ   �  sw   € õ �SÕ,Ñ
-Ô
-ð  °#´.ð  ØŒn˜QÔˆõ �SÕ,Ñ
-Ô
-ð  °#´.ð  õ �#•yÑ!Ô!ð Øˆ
Ý�˜C™œÑ!Ô!Ð!r    c                 ó~  ‡"— | j         }t          | dd¦  «        }t          | dd¦  «        }t          | dd¦  «        pg }|r|d         dk    r
|dd…         }t          | dd¦  «        }t          | d	d¦  «        }t          | d
d¦  «        }t          | dd¦  «        }i }		 t          |¦  «        }
t          ||||t	          |¦  «        |	¬¦  «        \  }}}}n4# t
          $ r'}t          t          |¦  «        ¦  «         Y d}~dS d}~ww xY w|r|
rt          d¦  «         dS |sO|sMt          d¦  «         t          d¦  «         t          d¦  «         t          d¦  «         t          d¦  «         dS t          ¦   «         }||v r&t          d|› d�d¬¦  «        st          d¦  «         dS |r||	d<   n||	d<   |r||	d<   |
r|
|	d
<   |�||	d<   t          ||	¦  «        }|r)|D ]}t          |¦  «         Œt          d|› d�¦  «         dS |ré|dk    rãt          ¦   «          t          d|› d�¦  «         d}	 ddlm}  |¦   «                              |||	                     d¦  «        ¦  «        }|rd|	d<   t%          d¦  «         d}nt          d ¦  «         n)# t&          $ r}t          d!|› �¦  «         Y d}~nd}~ww xY w|s2t          d"¦  «         t          d#d¬¦  «        rnÝt          d¦  «         dS nË|rÉt          ¦   «          t          d$|› �¦  «         t          d%d¬¦  «        }|r–|d&k    s|sŽt)          |¦  «        }t+          |¦  «        }|rt%          |› d'�¦  «         nGt-          d(d¬)¦  «        }|r4t/          ||¦  «        |	d*<   t%          d+t1          ¦   «         › d,|› �¦  «         |rt3          |¦  «        |	d*<   t          ¦   «          t          t5          d-|› d�t6          j        ¦  «        ¦  «         	 t;          ||	¦  «        Š"nu# t&          $ rh}t          d.|› �¦  «         t          d/d¬¦  «        r:d|	d0<   t=          ||	¦  «        r%t%          d1|› d2�¦  «         t          d3|z   ¦  «         Y d}~dS d}~ww xY w‰"sEt          d4¦  «         t          d5d¬¦  «        r#t=          ||	¦  «        rt%          d1|› d6�¦  «         dS t          ¦   «          t%          d7t?          ‰"¦  «        › d8|› d9�¦  «         t          ¦   «          ‰"D ]U\  }}t?          |¦  «        d:k    r|dd:…         d;z   n|}t          d<t5          |t6          j         ¦  «        d=›d>|› �¦  «         ŒVt          ¦   «          	 tC          t5          d?t?          ‰"¦  «        › d@�t6          j"        ¦  «        ¦  «         #                    ¦   «          $                    ¦   «         }n5# tJ          tL          f$ r! t          ¦   «          t          d¦  «         Y dS w xY w|dAv rt          dB¦  «         dS |dCv r²ddDl'm(} dE„ ‰"D ¦   «         }tS          tU          t?          ‰"¦  «        ¦  «        ¦  «        } |dF|› dG�||¦  «        }|st          dH¦  «         dS ˆ"fdI„tW          |¦  «        D ¦   «         }||	 ,                    dJi ¦  «        dK<   t?          |¦  «        } t?          ‰"¦  «        }!nt?          ‰"¦  «        } t?          ‰"¦  «        }!d|	d0<   t=          ||	¦  «        rGt          ¦   «          t%          d1|› dLt1          ¦   «         › dM| › dN|!› dO�	¦  «         t          dP¦  «         dS dS )Qz9Add a new MCP server with discovery-first tool selection.r€   NÚmcp_commandr   r   z--ru   Úauthr„   Úenvr�   )r   r€   r   r�   rH   zJ--env is only supported for stdio MCP servers (--command or stdio presets)zBMust specify --url <endpoint>, --command <cmd>, or --preset <name>z	Examples:z3  hermes mcp add ink --url "https://mcp.ml.ink/mcp"zP  hermes mcp add github --command npx --args @modelcontextprotocol/server-githubz+  hermes mcp add myserver --preset mypresetrJ   z' already exists. Overwrite?Fr¡   ú
Cancelled.r   rK   ÚoauthúStarting OAuth flow for 'ú'...©Úget_managerz>OAuth configured (tokens will be acquired on first connection)Tu8   OAuth setup failed â€” MCP SDK auth module not availablezOAuth error: z"This server may not support OAuth.z Continue without authentication?zConnecting to z(Does this server require authentication?Úheaderz: already configuredzAPI key / Bearer token)r9   Úheadersz	Saved to z	/.env as ú  Connecting to 'úFailed to connect: z(Save config anyway (you can test later)?ÚenabledzSaved 'z' to config (disabled)z%Fix the issue, then: hermes mcp test z'Server connected but reported no tools.zSave config anyway?z' to configzConnected! Found z tool(s) from 'z':é<   rž   ú    Ú40sÚ z  Enable all z tools? [Y/n/select]: >   ÚnÚnou   Cancelled â€” server not saved.>   ÚsÚselect©Úcurses_checklistc                 ó4   — g | ]}|d          › d|d         › �‘ŒS ©r   u     â€”  ru   © ©Ú.0r´   s     r   ú
<listcomp>zcmd_mcp_add.<locals>.<listcomp>L  s.   € Ð8Ð8Ð8¨Q�Q�q”TÐ(Ð( ! A¤$Ð(Ð(Ð8Ð8Ð8r    úSelect tools for 'rv   u'   No tools selected â€” server not saved.c                 ó,   •— g | ]}‰|         d          ‘ŒS ©r   rì   )rî   ÚirŸ   s     €r   rï   zcmd_mcp_add.<locals>.<listcomp>Y  s!   ø€ Ð<Ð<Ð<¨˜˜aœ œÐ<Ð<Ð<r    rŸ   Úincludez' to z/config.yaml (ú/z tools enabled)z'Start a new session to use these tools.)-rG   r§   r~   r…   rƒ   ro   r)   re   r   rF   r7   r   r&   r   Útools.mcp_oauth_managerrÚ   Úget_or_build_providerrB   r#   r�   ra   r   r>   rq   r   rl   r   r   ÚCYANrÅ   rO   r­   r"   r0   r%   r1   r2   r3   r4   Úhermes_cli.curses_uiré   ÚsetÚrangeÚsortedrL   )#r   rG   r€   r   r�   Ú	auth_typer   rr   Úraw_connect_timeoutrH   Úexplicit_envÚ_preset_appliedrÄ   ÚexistingrM   rN   Úoauth_okrÚ   Ú
oauth_authÚ
needs_authrk   Úexisting_keyÚapi_keyÚ	tool_namerµ   ÚshortÚchoiceré   ÚlabelsÚpre_selectedÚchosenÚchosen_namesÚ
tool_countÚtotalrŸ   s#                                     @r   Úcmd_mcp_addr  Ÿ  s5	  ø€ àŒ9€DÝ
�$˜˜tÑ
$Ô
$€Cõ �d˜M¨4Ñ0Ô0€GÝ�t˜V TÑ*Ô*Ð0¨b€HØð  �H˜Q”K 4Ò'Ð'Ø˜A˜B˜B”<ˆÝ˜˜f dÑ+Ô+€IÝ˜$ ¨$Ñ/Ô/€KÝ�d˜E 4Ñ(Ô(€GÝ! $Ð(9¸4Ñ@Ô@Ðà$&€MðÝ-¨gÑ6Ô6ˆÝ2CØØ#ØØÝ˜(‘^”^Ø'ð3
ñ 3
ô 3
Ñ/ˆˆW�h  øõ ð ð ð Ý�s�3‰xŒxÑÔÐØˆˆˆˆˆøøøøðøøøð ð ˆ|ð ÝÐ[Ñ\Ô\Ð\Øˆð ð �wð ÝÐSÑTÔTÐTÝˆkÑÔÐÝÐCÑDÔDÐDÝÐ`ÑaÔaÐaÝÐ;Ñ<Ô<Ð<Øˆõ  Ñ!Ô!€HØˆxÐÐÝÐE 4ÐEÐEÐEÈuÐUÑUÔUð 	Ý�,ÑÔÐØˆFð ð 0Ø"ˆ�eÑÐà#*ˆ�iÑ Øð 	-Ø$,ˆM˜&Ñ!Øð 	0Ø#/ˆM˜%Ñ ØÐ&Ø+>ˆÐ'Ñ(å& t¨]Ñ;Ô;€FØð Øð 	ð 	ˆEÝ�U‰OŒOˆOˆOÝÐR˜DÐRÐRÐRÑSÔSÐSØˆð ð 0Jˆy˜GÒ#Ð#Ý‰ŒˆÝÐ4¨$Ð4Ð4Ð4Ñ5Ô5Ð5Øˆð	,Ø;Ð;Ð;Ð;Ð;Ð;Ø$˜™œ×<Ò<Ø�c˜=×,Ò,¨WÑ5Ô5ñô ˆJð ð UØ(/�˜fÑ%ÝÐYÑZÔZÐZØ��åÐSÑTÔTÐTøøÝð 	,ð 	,ð 	,ÝÐ* SÐ*Ð*Ñ+Ô+Ð+Ð+Ð+Ð+Ð+Ð+øøøøð	,øøøð ð 	ÝÐ6Ñ7Ô7Ð7ÝÐ:ÀDÐIÑIÔIð àå�lÑ#Ô#Ð#Ø�ð	ð 
ð Jå‰ŒˆÝÐ$˜sÐ$Ð$Ñ%Ô%Ð%ÝÐHÐRVÐWÑWÔWˆ
Øð 	JØ˜HÒ$Ð$¨IÐ$Ý-¨dÑ3Ô3�Ý,¨WÑ5Ô5�Øð XÝ Ð=Ð=Ð=Ñ>Ô>Ð>Ð>å%Ð&>ÈÐNÑNÔN�GØð XÝ3JØ  'ñ4ô 4˜ iÑ0õ !Ð!VÕ-@Ñ-BÔ-BÐ!VÐ!VÈWÐ!VÐ!VÑWÔWÐWð  ð JÝ/CÀDÑ/IÔ/I�M )Ñ,õ 
�G„G€GÝ	�%Ð. DÐ.Ð.Ð.µ´Ñ
<Ô
<Ñ=Ô=Ð=ð	Ý$ T¨=Ñ9Ô9ˆˆøÝð ð ð ÝÐ* SÐ*Ð*Ñ+Ô+Ð+ÝÐ>ÈÐNÑNÔNð 	FØ',ˆM˜)Ñ$Ý  mÑ4Ô4ð FÝÐ? 4Ð?Ð?Ð?Ñ@Ô@Ð@ÝÐ=ÀÑDÑEÔEÐEØˆˆˆˆˆøøøøðøøøð ð ÝÐ:Ñ;Ô;Ð;ÝÐ)°4Ð8Ñ8Ô8ð 	6Ý  mÑ4Ô4ð 6ÝÐ4 4Ð4Ð4Ð4Ñ5Ô5Ð5Øˆõ 
�G„G€GÝÐD¥ U¡¤ÐDÐD¸DÐDÐDÐDÑEÔEÐEÝ	�G„G€GØ ð Cð C‰ˆ	�4Ý%(¨¡Y¤Y°¢^ ^��S�b�S”	˜EÑ!Ð!¸ˆÝÐA•U˜9¥f¤lÑ3Ô3ÐAÐAÐA¸%ÐAÐAÑBÔBÐBÐBÝ	�G„G€GðÝÝÐD¥# e¡*¤*ÐDÐDÐDÅfÄmÑTÔTñ
ô 
ç
Š%‰'Œ'—%’%‘'”'ð 	ˆøõ �xÐ(ð ð ð Ý‰ŒˆÝˆlÑÔÐØˆˆðøøøð
 �ÐÐÝÐ/Ñ0Ô0Ð0Øˆà�Ð Ð à9Ð9Ð9Ð9Ð9Ð9à8Ð8°%Ð8Ñ8Ô8ˆÝ�5¥ U¡¤Ñ,Ô,Ñ-Ô-ˆà!Ð!Ø( Ð(Ð(Ð(ØØñ
ô 
ˆð ð 	ÝÐ;Ñ<Ô<Ð<ØˆFà<Ð<Ð<Ð<­V°F©^¬^Ð<Ñ<Ô<ˆØ;Gˆ× Ò  ¨"Ñ-Ô-¨iÑ8å˜Ñ&Ô&ˆ
Ý�E‘
”
ˆˆõ ˜‘Z”Zˆ
Ý�E‘
”
ˆð  $€M�)ÑÝ˜˜mÑ,Ô,ð 9Ý‰ŒˆÝÐn˜4ÐnÐnÕ&9Ñ&;Ô&;ÐnÐnÈ:ÐnÐnÐX]ÐnÐnÐnÑoÔoÐoÝÐ7Ñ8Ô8Ð8Ð8Ð8ð9ð 9s]   Â6C Ã
DÃD Ä DÈ/A J Ê
J6ÊJ1Ê1J6Ï3P Ð
Q6ÐAQ1Ñ1Q6Õ&AW ×.W5×4W5c                 ó
  — | j         }t          ¦   «         }||vr]t          d|› d�¦  «         t          |                     ¦   «         ¦  «        }|r%t          dd                     |¦  «        › �¦  «         dS t          d|› d�d¬	¦  «        st          d
¦  «         dS t          |¦  «         t          d|› d�¦  «         	 ddl
m}  |¦   «                              |¦  «         t          d¦  «         dS # t          $ r Y dS w xY w)z!Remove an MCP server from config.rJ   ú' not found in config.úAvailable servers: ú, NzRemove server 'z'?Tr¡   rÕ   z	Removed 'z' from configr   rÙ   zCleaned up OAuth tokens)rG   rF   r)   rƒ   Úkeysr   r½   r7   rR   r#   rö   rÚ   Úremover�   )r   rG   r  rE   rÚ   s        r   Úcmd_mcp_remover  n  sB  € àŒ9€DÝÑ!Ô!€Hà�8ÐÐÝÐ6˜$Ð6Ð6Ð6Ñ7Ô7Ð7Ý�x—}’}‘”Ñ'Ô'ˆØð 	>ÝÐ<¨¯	ª	°'Ñ(:Ô(:Ð<Ð<Ñ=Ô=Ð=ØˆåÐ. dÐ.Ð.Ð.¸Ð=Ñ=Ô=ð ÝˆlÑÔÐØˆå�tÑÔÐÝÐ,˜Ð,Ð,Ð,Ñ-Ô-Ð-ð
Ø7Ð7Ð7Ð7Ð7Ð7Øˆ‰Œ×Ò˜TÑ"Ô"Ð"ÝÐ*Ñ+Ô+Ð+Ð+Ð+øÝð ð ð Øˆˆðøøøs   Ã 2C4 Ã4
DÄDc                 óZ  — t          ¦   «         }|sht          ¦   «          t          d¦  «         t          ¦   «          t          d¦  «         t          d¦  «         t          d¦  «         t          ¦   «          dS t          ¦   «          t          t          dt          j        t          j        z   ¦  «        ¦  «         t          ¦   «          t          ddd	›d
dd›d
dd›d
dd›�¦  «         t          dd› d
d› d
d› d
d› �¦  «         |                     ¦   «         D �]\  }}d|v r+|d         }t          |¦  «        dk    r|dd…         dz   }|}n‹d|v r…|d         }| 	                    dg ¦  «        }t          |t          ¦  «        r/|r-|› d
d
                     d„ |dd…         D ¦   «         ¦  «        › �}n|}t          |¦  «        dk    r|dd…         dz   }nd}| 	                    di ¦  «        }t          |t          ¦  «        r‚| 	                    d¦  «        }	| 	                    d ¦  «        }
|	r(t          |	t          ¦  «        rt          |	¦  «        › d!�}n0|
r)t          |
t          ¦  «        rd"t          |
¦  «        › d#�}nd$}nd$}| 	                    d%d&¦  «        }t          |t          ¦  «        r|                     ¦   «         d'v }|rt          d(t          j        ¦  «        nt          d)t          j        ¦  «        }t          d|d	›d
|d›d
|d›d
|› �¦  «         �Œt          ¦   «          dS )*z List all configured MCP servers.zNo MCP servers configured.zAdd one with:z(  hermes mcp add <name> --url <endpoint>z8  hermes mcp add <name> --command <cmd> --args <args...>Nz  MCP Servers:r   ÚNamez<16rã   Ú	Transportz<30ÚToolsz<12ÚStatusz<10u0   â”€â”€â”€â”€â”€â”€â”€â”€â”€â”€â”€â”€â”€â”€â”€â”€uZ   â”€â”€â”€â”€â”€â”€â”€â”€â”€â”€â”€â”€â”€â”€â”€â”€â”€â”€â”€â”€â”€â”€â”€â”€â”€â”€â”€â”€â”€â”€u$   â”€â”€â”€â”€â”€â”€â”€â”€â”€â”€â”€â”€u   â”€â”€â”€â”€â”€â”€â”€â”€â”€â”€r€   é   é   rž   r   r   c              3   ó4   K  — | ]}t          |¦  «        V — Œd S ©N©re   )rî   Úas     r   ú	<genexpr>zcmd_mcp_list.<locals>.<genexpr>°  s(   è è € Ð-KÐ-K¸­c°!©f¬fÐ-KÐ-KÐ-KÐ-KÐ-KÐ-Kr    é   ú?rŸ   rô   Úexcludez	 selectedÚ-z	 excludedÚallrß   T>   Ú1r/   Útrueu   âœ“ enabledu   âœ— disabled)rF   r   r   r   r   rø   ÚBOLDrT   r­   rB   rC   rƒ   r½   rD   re   r2   r"   r   )r   rE   rG   rW   r€   Ú	transportÚcmdr�   Ú	tools_cfgrô   r&  Ú	tools_strrß   Ústatuss                 r   Úcmd_mcp_listr1  Ž  sm  € åÑ Ô €Gàð Ý‰ŒˆÝÐ*Ñ+Ô+Ð+Ý‰ŒˆÝˆoÑÔÐÝÐ8Ñ9Ô9Ð9ÝÐHÑIÔIÐIÝ‰ŒˆØˆå	�G„G€GÝ	�%Ð ¥&¤+µ´Ñ";Ñ
<Ô
<Ñ=Ô=Ð=Ý	�G„G€Gõ 
Ð
JˆvÐ
JÐ
JÐ
J˜KÐ
JÐ
JÐ
J¨gÐ
JÐ
JÐ
J¸HÐ
JÐ
JÐ
JÑKÔKÐKÝ	Ð
BˆzÐ
BÐ
B˜JÐ
BÐ
B¨Ð
BÐ
B°jÐ
BÐ
BÑCÔCÐCà—]’]‘_”_ð (Hñ (H‰	ˆˆcà�Cˆ<ˆ<Ø�e”*ˆCå�3‰xŒx˜"Š}ˆ}Ø˜#˜2˜#”h Ñ&�ØˆIˆIØ˜#ÐÐØ�i”.ˆCØ—w’w˜v rÑ*Ô*ˆHÝ˜(¥DÑ)Ô)ð  ¨hð  Ø"ÐMÐM S§X¢XÐ-KÐ-K¸hÀrÈÀr¼lÐ-KÑ-KÔ-KÑ%KÔ%KÐMÐM�	�	à�	Ý�9‰~Œ~ Ò"Ð"Ø% c r cœN¨UÑ2�	øàˆIð —G’G˜G RÑ(Ô(ˆ	Ý�i¥Ñ&Ô&ð 
	Ø—m’m IÑ.Ô.ˆGØ—m’m IÑ.Ô.ˆGØð "�: g­tÑ4Ô4ð "Ý" 7™|œ|Ð6Ð6Ð6�	�	Øð "�Z¨µÑ6Ô6ð "Ø7¥ G¡¤Ð7Ð7Ð7�	�	à!�	�	àˆIð —'’'˜) TÑ*Ô*ˆÝ�g�sÑ#Ô#ð 	>Ø—m’m‘o”oÐ)=Ð=ˆGØ7>Ðe•�}¥f¤lÑ3Ô3Ð3ÅEÈ.ÕZ`ÔZdÑDeÔDeˆåÐF�4ÐFÐFÐF˜iÐFÐFÐF¨iÐFÐFÐF¸fÐFÐFÑGÔGÐGÑGå	�G„G€G€G€Gr    c                 ój  — | j         }t          ¦   «         }||vr]t          d|› d�¦  «         t          |                     ¦   «         ¦  «        }|r%t          dd                     |¦  «        › �¦  «         dS ||         }t          ¦   «          t          t          d|› d�t          j
        ¦  «        ¦  «         d|v rt          d	|d         › �¦  «         n(|                     d
d¦  «        }t          d|› �¦  «         |                     dd¦  «        }|                     di ¦  «        }|dk    rt          d¦  «         nÆ|rµ|                     ¦   «         D ]Ÿ\  }}	t          |	t          ¦  «        r…d|                     ¦   «         v sd|                     ¦   «         v rYt!          j        d„ |	¦  «        }
t%          |
¦  «        dk    r|
dd…         dz   |
dd…         z   }nd}t          d|› d|› �¦  «         Œ nt          d¦  «         t'          j        ¦   «         }	 t+          ||¦  «        }t'          j        ¦   «         |z
  dz  }nG# t,          $ r:}t'          j        ¦   «         |z
  dz  }t          d|d›d|› �¦  «         Y d}~dS d}~ww xY wt/          d|d›d �¦  «         t/          d!t%          |¦  «        › �¦  «         |rft          ¦   «          |D ]U\  }}t%          |¦  «        d"k    r|dd"…         d#z   n|}t          dt          |t          j        ¦  «        d$›d%|› �¦  «         ŒVt          ¦   «          dS )&z!Test connection to an MCP server.rJ   r  úAvailable: r  Nz  Testing 'rØ   r€   u   Transport: HTTP â†’ r   r%  u   Transport: stdio â†’ rÓ   r8   rÜ   rÖ   zAuth: OAuth 2.1 PKCEr|   c                 ól   — t          j        t          |                      d¦  «        ¦  «        d¦  «        S )Nru   r8   )ÚosÚgetenvr   Úgroup)Úms    r   ú<lambda>zcmd_mcp_test.<locals>.<lambda>ó  s+   € ½"¼)ÅMÐRS×RYÒRYÐZ[ÑR\ÔR\ÑD]ÔD]Ð_aÑ:bÔ:b€ r    é   é   z***éüÿÿÿrá   z: z
Auth: noneiè  zConnection failed (z.0fzms): zConnected (zms)zTools discovered: é7   rž   Ú36srã   )rG   rF   r)   rƒ   r  r   r½   r   r   r   rø   rB   rT   rC   re   r2   r   r^   r­   ÚtimeÚ	monotonicrÅ   r�   r#   r"   )r   rG   rE   Ú	availablerW   r-  rý   rÜ   ÚkÚvÚresolvedÚmaskedÚstartrŸ   Ú
elapsed_msrÄ   r  rµ   r  s                      r   Úcmd_mcp_testrH  Ó  s‘  € àŒ9€DÝÑ Ô €Gà�7ÐÐÝÐ6˜$Ð6Ð6Ð6Ñ7Ô7Ð7Ý˜Ÿš™œÑ(Ô(ˆ	Øð 	8ÝÐ6 §	¢	¨)Ñ 4Ô 4Ð6Ð6Ñ7Ô7Ð7Øˆà
�$Œ-€CÝ	�G„G€GÝ	�%Ð(˜dÐ(Ð(Ð(­&¬+Ñ
6Ô
6Ñ7Ô7Ð7ð �€|€|ÝÐ1 S¨¤ZÐ1Ð1Ñ2Ô2Ð2Ð2à�gŠg�i Ñ%Ô%ˆÝÐ+ cÐ+Ð+Ñ,Ô,Ð,ð —’˜ Ñ#Ô#€IØ�gŠg�i Ñ$Ô$€GØ�GÒÐÝÐ$Ñ%Ô%Ð%Ð%Ø	ð Ø—M’M‘O”Oð 	,ð 	,‰DˆAˆqÝ˜!�SÑ!Ô!ð , u°·²±	´	Ð'9Ð'9¸VÀqÇwÂwÁyÄyÐ=PÐ=På+Ô/Ð0bÐ0bÐdeÑfÔf�Ý�x‘=”= 1Ò$Ð$Ø% b q bœ\¨EÑ1°H¸R¸S¸S´MÑA�F�Fà"�FÝÐ*˜QÐ*Ð* &Ð*Ð*Ñ+Ô+Ð+øð	,õ 	ˆlÑÔÐõ ŒNÑÔ€EðÝ$ T¨3Ñ/Ô/ˆÝ”nÑ&Ô&¨Ñ.°$Ñ6ˆ
ˆ
øÝð ð ð Ý”nÑ&Ô&¨Ñ.°$Ñ6ˆ
ÝÐ? ZÐ?Ð?Ð?¸#Ð?Ð?Ñ@Ô@Ð@Øˆˆˆˆˆøøøøðøøøõ
 Ð.˜:Ð.Ð.Ð.Ð.Ñ/Ô/Ð/ÝÐ.¥# e¡*¤*Ð.Ð.Ñ/Ô/Ð/àð GÝ‰ŒˆØ$ð 	Gð 	G‰OˆI�tÝ),¨T©¬°Rª¨�D˜˜"˜”I Ñ%Ð%¸TˆEÝÐE�˜y­&¬,Ñ7Ô7ÐEÐEÐE¸eÐEÐEÑFÔFÐFÐFÝ	�G„G€G€G€Gs   È)I É
JÉ/JÊJc                 ó  — |                      d¦  «        }|st          d| › d�¦  «         dS |                      d¦  «        dk    r:t          d| › d|                      d¦  «        › d�¦  «         t          d	¦  «         dS 	 d
dlm}  |¦   «                              | ¦  «         n)# t          $ r}t          d|› �¦  «         Y d}~nd}~ww xY wt          ¦   «          t          d| › d�¦  «         	 d
dl	m
} |                      d¦  «        }	 t          |¦  «        }n# t          t          f$ r d}Y nw xY wt          |d¦  «        } |¦   «         5  t          | ||¬¦  «        }ddd¦  «         n# 1 swxY w Y   t!          | ¦  «        �swt          d¦  «         t          ¦   «          t          d¦  «         t          ¦   «          t          t#          dt$          j        ¦  «        ¦  «         t          t#          d| › d�t$          j        ¦  «        ¦  «         t          t#          d|› �t$          j        ¦  «        ¦  «         t          t#          dt$          j        ¦  «        ¦  «         t          t#          dt$          j        ¦  «        ¦  «         t          t#          dt$          j        ¦  «        ¦  «         t          t#          dt$          j        ¦  «        ¦  «         t          ¦   «          t          d| z   d z   ¦  «         dS |r!t)          d!t+          |¦  «        › d"�¦  «         nt)          d#¦  «         d$S # t          $ rG}	 d
d%l	m}  || ||¬&¦  «        }	n# t          $ r d}	Y nw xY wt          d'|	p|› �¦  «         Y d}~dS d}~ww xY w)(aj  Force a fresh OAuth flow for one server. Returns True on success.

    Wipes cached OAuth state (disk + in-process MCPOAuthManager cache),
    re-probes to trigger the browser flow, and verifies a token actually
    landed before reporting success. Shared by ``hermes mcp login`` and
    ``hermes mcp reauth`` so both behave identically for a single server.
    r€   rJ   u,   ' has no URL â€” not an OAuth-capable serverFrÓ   rÖ   z$' is not configured for OAuth (auth=ú)z?Use `hermes mcp remove` + `hermes mcp add` to reconfigure auth.r   rÙ   z&Could not clear existing OAuth state: Nr×   rØ   )Úforce_interactive_oauthr�   g        g     °s@)r�   uV   Server responded, but no OAuth token was obtained â€” authentication did not complete.z¶Some providers (e.g. Google Drive, Atlassian) do not support automatic client registration. For those you must create an OAuth client yourself and add its credentials to config.yaml:z    mcp_servers:z      ú:z        url: z        auth: oauthz        oauth:z-          client_id: "<your-oauth-client-id>"z5          client_secret: "<your-oauth-client-secret>"zThen re-run `hermes mcp login z`.u   Authenticated â€” z tool(s) availablez(Authenticated (server reported no tools)T)Ú!humanize_oauth_registration_error)Ú
server_urlzAuthentication failed: )rB   r)   r   rö   rÚ   r  r�   r&   r   rÈ   rK  r¿   rÀ   ro   r¾   rÅ   rÌ   r   r   r   r#   r­   rM  )
rG   rH   r€   rÚ   rÄ   rK  Ú_login_connect_timeoutrŸ   rM  Ú	humanizeds
             r   Ú_reauth_oauth_serverrQ    st  € ð ×
Ò
˜EÑ
"Ô
"€CØð ÝÐL˜$ÐLÐLÐLÑMÔMÐMØˆuØ×Ò˜Ñ Ô  GÒ+Ð+ÝÐ`˜$Ð`Ð`ÀM×DUÒDUÐV\ÑD]ÔD]Ð`Ð`Ð`ÑaÔaÐaÝÐOÑPÔPÐPØˆuðAØ7Ð7Ð7Ð7Ð7Ð7Øˆ‰Œ×Ò˜TÑ"Ô"Ð"Ð"øÝð Að Að AÝÐ?¸#Ð?Ð?Ñ@Ô@Ð@Ð@Ð@Ð@Ð@Ð@øøøøðAøøøõ 
�G„G€GÝ	Ð
0 dÐ
0Ð
0Ð
0Ñ1Ô1Ð1ð:Ø;Ð;Ð;Ð;Ð;Ð;à!.×!2Ò!2Ð3DÑ!EÔ!EÐð	)Ý%*Ð+AÑ%BÔ%BÐ"Ð"øÝ�:Ð&ð 	)ð 	)ð 	)Ø%(Ð"Ð"Ð"ð	)øøøå!$Ð%;¸UÑ!CÔ!CÐØ$Ð$Ñ&Ô&ð 	ð 	Ý(Ø�mÐ5Kðñ ô ˆEð	ð 	ð 	ñ 	ô 	ð 	ð 	ð 	ð 	ð 	ð 	øøøð 	ð 	ð 	ð 	õ % TÑ*Ô*ñ 	Ýð3ñô ð õ ‰GŒGˆGÝðPñô ð õ
 ‰GŒGˆGÝ•%Ð*­F¬JÑ7Ô7Ñ8Ô8Ð8Ý•%Ð( Ð(Ð(Ð(­&¬*Ñ5Ô5Ñ6Ô6Ð6Ý•%Ð-¨Ð-Ð-­v¬zÑ:Ô:Ñ;Ô;Ð;Ý•%Ð-­v¬zÑ:Ô:Ñ;Ô;Ð;Ý•%Ð(­&¬*Ñ5Ô5Ñ6Ô6Ð6Ý•%ÐIÍ6Ì:ÑVÔVÑWÔWÐWÝ•%ÐQÕSYÔS]Ñ^Ô^Ñ_Ô_Ð_Ý‰GŒGˆGÝÐ2°TÑ9¸DÑ@ÑAÔAÐAØ�5Øð 	AÝÐH­#¨e©*¬*ÐHÐHÐHÑIÔIÐIÐIåÐ?Ñ@Ô@Ð@ØˆtøÝð 
ð 
ð 
ð	ØIÐIÐIÐIÐIÐIà9Ð9Ø�c cðñ ô ˆIˆIøõ ð 	ð 	ð 	ØˆIˆIˆIð	øøøåÐ;¨Ð)9°cÐ;Ð;Ñ<Ô<Ð<Øˆuˆuˆuˆuˆuøøøøð
øøøs�   Â#B% Â%
CÂ/CÃCÃ0L4 ÄD ÄL4 ÄD2Ä/L4 Ä1D2Ä2L4 ÅE.Å"L4 Å.E2Å2L4 Å5E2Å6FL4 Ì 2L4 Ì4
NÌ?MÍN ÍM#Í N Í"M#Í#N Î Nc                 óÜ   — | j         }t          ¦   «         }||vr<t          d|› d�¦  «         |r%t          dd                     |¦  «        › �¦  «         dS t          |||         ¦  «         dS )aÛ  Force re-authentication for an OAuth-based MCP server.

    Deletes cached tokens (both on disk and in the running process's
    MCPOAuthManager cache) and triggers a fresh OAuth flow via the
    existing probe path.

    Use this when:
      - Tokens are stuck in a bad state (server revoked, refresh token
        consumed by an external process, etc.)
      - You want to re-authenticate to change scopes or account
      - A tool call returned ``needs_reauth: true``
    rJ   r  r  r  N)rG   rF   r)   r   r½   rQ  )r   rG   rE   s      r   Úcmd_mcp_loginrS  w  s…   € ð Œ9€DÝÑ Ô €Gà�7ÐÐÝÐ6˜$Ð6Ð6Ð6Ñ7Ô7Ð7Øð 	>ÝÐ<¨¯	ª	°'Ñ(:Ô(:Ð<Ð<Ñ=Ô=Ð=Øˆå˜˜w tœ}Ñ-Ô-Ð-Ð-Ð-r    c                 óH  — t          ¦   «         }t          | dd¦  «        }t          | dd¦  «        }|r÷d„ |                     ¦   «         D ¦   «         }|st          d¦  «         dS t	          ¦   «          t          dt          |¦  «        › d�¦  «         d	}|D ]`\  }}t	          ¦   «          t	          t          d
|› d�t          j        t          j	        z   ¦  «        ¦  «         t          ||¦  «        r|dz  }Œat	          ¦   «          t          d|› dt          |¦  «        › d�¦  «         dS |s t          d¦  «         t          d¦  «         dS ||vr<t          d|› d�¦  «         |r%t          dd                     |¦  «        › �¦  «         dS t          |||         ¦  «         dS )ad  Re-authenticate one OAuth MCP server, or all of them sequentially.

    ``hermes mcp reauth <name>`` re-auths a single server (same as ``login``).
    ``hermes mcp reauth --all`` discovers every ``auth: oauth`` server in
    config and re-auths them ONE AT A TIME.

    Serial-by-design: a human can only complete one browser OAuth flow at a
    time, so re-authing all servers concurrently would open N tabs at once
    and N-1 would time out. This is the self-service fix for the recurring
    stale-client ritual in GH#36767 (and avoids the startup popup storm when
    several servers go stale at once).
    r(  FrG   Nc                 óx   — g | ]7\  }}|                      d ¦  «        dk    ¯|                      d¦  «        ¯3||f‘Œ8S )rÓ   rÖ   r€   )rB   )rî   rä   Úcs      r   rï   z"cmd_mcp_reauth.<locals>.<listcomp>¢  sN   € ð 
ð 
ð 
Ù�q˜!Ø�uŠu�V‰}Œ} Ò'Ð'¨A¯EªE°%©L¬LÐ'ð �ˆFØ'Ð'Ð'r    z+No OAuth-based MCP servers found in config.zRe-authenticating z! OAuth server(s) one at a time...r   u	     â”€â”€ u    â”€â”€ru   zRe-authenticated rõ   z
 server(s)zBSpecify a server name, or use --all to re-auth every OAuth server.z=Usage: hermes mcp reauth <name>   |   hermes mcp reauth --allrJ   r  r  r  )rF   r§   rT   r   r   r­   r   r   rø   r+  rQ  r#   r)   r½   )r   rE   Údo_allrG   Úoauth_serversÚ	succeededrä   rV  s           r   Úcmd_mcp_reauthrZ  �  sä  € õ Ñ Ô €GÝ�T˜5 %Ñ(Ô(€FÝ�4˜ Ñ&Ô&€Dàð ð
ð 
Ø&Ÿ}š}™œð
ñ 
ô 
ˆð ð 	ÝÐ?Ñ@Ô@Ð@ØˆFÝ‰ŒˆÝÐX¥3 }Ñ#5Ô#5ÐXÐXÐXÑYÔYÐYØˆ	Ø!ð 	ð 	‰DˆAˆqÝ‰GŒGˆGÝ•%Ð. AÐ.Ð.Ð.µ´½f¼kÑ0IÑJÔJÑKÔKÐKÝ# A qÑ)Ô)ð Ø˜Q‘�	øÝ‰ŒˆÝÐO YÐOÐOµ°]Ñ1CÔ1CÐOÐOÐOÑPÔPÐPØˆàð ÝÐSÑTÔTÐTÝÐMÑNÔNÐNØˆØ�7ÐÐÝÐ6˜$Ð6Ð6Ð6Ñ7Ô7Ð7Øð 	>ÝÐ<¨¯	ª	°'Ñ(:Ô(:Ð<Ð<Ñ=Ô=Ð=Øˆå˜˜w tœ}Ñ-Ô-Ð-Ð-Ð-r    c           	      óú  ‡‡‡‡— ddl }|j                             ¦   «         s+t          d|j        ¬¦  «         |                     d¦  «         | j        }t          ¦   «         }||vr]t          d|› d�¦  «         t          | 
                    ¦   «         ¦  «        }|r%t          dd	                     |¦  «        › �¦  «         dS ||         }t          ¦   «          t          t          d
|› d�t          j        ¦  «        ¦  «         	 t!          ||¦  «        }n*# t"          $ r}t          d|› �¦  «         Y d}~dS d}~ww xY w|st%          d¦  «         dS |                     di ¦  «        }t)          |t*          ¦  «        r+|                     d¦  «        }	|                     d¦  «        }
nd}	d}
d„ |D ¦   «         Š	 ddlmŠ n# t0          $ r d„ ŠY nw xY w|	r>t)          |	t          ¦  «        r)d„ |	D ¦   «         Šˆˆfd„t3          ‰¦  «        D ¦   «         }ni|
r>t)          |
t          ¦  «        r)d„ |
D ¦   «         Šˆˆfd„t3          ‰¦  «        D ¦   «         }n)t5          t7          t9          |¦  «        ¦  «        ¦  «        }t9          |¦  «        }t9          |¦  «        }t          d|› d|› d|› d�¦  «         t          ¦   «          ddlm} d„ |D ¦   «         } |d|› d�||¦  «        }||k    rt          d ¦  «         dS t?          ¦   «         }tA          |d!|i ¬"¦  «        }t9          |¦  «        |k    r| !                    dd¦  «         nXˆfd#„tE          |¦  «        D ¦   «         }| #                    di ¦  «         ||d         d<   |d          !                    dd¦  «         || #                    d!i ¦  «        |<   tI          |¦  «         t9          |¦  «        }tK          d$|› d|› d%�¦  «         t          d&¦  «         dS )'z?Reconfigure which tools are enabled for an existing MCP server.r   Nz?Error: 'hermes mcp configure' requires an interactive terminal.)Úfileru   rJ   r  r3  r  rÝ   z' to discover tools...rÞ   zServer reports no tools.rŸ   rô   r&  c                 ó   — g | ]
}|d          ‘ŒS rò   rì   rí   s     r   rï   z%cmd_mcp_configure.<locals>.<listcomp>í  s   € Ð*Ð*Ð*˜1�!�A”$Ð*Ð*Ð*r    )Úmatches_name_filterc                 ó
   — | |v S r   rì   )r  Úpatternss     r   r^  z.cmd_mcp_configure.<locals>.matches_name_filterô  s   € Ø Ð(Ð(r    c                 ó,   — h | ]}t          |¦  «        ’ŒS rì   r!  ©rî   Úps     r   ú	<setcomp>z$cmd_mcp_configure.<locals>.<setcomp>ø  ó   € Ð/Ð/Ð/ !•s˜1‘v”vÐ/Ð/Ð/r    c                 ó2   •— h | ]\  }} ‰|‰¦  «        ¯|’ŒS rì   rì   )rî   ró   ÚtnÚinclude_setr^  s      €€r   rd  z$cmd_mcp_configure.<locals>.<setcomp>ù  s@   ø€ ð 
ð 
ð 
Ù�!�RØ"Ð" 2 {Ñ3Ô3ð
Øð
ð 
ð 
r    c                 ó,   — h | ]}t          |¦  «        ’ŒS rì   r!  rb  s     r   rd  z$cmd_mcp_configure.<locals>.<setcomp>þ  re  r    c                 ó2   •— h | ]\  }} ‰|‰¦  «        °|’ŒS rì   rì   )rî   ró   rg  Úexclude_setr^  s      €€r   rd  z$cmd_mcp_configure.<locals>.<setcomp>ÿ  s@   ø€ ð 
ð 
ð 
Ù�!�RØ&Ð& r¨;Ñ7Ô7ð
Øð
ð 
ð 
r    z
Currently rõ   z tools enabled for 'z'.rè   c                 ó4   — g | ]}|d          › d|d         › �‘ŒS rë   rì   rí   s     r   rï   z%cmd_mcp_configure.<locals>.<listcomp>  s.   € Ð8Ð8Ð8¨��1”Ð$Ð$˜a œdÐ$Ð$Ð8Ð8Ð8r    rð   rv   zNo changes made.rA   r¡   c                 ó    •— g | ]
}‰|         ‘ŒS rì   rì   )rî   ró   Ú
tool_namess     €r   rï   z%cmd_mcp_configure.<locals>.<listcomp>"  s   ø€ Ð>Ð>Ð>¨!˜
 1œÐ>Ð>Ð>r    zUpdated config: z tools enabledz/Start a new session for changes to take effect.)&ÚsysÚstdinÚisattyr   ÚstderrÚexitrG   rF   r)   rƒ   r  r   r½   r   r   rø   rÅ   r�   r&   rB   rC   rD   rŠ   r^  ÚImportErrorÚ	enumeraterú   rû   r­   rù   ré   r	   r   rQ   rü   rL   r
   r#   )r   Ú_sysrG   rE   rA  rW   Ú	all_toolsrÄ   r.  rô   r&  r  Ú	currentlyr  ré   r
  r  r?   Úserver_entryr  Ú	new_countrk  rh  r^  rn  s                        @@@@r   Úcmd_mcp_configurer{  Ä  sæ  øøøø€ àÐÐÐØŒ:×ÒÑÔð ÝÐOÐVZÔVaÐbÑbÔbÐbØ�	Š	�!‰ŒˆØŒ9€DÝÑ Ô €Gà�7ÐÐÝÐ6˜$Ð6Ð6Ð6Ñ7Ô7Ð7Ý˜Ÿš™œÑ(Ô(ˆ	Øð 	8ÝÐ6 §	¢	¨)Ñ 4Ô 4Ð6Ð6Ñ7Ô7Ð7Øˆà
�$Œ-€Cõ 
�G„G€GÝ	�%Ð@ DÐ@Ð@Ð@Å&Ä+Ñ
NÔ
NÑOÔOÐOðÝ(¨¨sÑ3Ô3ˆ	ˆ	øÝð ð ð ÝÐ* SÐ*Ð*Ñ+Ô+Ð+Øˆˆˆˆˆøøøøðøøøð ð ÝÐ+Ñ,Ô,Ð,Øˆð —’˜ Ñ$Ô$€IÝ�)�TÑ"Ô"ð Ø—-’- 	Ñ*Ô*ˆØ—-’- 	Ñ*Ô*ˆˆàˆØˆà*Ð* 	Ð*Ñ*Ô*€Jð)Ø6Ð6Ð6Ð6Ð6Ð6Ð6øÝð )ð )ð )ð	)ð 	)ð 	)ð 	)ð 	)ð)øøøð ð 2•:˜g¥tÑ,Ô,ð 2Ø/Ð/ wÐ/Ñ/Ô/ˆð
ð 
ð 
ð 
ð 
Ý$ ZÑ0Ô0ð
ñ 
ô 
ˆˆð 
ð 2•Z ­Ñ.Ô.ð 2Ø/Ð/ wÐ/Ñ/Ô/ˆð
ð 
ð 
ð 
ð 
Ý$ ZÑ0Ô0ð
ñ 
ô 
ˆˆõ
 �5¥ Y¡¤Ñ0Ô0Ñ1Ô1ˆå�LÑ!Ô!€IÝ�	‰NŒN€EÝ	Ð
F�yÐ
FÐ
F 5Ð
FÐ
F¸dÐ
FÐ
FÐ
FÑGÔGÐGÝ	�G„G€Gð 6Ð5Ð5Ð5Ð5Ð5à8Ð8¨iÐ8Ñ8Ô8€FàÐØ$˜TÐ$Ð$Ð$ØØñô €Fð �ÒÐÝÐ Ñ!Ô!Ð!Øˆõ ‰]Œ]€FÝ˜6 =°$ÀÐCÑCÔC€Lå
ˆ6�{„{�eÒÐà×Ò˜ $Ñ'Ô'Ð'Ð'à>Ð>Ð>Ð>­v°f©~¬~Ð>Ñ>Ô>ˆØ×Ò ¨Ñ,Ô,Ð,Ø+7ˆ�WÔ˜iÑ(Ø�WÔ×!Ò! )¨TÑ2Ô2Ð2à1=€F×Ò�m RÑ(Ô(¨Ñ.Ý�ÑÔÐå�F‘”€IÝÐA 	ÐAÐA¨EÐAÐAÐAÑBÔBÐBÝ	Ð
;Ñ<Ô<Ð<Ð<Ð<s*   ÄD Ä
D=Ä D8Ä8D=Æ:G ÇGÇGc                 ó:  — t          | dd¦  «        }|dk    r#ddlm}  |t          | dd¦  «        ¬¦  «         dS |d	k    rdd
lm}  |¦   «          dS |dk    rddlm}  |¦   «          dS |dk    r?ddlm} ddl} |t          | dd¦  «        pd¦  «        }|r|                     |¦  «         dS t          t          t          t          t          t          t          t          t          t          dœ
}|                     |¦  «        }	|	r |	| ¦  «         dS dd
lm}  |¦   «          t#          t%          dt&          j        ¦  «        ¦  «         t+          d¦  «         t+          d¦  «         t+          d¦  «         t+          d¦  «         t+          d¦  «         t+          d¦  «         t+          d¦  «         t+          d¦  «         t+          d¦  «         t+          d¦  «         t+          d¦  «         t+          d¦  «         t+          d¦  «         t#          ¦   «          dS ) z/Main dispatcher for ``hermes mcp`` subcommands.Ú
mcp_actionNÚserver   )Úrun_mcp_serverÚverboseF)r€  Úpicker)Ú
run_pickerÚcatalog)Úshow_catalogÚinstall)Úinstall_by_nameÚ
identifierr8   )
Úaddr  Úrmrƒ   ÚlsÚtestÚ	configurer?   ÚloginÚreauthz  Commands:zOhermes mcp                                    Open the catalog picker (default)zEhermes mcp catalog                            List Nous-approved MCPszChermes mcp install <name>                     Install a catalog MCPz?hermes mcp serve                              Run as MCP serverzEhermes mcp add <name> --url <endpoint>        Add a custom MCP serverz@hermes mcp add <name> --command <cmd>         Add a stdio serverzEhermes mcp add <name> --preset <preset>       Add from a known presetz=hermes mcp remove <name>                      Remove a serverzEhermes mcp list                               List configured serversz=hermes mcp test <name>                        Test connectionz:hermes mcp configure <name>                   Toggle toolszChermes mcp login <name>                       Re-authenticate OAuthzNhermes mcp reauth <name> | --all              Re-auth one or all OAuth servers)r§   Ú	mcp_server  Úhermes_cli.mcp_pickerr‚  r„  r†  ro  rs  r  r  r1  rH  r{  rS  rZ  rB   r   r   r   rø   r   )
r   Úactionr  r‚  r„  r†  rv  ÚrcÚhandlersÚhandlers
             r   rÒ   rÒ   1  sv  € å�T˜<¨Ñ.Ô.€Fà�ÒÐØ,Ð,Ð,Ð,Ð,Ð,Øˆ�w t¨Y¸Ñ>Ô>Ð?Ñ?Ô?Ð?Øˆð �ÒÐØ4Ð4Ð4Ð4Ð4Ð4Øˆ
‰ŒˆØˆØ�ÒÐØ6Ð6Ð6Ð6Ð6Ð6Øˆ‰ŒˆØˆØ�ÒÐØ9Ð9Ð9Ð9Ð9Ð9ØÐÐÐØˆ_�W T¨<¸Ñ<Ô<ÐBÀÑCÔCˆØð 	Ø�IŠI�b‰MŒMˆMØˆõ Ý ÝÝÝÝÝ&Ý#ÝÝ ðð €Hð �lŠl˜6Ñ"Ô"€GØð Øˆ�‰Œˆˆˆð 	5Ð4Ð4Ð4Ð4Ð4Øˆ
‰ŒˆÝ�e�M¥6¤;Ñ/Ô/Ñ0Ô0Ð0ÝÐ_Ñ`Ô`Ð`ÝÐUÑVÔVÐVÝÐSÑTÔTÐTÝÐOÑPÔPÐPÝÐUÑVÔVÐVÝÐPÑQÔQÐQÝÐUÑVÔVÐVÝÐMÑNÔNÐNÝÐUÑVÔVÐVÝÐMÑNÔNÐNÝÐJÑKÔKÐKÝÐSÑTÔTÐTÝÐ^Ñ_Ô_Ð_Ý‰Œˆˆˆr    )Tr   )HÚ__doc__rª   Úloggingr5  r]   r?  Útypingr   r   r   r   r   Úhermes_cli.configr   r	   r
   r   r   r   Úhermes_cli.colorsr   r   Úhermes_constantsr   Úhermes_cli.mcp_securityr   rŠ   r   r   Ú	getLoggerÚ__name__rÊ   Úcompilerx   r   re   Ú__annotations__r   r#   r&   r)   r®   r7   r>   rD   rF   rO   rR   rX   ra   rg   rl   rq   r~   Útupler…   rŽ   r¿   rÅ   rÌ   rÁ   r�   rÂ   r  r  r1  rH  rQ  rS  rZ  r{  rÒ   rì   r    r   ú<module>r¡     s  ððð ð ð €€€Ø €€€Ø 	€	€	€	Ø 	€	€	€	Ø €€€Ø 3Ð 3Ð 3Ð 3Ð 3Ð 3Ð 3Ð 3Ð 3Ð 3Ð 3Ð 3Ð 3Ð 3ðð ð ð ð ð ð ð ð ð ð ð ð ð ð ð ð ,Ð +Ð +Ð +Ð +Ð +Ð +Ð +Ø 0Ð 0Ð 0Ð 0Ð 0Ð 0Ø =Ð =Ð =Ð =Ð =Ð =Ø :Ð :Ð :Ð :Ð :Ð :Ð :Ð :à	ˆÔ	˜8Ñ	$Ô	$€à�2”:Ð9Ñ:Ô:Ð ð ØØ�ðð ð+€ˆd�3˜˜S #˜XœÐ&Ô'ð ð ñ ð*�ð *ð *ð *ð *ð0�3ð 0ð 0ð 0ð 0ð1�3ð 1ð 1ð 1ð 1ð.�ð .ð .ð .ð .ð	ð 	�sð 	 Tð 	°Tð 	ð 	ð 	ð 	ð 05ÀRð Hð Hð H�cð H¨ð H¸sð HÈCð Hð Hð Hð Hðð ˜X dœ^ð °t¸CÀ¸I´ð ð ð ð ð˜3ð ¨tð ¸ð ð ð ð ð&
˜Sð 
 Tð 
ð 
ð 
ð 
ð $ s¨D y¤/ð °e¸DÀ$ÀsÄ)¸OÔ6Lð ð ð ð ðB#˜cð # cð #ð #ð #ð #ð ð ¨ð ð ð ð ð7˜sð 7 t¨C°¨H¤~ð 7ð 7ð 7ð 7ð& #ð &¨cð &°d¸3À¸8´nð &ð &ð &ð &ð H¨T°#¬YÔ$7ð ¸DÀÀcÀ¼Nð ð ð ð ð&(Ø
ð(ð ˜#”ð(ð 
�#Œð	(ð
 �cŒ]ð(ð �3Œið(ð ˜˜S˜”>ð(ð ˆ8�CŒ=˜( 3œ-¨¨c¬°DÐ8Ô9ð(ð (ð (ð (ðH) tð )°ð )ð )ð )ð )ð2 AEðdØcgðdð dð dØ
ðdØðdØ.6°u¬oðdØRZÐ[_ÔR`ðdà	ˆ%��S�Œ/Ôðdð dð dð dðN ð ¨ð ð ð ð ð " ð "°9ð "ð "ð "ð "ð$J9ð J9ð J9ð^ð ð ð@@ð @ð @ð @ðJ;ð ;ð ;ð@a˜sð a°4ð a¸Dð að að að aðH.ð .ð .ð2/.ð /.ð /.ðhh=ð h=ð h=ðZ>ð >ð >ð >ð >r    