
    gj                        U d Z ddlZddlZddlZddlmZ ddlmZmZ ddl	m
Z
 ddl	mZ  ej        e          Zd	Zd
Z G d ded          Z G d de          Zg i dZeed<   daedz  ed<   dee         fdZdefdZdeeef         defdZdefdZdefdZdededz  dedz  fdZdededdfdZ dedz  fd Z!dS )!u  Detect whether the process is being invoked by an AI coding agent.

Detection is based on environment variables that AI agents set in their shell
sessions. `AI_AGENT` and `AGENT` are treated as a universal standard (any
tool can set its harness id there); the remaining checks are tool-specific and
ordered by priority (first match wins).

The list of known harnesses is maintained on the Hub and exposed at
`{ENDPOINT}/api/agent-harnesses`. We fetch it at most once a day and cache it
locally so the list can be updated without requiring a new client release.

Detection is entirely best-effort: there is no hardcoded list of harnesses. When
the registry cannot be fetched (and no cached copy is available), detection simply
reports "no agent". Any error while fetching/reading the registry is swallowed —
detection must never make a process fail.

More details: https://huggingface.co/docs/hub/agents-overview#register-your-agent-harness
    N)Path)Optional	TypedDict   )	constants   )loggingiQ    c                   .    e Zd ZU dZeeef         ed<   dS )HarnessInfozbA single harness entry. `envVars` maps an env var name to a match pattern (see `_env_vars_match`).envVarsN)__name__
__module____qualname____doc__dictstr__annotations__     g/var/www/app.qaans.com/backend/venv/lib/python3.11/site-packages/huggingface_hub/utils/_detect_agent.pyr   r   4   s,         ll#s(^r   r   F)totalc                   D    e Zd ZU dZee         ed<   eeef         ed<   dS )RegistryzJThe agent harness registry, as served by `{ENDPOINT}/api/agent-harnesses`.standardEnvVars	harnessesN)	r   r   r   r   listr   r   r   r   r   r   r   r   r   :   s>         TT#YC$%%%%%%r   r   )r   r   _EMPTY_REGISTRY	_registryreturnc                  t   t                      } |                     d          pg }|                     d          pi }|                                D ]r\  }}|pi                     d          }|rt          |          r|c S |D ]>}t          j                            |d                                          |k    r|c c S ?sd |                                D             }|D ]S}t          j                            |d                                                                          x}r||v r|c S  dS TdS )a[  Return the id of the detected AI agent harness or `None`.

    Harnesses are checked in registry order; for each one we match its env var
    pattern(s) and, failing that, the standard `AI_AGENT` / `AGENT` vars
    against the harness id. The first match wins. When a standard var is set to
    an unrecognized value, `"unknown"` is returned.
    r   r   r    c                 6    h | ]}|                                 S r   )lower).0ks     r   	<setcomp>zdetect_agent.<locals>.<setcomp>^   s     @@@!AGGII@@@r   unknownN)	_get_registrygetitems_env_vars_matchosenvironstripkeysr$   )	registrystandard_varsr   
