o
    i eGA                     @   s   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ZddlZddlZddl	m
Z ddlZddlZddlZddlZddlmZ ddlmZ e ZdZdZdZdZd	Zg d
ZG dd dZ	ddejjj fddZ!G dd dZ"G dd dej#Z$dd Z%dS )z8Provides authentication support for TensorBoardUploader.    N)util)
tb_logging)openidz.https://www.googleapis.com/auth/userinfo.emaila	  
    {
        "installed":{
            "client_id":"373649185512-8v619h5kft38l4456nm2dj4ubeqsrvh6.apps.googleusercontent.com",
            "project_id":"hosted-tensorboard-prod",
            "auth_uri":"https://accounts.google.com/o/oauth2/auth",
            "token_uri":"https://oauth2.googleapis.com/token",
            "auth_provider_x509_cert_url":"https://www.googleapis.com/oauth2/v1/certs",
            "client_secret":"pOyAuU2yq2arsM98Bw5hwYtr",
            "redirect_uris":["http://localhost"]
        }
    }
z)https://oauth2.googleapis.com/device/codez,urn:ietf:params:oauth:grant-type:device_codea  
    {
        "installed":{
            "client_id":"373649185512-26ojik4u7dt0rdtfdmfnhpajqqh579qd.apps.googleusercontent.com",
            "project_id":"hosted-tensorboard-prod",
            "auth_uri":"https://accounts.google.com/o/oauth2/auth",
            "token_uri":"https://oauth2.googleapis.com/token",
            "auth_provider_x509_cert_url":"https://www.googleapis.com/oauth2/v1/certs",
            "client_secret":"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"
        }
    }
)tensorboardcredentialszuploader-creds.jsonc                   @   s:   e Zd ZdZe ZefddZdd Zdd Zdd	 Z	d
S )CredentialsStorezAPrivate file store for a `google.oauth2.credentials.Credentials`.c                 C   sP   |t ju rt }|du rtd |du rd| _dS tjj	|gt
R  | _dS )aw  Creates a CredentialsStore.

        Args:
          user_config_directory: Optional absolute path to the root directory for
            storing user configs, under which to store the credentials file. If not
            set, defaults to a platform-specific location. If set to None, the
            store is disabled (reads return None; write and clear are no-ops).
        Nz@Credentials caching disabled - no private config directory found)r   _DEFAULT_CONFIG_DIRECTORYr   get_user_config_directoryloggerwarning_credentials_filepathospathjoin&TENSORBOARD_CREDENTIALS_FILEPATH_PARTS)selfuser_config_directory r   H/var/www/myenv/lib/python3.10/site-packages/tensorboard/uploader/auth.py__init__   s   
	
zCredentialsStore.__init__c                 C   s2   | j du rdS tj| j rtjjj| j S dS )zMReturns the current `google.oauth2.credentials.Credentials`, or
        None.N)	r   r   r   existsgoogleoauth2r   Credentialsfrom_authorized_user_file)r   r   r   r   read_credentials   s   

z!CredentialsStore.read_credentialsc                 C   s   t |tjjjstdt| | jdu rdS tj	dk}t
j| j|d |j|j|j|j|jdd}t| jd}t|| W d   dS 1 sJw   Y  dS )z>Writes a `google.oauth2.credentials.Credentials` to the store.z#Cannot write credentials of type %sNnt)privateauthorized_user)refresh_token	token_uri	client_idclient_secretscopestypew)
isinstancer   r   r   r   	TypeErrorr$   r   r   namer   make_file_with_directoriesr   r    r!   r"   r#   openjsondump)r   r   r   datafr   r   r   write_credentials   s(   


"z"CredentialsStore.write_credentialsc              
   C   sV   | j du rdS z	t| j  W dS  ty* } z|jtjkr W Y d}~dS d}~ww )z:Clears the store of any persisted credentials information.N)r   r   removeOSErrorerrnoENOENT)r   er   r   r   clear   s   
zCredentialsStore.clearN)
__name__
__module____qualname____doc__objectr   r   r   r/   r5   r   r   r   r   r   |   s    r   Freturnc                 C   sz   t }| s.tdr.ztt}tjj||d}|j	ddW S  t
jy-   tjd Y nw tt}t||d}| S )a+  Makes the user authenticate to retrieve auth credentials.

    The default behavior is to use the [installed app flow](
    http://developers.google.com/identity/protocols/oauth2/native-app), in which
    a browser is started for the user to authenticate, along with a local web
    server. The authentication in the browser would produce a redirect response
    to `localhost` with an authorization code that would then be received by the
    local web server started here.

    The two most notable cases where the default flow is not well supported are:
    - When the uploader is run from a colab notebook.
    - Then the uploader is run via a remote terminal (SSH).

    If any of the following is true, a different auth flow will be used:
    - the flag `--auth_force_console` is set to true, or
    - a browser is not available, or
    - a local web server cannot be started

    In this case, a [limited-input device flow](
    http://developers.google.com/identity/protocols/oauth2/limited-input-device)
    will be used, in which the user is presented with a URL and a short code
    that they'd need to use to authenticate and authorize access in a separate
    browser or device. The uploader will poll for access until the access is
    granted or rejected, or the initiated authorization request expires.
    DISPLAY)r#   r   )portz.Falling back to remote authentication flow...
)OPENID_CONNECT_SCOPESr   getenvr+   loads"_INSTALLED_APP_OAUTH_CLIENT_CONFIG
auth_flowsInstalledAppFlowfrom_client_configrun_local_server
webbrowserErrorsysstderrwrite)_LIMITED_INPUT_DEVICE_OAUTH_CLIENT_CONFIG_LimitedInputDeviceAuthFlowrun)force_consoler#   client_configflowr   r   r   authenticate_user   s   

