o
    ưix*                     @  s  U d dl mZ d dlmZmZmZmZmZmZm	Z	m
Z
 d dlmZmZmZ d dlmZ d dlmZ d dlmZ d dlZd dlZd dlZd dlmZ d d	lmZ d
ZdZdZdZdZdZ dZ!ej"#ej"$ddZ%dcddZ&ddddZ'ded d!Z(dfd"d#Z)dgd%d&Z*ed'd(G d)d* d*Z+e+d+d,e+d-d.e+d/d0d1d2 d3e+d4d5d6d2 d3e+d7d8d9e+d:d;d<d2 d3e+d=e+d>e+d?d@dAd2 d3e+dBdCdDd2 d3g
Z,dEe-dF< dhdidIdJZ.djdLdMZ/dkdTdUZ0dldmdWdXZ1		dldYdZd[dndadbZ2dS )o    )annotations)AnyCallableDictFinalListOptionalSequenceTuple)datetime	timedeltatimezone)Lock)Path)	dataclassN)sap_service_key)_get_httpx_clientz/oauth/tokenZAICORE_CONFIGZAICORE_HOMEZAICORE_PROFILEZVCAP_SERVICESZaicoreZAICORE_SERVICE_KEY~z.aicorereturnstrc                   C  s   t ttS N)osgetenvHOME_PATH_ENV_VARDEFAULT_HOME_PATH r   r   S/home/app/Keep/.python/lib/python3.10/site-packages/litellm/llms/sap/credentials.py	_get_home      r   dDict[str, Any]pathSequence[str]r   c                 C  s:   | }|D ]}t |tr||vrtd||| }q|S )N.)
isinstancedictKeyErrorjoin)r   r!   curkr   r   r   _get_nested   s   
r*   var_nameOptional[Dict[str, Any]]c                 C  s8   t j| }|s
d S zt|W S  tjy   Y d S w r   )r   environgetjsonloadsJSONDecodeError)r+   rawr   r   r   _load_json_env(   s   r3   c                   C  s   t tpi S r   )r3   VCAP_SERVICES_ENV_VARr   r   r   r   
_load_vcap2   r   r5   labelc                 C  s8   t   D ]}|D ]}|d| kr|    S q	qd S )Nr6   )r5   valuesr.   )r6   ZservicesZsvcr   r   r   _get_vcap_service6   s   r8   T)frozenc                   @  s:   e Zd ZU ded< dZded< dZded< dZded	< dS )
CredentialsValuer   nameNzOptional[Tuple[str, ...]]vcap_keyOptional[str]defaultzOptional[Callable[[str], str]]transform_fn)__name__
__module____qualname____annotations__r<   r>   r?   r   r   r   r   r:   >   s
   
 r:   	client_id)Zclientidclient_secret)Zclientsecretauth_urlurlc                 C     |  d| trd S t S N/ rstripendswithAUTH_ENDPOINT_SUFFIXrG   r   r   r   <lambda>L   
    rQ   )r?   base_url)ZserviceurlsZ