harness_idinfoenv_varsvarlowercased_harnessesvalues	            r   detect_agentr9   I   sq    HLL!2339rM[))/RI%OO-- " "
DJB##I.. 	11 	  	" 	"Cz~~c2&&,,..*<<!!!!!! =	"
 A@y~~/?/?@@@  JNN3++113399;;;5 	,,,99	
 4r   c                  "    t                      duS )zDReturn `True` if the process is being invoked by an AI coding agent.N)r9   r   r   r   is_agentr;   h   s    >>%%r   r5   c                     |                                  D ]9\  }}t          j                            |          }|s'|dk    r dS ||k    r dS :dS )zReturn `True` if any `(var, pattern)` from the harness matches the environment.

    Supported patterns:
      - `"*"`: the variable is set to any non-empty value
      - `"<value>"`: the variable equals this exact value
    *TF)r+   r-   r.   r*   )r5   r6   patternr8   s       r   r,   r,   m   sk     !((  W
s## 	c>>44G44 5r   c                      t           C	 t                      a n3# t          $ r& t                              dd           t
          a Y nw xY wt           S )zReturn the harness registry, loading (and caching in-process) on first call.

    Best-effort: any unexpected error degrades to an empty registry so detection
    never raises.
    Nz+Could not resolve agent harnesses registry.Texc_info)r   _load_registry	Exceptionloggerdebugr   r   r   r   r)   r)      s`     	(&((II 	( 	( 	(LLFQULVVV'III	( s    -AAc                      t           j        } t          | t                    x}r|S t	                      x}t          | |           |S t          | d          x}r|S t          S )zResolve the registry from the local cache or the Hub.

    No hardcoded list: if the Hub is unreachable and no cached copy exists, an
    empty registry is returned (i.e. no agent is detected).
    )max_ageN)r   AGENT_HARNESSES_PATH_read_cached_registry_REGISTRY_TTL_SECONDS_fetch_registry_write_cached_registryr   )pathcachedfetchedstales       r   rB   rB      s}     )D 't5JKKKKv  #$$$1tW--- &dD9999u r   rM   rG   c                    	 t           j                            |           sdS |9t          j                    t           j                            |           z
  |k    rdS t          | d          5 }t          j        |          cddd           S # 1 swxY w Y   dS # t          $ r  t          
                    dd           Y dS w xY w)zBReturn the cached registry, or `None` if missing/stale/unreadable.Nutf-8encodingz/Could not read cached agent harnesses registry.Tr@   )r-   rM   existstimegetmtimeopenjsonloadrC   rD   rE   )rM   rG   fs      r   rI   rI      s   	w~~d## 	4DIKK"'2B2B42H2H$HW#T#T4$))) 	 Q9Q<<	  	  	  	  	  	  	  	  	  	  	  	  	  	  	  	  	  	    FQUVVVtts@   B 9B B /BB BB BB &CCr1   c                 4   	 t          |           j                            dd           t          | dd          5 }t	          j        ||           d d d            d S # 1 swxY w Y   d S # t          $ r  t                              dd           Y d S w xY w)NT)parentsexist_okwrR   rS   z)Could not cache agent harnesses registry.r@   )	r   parentmkdirrX   rY   dumprC   rD   rE   )rM   r1   r[   s      r   rL   rL      s    QT

t<<<$g... 	#!Ih"""	# 	# 	# 	# 	# 	# 	# 	# 	# 	# 	# 	# 	# 	# 	# 	# 	# 	# Q Q Q@4PPPPPPQs4   ;A- A A-  A$$A- 'A$(A- -&BBc                  8   t           j        rdS 	 ddlm}   |                                 t           j         dt                    }|                                 |                                S # t          $ r  t                              dd           Y dS w xY w)	zMFetch the registry from the Hub. Returns `None` when offline or on any error.Nr   )get_sessionz/api/agent-harnesses)timeoutz6Could not fetch agent harnesses registry from the Hub.Tr@   )r   HF_HUB_OFFLINE_httprd   r*   ENDPOINT_REGISTRY_FETCH_TIMEOUTraise_for_statusrY   rC   rD   rE   )rd   responses     r   rK   rK      s     t&&&&&&;==$$!777+ % 
 
 	!!###}}   MX\]]]tts   AA/ /&BB)"r   rY   r-   rV   pathlibr   typingr   r   r"   r   r	   
get_loggerr   rD   rJ   ri   r   r   r   r   r   r   r9   boolr;   r   r,   r)   rB   intrI   rL   rK   r   r   r   <module>rq      sR    &  				        & & & & & & & &             
	H	%	% "       )5    & & & & &y & & & 13DD D D D "	8d? ! ! !hsm    >&$ & & & &
d38n     $x         . cDj X_    Q Q QT Q Q Q QD      r   