rQ   c                   @   s^   e Zd ZdZdd ZdejjjfddZ	dd Z
d	ed
edefddZdejjjfddZdS )rL   zOAuth flow to authenticate using the limited-input device flow.

    See:
    http://developers.google.com/identity/protocols/oauth2/limited-input-device
    c                 C   s   |d | _ || _d S )N	installed)_client_config_scopes)r   rO   r#   r   r   r   r      s   

z$_LimitedInputDeviceAuthFlow.__init__r;   c                 C   sL   |   }dj|d |d d}t| | j|d |d |d d}| |S )	NzTo sign in with the TensorBoard uploader:

1. On your computer or phone, visit:

   {url}

2. Sign in with your Google account, then enter:

   {code}
verification_url	user_code)urlcodedevice_codeinterval
expires_in)rY   polling_intervalexpiration_seconds)_send_device_auth_requestformatprint_poll_for_auth_token_build_credentials)r   device_responseprompt_messageauth_responser   r   r   rM     s   
z_LimitedInputDeviceAuthFlow.runc                 C   s>   | j d d| jd}tjt|d }d|vrtd|S )Nr!    )r!   scoper-   rY   zZThere was an error while contacting Google's authorization server. Please try again later.)rS   r   rT   requestspost_DEVICE_AUTH_CODE_URIr+   RuntimeError)r   paramsrr   r   r   r^     s   
z5_LimitedInputDeviceAuthFlow._send_device_auth_requestrY   r\   r]   c           	      C   s   | j d }| j d | j d |td}t | }t |k rvtj||d}| }d|v r/|S d|v r?|d dkr?t| n1d|v rU|d d	krUt|d
 }t| nd|v rc|d dkrctd|j	dv rlt
dtdt |k std)Nr    r!   r"   )r!   r"   rY   
grant_typerh   access_tokenerrorauthorization_pending	slow_downg      ?access_deniedzAccess was denied by user.>       z&There must be an error in the request.z=An unexpected error occurred while waiting for authorization.z$Timed out waiting for authorization.)rS   %_LIMITED_INPUT_DEVICE_AUTH_GRANT_TYPEtimeri   rj   r+   sleepintPermissionErrorstatus_code
ValueErrorrl   TimeoutError)	r   rY   r\   r]   r    rm   expiration_timeresprn   r   r   r   ra   *  s4   

z0_LimitedInputDeviceAuthFlow._poll_for_auth_tokenc              
   C   sZ   t j tt |d  }tjjj|d |d |d | jd | jd | jd | j	|dS )	Nr[   rp   r   id_tokenr    r!   r"   )r   r   r    r!   r"   r#   expiry)
datetimeutcfromtimestamprz   rx   r   r   r   r   rS   rT   )r   re   expiration_datetimer   r   r   rb   R  s   z._LimitedInputDeviceAuthFlow._build_credentialsN)r6   r7   r8   r9   r   r   r   r   r   rM   r^   strrz   ra   rb   r   r   r   r   rL      s    
(rL   c                       s(   e Zd ZdZ fddZdd Z  ZS )IdTokenAuthMetadataPluginas  A `gRPC AuthMetadataPlugin` that uses ID tokens.

    This works like the existing `google.auth.transport.grpc.AuthMetadataPlugin`
    except that instead of always using access tokens, it preferentially uses the
    `Credentials.id_token` property if available (and logs an error otherwise).

    See http://www.grpc.io/grpc/python/grpc.html#grpc.AuthMetadataPlugin
    c                    s:   t    t|tjjjstdt| || _	|| _
dS )a3  Constructs an IdTokenAuthMetadataPlugin.

        Args:
          credentials (google.auth.credentials.Credentials): The credentials to
            add to requests.
          request (google.auth.transport.Request): A HTTP transport request object
            used to refresh credentials as needed.
        z-Cannot get ID tokens from credentials type %sN)superr   r&   r   r   r   r   r'   r$   _credentials_request)r   r   request	__class__r   r   r   o  s   
	
z"IdTokenAuthMetadataPlugin.__init__c                 C   s`   i }| j | j|j|j| t| j dd}|r | j j||d ntd |t	|
 d dS )a  Passes authorization metadata into the given callback.

        Args:
          context (grpc.AuthMetadataContext): The RPC context.
          callback (grpc.AuthMetadataPluginCallback): The callback that will
            be invoked to pass in the authorization metadata.
        r   N)tokenz#Failed to find ID token credentials)r   before_requestr   method_nameservice_urlgetattrapplyr
   rq   listitems)r   contextcallbackheadersr   r   r   r   __call__  s   
z"IdTokenAuthMetadataPlugin.__call__)r6   r7   r8   r9   r   r   __classcell__r   r   r   r   r   e  s    	r   c                 C   s   t jjj }tt| |S )zConstructs `grpc.CallCredentials` using
    `google.auth.Credentials.id_token`.

    Args:
      credentials (google.auth.credentials.Credentials): The credentials to use.

    Returns:
      grpc.CallCredentials: The call credentials.
    )r   auth	transportri   Requestgrpcmetadata_call_credentialsr   )r   r   r   r   r   id_token_call_credentials  s   
r   )F)&r9   r   r2   r+   r   ri   rH   rx   rF   google_auth_oauthlib.flowrP   rB   r   google.authr   google.auth.transport.requestsgoogle.oauth2.credentialstensorboard.uploaderr   tensorboard.utilr   
get_loggerr
   r>   rA   rk   rw   rK   r   r   r   r   r   rQ   rL   AuthMetadataPluginr   r   r   r   r   r   <module>   s@   N
-o1