AI_API_URLc                 C  s   |  d| drd S d S )NrK   z/v2rL   )rN   rO   rG   r   r   r   rQ   R   rR   resource_groupr>   )r>   cert_url)Zcerturlc                 C  rI   rJ   rM   rG   r   r   r   rQ   Y   rR   cert_file_pathkey_file_pathcert_str)Zcertificatec                 C     |  ddS N\n
replacesr   r   r   rQ   a       key_str)keyc                 C  rY   rZ   r]   r_   r   r   r   rQ   d   ra   zFinal[List[CredentialsValue]]CREDENTIAL_VALUESprofiler=   c                 C  s   t t }| ptjt} tt}|rt |n|| dv rdnd|  d }|rZ| rZz|j	dd}t
|W  d   W S 1 sDw   Y  W n t
jyY   t| dw |s`| dvrktd	| d
| di S )z
    Loads config JSON from:
      1) $AICORE_CONFIG if set, otherwise
      2) $AICORE_HOME/config.json (or config_<profile>.json when profile is given/not default)
    Returns {} when nothing is found.
    )NrL   r>   zconfig.jsonZconfig_z.jsonzutf-8)encodingNz, is not valid JSON. Please fix or remove it!z)Unable to locate profile config file at 'z' in AICORE_HOME '')r   r   r   r-   r.   PROFILE_ENV_VARr   CONFIG_FILE_ENV_VARexistsopenr/   loadr1   r&   FileNotFoundError)re   homeZcfg_envZcfg_pathfr   r   r   	init_confi   s0   



&rp   r;   c                 C  s   d|    S )NZAICORE_)upper)r;   r   r   r   	_env_name   s   rr   credkwargsenvDict[str, str]configservice_likec                C  s   | j |v r|| j  d ur|| j  S t| j }||v r$|| d ur$|| S || j fD ]}||v r;|| d ur;||   S q)|r`| jr`zt|d| j }|d urQ|W S W | jS  ty_   Y | jS w | jS )N)credentials)r;   rr   r<   r*   r&   r>   )rs   rt   ru   rw   rx   Zenv_keyrc   valr   r   r   _resolve_value   s*   	


r{   service_keyc           	      K  s   t |}tj}d}|s| ptpttptt}i }tD ]}t	|||||d}|du r+q|j
r3|
|}|||j< qd| v rF|d|d< |S )a>  
    Resolution order per key:
      kwargs
      > env (AICORE_<NAME>)
      > config (AICORE_<NAME> or plain <name>)
      > service-like source from JSON in $AICORE_SERVICE_KEY (same structure as a VCAP service object)
        falling back to service entry in $VCAP_SERVICES with label 'aicore'
      > default
    N)rt   ru   rw   rx   rU   rF   )rp   r   r-   r   r3   SERVICE_KEY_ENV_VARr8   VCAP_AICORE_SERVICE_NAMErd   r{   r?   r;   keyspop)	r|   re   rt   rw   ru   rx   outrs   valuer   r   r   fetch_credentials   s$   

r   g      >@<   )timeoutexpiry_buffer_minutesr   floatr   int"Tuple[Callable[[], str], str, str]c                  s  t d| |d|}|d|d|d|d|d	|d|dr1s5td	d
ud
uo?	d
ud
uoFd
ug}tdd |D dkrWtdt 
d
d
ddfddd	fdd d 
fdd}||d |d fS )a  
    Creates a callable that fetches and caches an OAuth2 bearer token
    using credentials from `fetch_credentials()`.

    The callable:
      - Automatically loads credentials via fetch_credentials(profile, **overrides)
      - Fetches a new token only if expired or near expiry
      - Caches token thread-safely with a configurable refresh buffer

    Args:
        profile: Optional AICore profile name
        timeout: HTTP request timeout in seconds (default 30s)
        expiry_buffer_minutes: Refresh the token this many minutes before expiry
        overrides: Any explicit credential overrides (client_id, client_secret, etc.)

    Returns:
        Callable[[], str]: function returning a valid "Bearer <token>" string.
    )r|   re   rF   rD   rE   rX   rb   rV   rW   z@fetch_credentials did not return valid 'auth_url' or 'client_id'Nc                 s  s    | ]}t |V  qd S r   )bool).0mr   r   r   	<genexpr>	  s    z$get_token_creator.<locals>.<genexpr>   zuInvalid credentials: provide exactly one of client_secret, (cert_str & key_str), or (cert_file_path & key_file_path).r   tuple[str, datetime]c           
   
     s   dd}r|d< t  }|j |d}z'|  | }|d }t|dd}ttj	t
|d }d	| |fW S  tyX } zt|d
t|}	td|	 |d }~ww )NZclient_credentials)Z
grant_typerD   rE   )dataaccess_token
expires_ini  )secondszBearer textzToken request failed: )r   postraise_for_statusr/   r   r.   r   nowr   utcr   	Exceptiongetattrr   RuntimeError)
	cert_pairr   clientresppayloadr   r   Zexpiry_dateemsg)rF   rD   rE   r   r   _request_token  s"   
z)get_token_creator.<locals>._request_tokenc               	     s   r  S rrrr dd}  dd}t Q}tj|d}tj|d}t|d}||  W d    n1 s=w   Y  t|d}|| W d    n1 sWw   Y   ||fdW  d    S 1 smw   Y   fdS )Nr[   r\   zcert.pemzkey.pemw)r   )r^   tempfileTemporaryDirectoryr   r!   r'   rk   write)Zcert_str_fixedZkey_str_fixedtmpZ	cert_pathZkey_pathro   )r   rV   rX   rE   rW   rb   r   r   _fetch_token&  s"   
 	z'get_token_creator.<locals>._fetch_tokenr   c                    sd   & t tj} d u sd u s|  tdk r  \W  d    S 1 s+w   Y  d S )N)minutes)r   r   r   r   r   )r   )r   r   locktokentoken_expiryr   r   	get_token9  s   
$z$get_token_creator.<locals>.get_tokenrS   rT   r   r   )r   r   r   r   )r   r.   
ValueErrorsumr   )r|   re   r   r   Z	overridesry   modesr   r   )r   r   rF   rV   rX   rD   rE   r   rW   rb   r   r   r   r   get_token_creator   s6   






r   r   )r   r    r!   r"   r   r   )r+   r   r   r,   )r   r    )r6   r   r   r,   r   )re   r=   r   r    )r;   r   r   r   )rs   r:   rt   r    ru   rv   rw   r    rx   r,   r   r=   )NN)r|   r=   re   r=   r   rv   )
r|   r=   re   r=   r   r   r   r   r   r   )3
__future__r   typingr   r   r   r   r   r   r	   r
   r   r   r   	threadingr   pathlibr   dataclassesr   r/   r   r   Zlitellmr   Z&litellm.llms.custom_httpx.http_handlerr   rP   ri   r   rh   r4   r~   r}   r!   r'   
expanduserr   r   r*   r3   r5   r8   r:   rd   rC   rp   rr   r{   r   r   r   r   r   r   <module>   s~    (


	





#
'
#"