o
    Df&                     @   s~   d dl mZ d dlmZ ddlmZ ddlmZ ddlmZ ddlm	Z	 ddlm
Z
 dd	lmZ dd
lmZ G dd dZdS )    )default_json_headers)	JoseError   )ClientMetadataClaims)scope_to_list)AccessDeniedError)InvalidClientError)InvalidRequestError)UnauthorizedClientError)InvalidClientMetadataErrorc                   @   s   e Zd ZdZeZdd Zdd Zdd Zdd	 Z	d
d Z
dd Zdd Zdd Zdd Zdd Zdd Zdd Zdd Zdd Zdd Zd d! Zd"d# Zd$d% Zd&S )'ClientConfigurationEndpointclient_configurationc                 C   s
   || _ d S N)server)selfr    r   X/home/ubuntu/webapp/venv/lib/python3.10/site-packages/authlib/oauth2/rfc7592/endpoint.py__init__      
z$ClientConfigurationEndpoint.__init__c                 C   s
   |  |S r   )create_configuration_responser   requestr   r   r   __call__   r   z$ClientConfigurationEndpoint.__call__c                 C   s   |  |}|s
t ||_| |}|s| || tdd| ||s*tdd||_|j	dkr8| 
||S |j	dkrC| ||S |j	dkrN| ||S d S )Ni  )status_codei  GETDELETEPUT)authenticate_tokenr   
credentialauthenticate_clientrevoke_access_tokenr   check_permissionr
   clientmethodcreate_read_client_responsecreate_delete_client_responsecreate_update_client_response)r   r   tokenr"   r   r   r   r      s$   






z9ClientConfigurationEndpoint.create_configuration_responsec                 C   s   | j |S r   )r   create_json_requestr   r   r   r   create_endpoint_request7   s   z3ClientConfigurationEndpoint.create_endpoint_requestc                 C   s&   |  |}|| || d|tfS )N   )introspect_clientupdate!generate_client_registration_infor   )r   r"   r   bodyr   r   r   r$   :   s   

z7ClientConfigurationEndpoint.create_read_client_responsec                 C   s   |  || ddg}dd|fS )N)zCache-Controlzno-store)Pragmazno-cache    )delete_client)r   r"   r   headersr   r   r   r%   ?   s
   
z9ClientConfigurationEndpoint.create_delete_client_responsec                 C   s   d}|D ]
}||j v rt q|j d}|st || kr#t d|j v r3||j d s3t | |}| |||}| ||S )N)registration_access_tokenregistration_client_uriclient_secret_expires_atclient_id_issued_at	client_idclient_secret)datar	   getget_client_idcheck_client_secretextract_client_metadataupdate_clientr$   )r   r"   r   must_not_includekr8   client_metadatar   r   r   r&   G   s    


z9ClientConfigurationEndpoint.create_update_client_responsec              
   C   s\   |j  }|  }| |i ||  }z	|  W |	 S  ty- } zt|jd }~ww r   )
r:   copyget_claims_optionsclaims_classget_server_metadatavalidater   r   descriptionget_registered_claims)r   r   	json_dataoptionsclaimserrorr   r   r   r>   g   s   


z3ClientConfigurationEndpoint.extract_client_metadatac                    s   |   }|si S |d|d|d |d}i }d ur2tfdd}d|i|d< d urFtfd	d
}d|i|d<  d urZt   fdd}d|i|d< |d urdd|i|d< |S )Nscopes_supportedresponse_types_supportedgrant_types_supported%token_endpoint_auth_methods_supportedc                    s   |sdS t t|} |S )NT)setr   
issuperset)rL   valuescopes)rN   r   r   _validate_scope   s   
zGClientConfigurationEndpoint.get_claims_options.<locals>._validate_scoperG   scopec                         t|S r   rS   rR   rL   rT   )rO   r   r   _validate_response_types      zPClientConfigurationEndpoint.get_claims_options.<locals>._validate_response_typesresponse_typesc                    rX   r   rY   rZ   )rP   r   r   _validate_grant_types   r\   zMClientConfigurationEndpoint.get_claims_options.<locals>._validate_grant_typesgrant_typesvaluestoken_endpoint_auth_method)rF   r;   rR   )r   metadataauth_methods_supportedrK   rV   r[   r^   r   )rP   rO   rN   r   rD   r   s.   



z.ClientConfigurationEndpoint.get_claims_optionsc                 C   s   i |j |jS r   )client_inforB   )r   r"   r   r   r   r+      s   z-ClientConfigurationEndpoint.introspect_clientc                 C      t  )a  Generate ```registration_client_uri`` and ``registration_access_token``
        for RFC7592. By default this method returns the values sent in the current
        request. Developers MUST rewrite this method to return different registration
        information.::

            def generate_client_registration_info(self, client, request):{
                access_token = request.headers['Authorization'].split(' ')[1]
                return {
                    'registration_client_uri': request.uri,
                    'registration_access_token': access_token,
                }

        :param client: the instance of OAuth client
        :param request: formatted request instance
        NotImplementedErrorr   r"   r   r   r   r   r-      s   z=ClientConfigurationEndpoint.generate_client_registration_infoc                 C   re   )aL  Authenticate current credential who is requesting to register a client.
        Developers MUST implement this method in subclass::

            def authenticate_token(self, request):
                auth = request.headers.get('Authorization')
                return get_token_by_auth(auth)

        :return: token instance
        rf   r   r   r   r   r         
z.ClientConfigurationEndpoint.authenticate_tokenc                 C   re   )a4  Read a client from the request payload.
        Developers MUST implement this method in subclass::

            def authenticate_client(self, request):
                client_id = request.data.get('client_id')
                return Client.get(client_id=client_id)

        :return: client instance
        rf   r   r   r   r   r      ri   z/ClientConfigurationEndpoint.authenticate_clientc                 C   re   )a  Revoke a token access in case an invalid client has been requested.
        Developers MUST implement this method in subclass::

            def revoke_access_token(self, token, request):
                token.revoked = True
                token.save()

        rf   )r   r'   r   r   r   r   r          	z/ClientConfigurationEndpoint.revoke_access_tokenc                 C   re   )a  Checks wether the current client is allowed to be accessed, edited
        or deleted. Developers MUST implement it in subclass, e.g.::

            def check_permission(self, client, request):
                return client.editable

        :return: boolean
        rf   rh   r   r   r   r!      rj   z,ClientConfigurationEndpoint.check_permissionc                 C   re   )a2  Delete authorization code from database or cache. Developers MUST
        implement it in subclass, e.g.::

            def delete_client(self, client, request):
                client.delete()

        :param client: the instance of OAuth client
        :param request: formatted request instance
        rf   rh   r   r   r   r2      ri   z)ClientConfigurationEndpoint.delete_clientc                 C   re   )a  Update the client in the database. Developers MUST implement this method
        in subclass::

            def update_client(self, client, client_metadata, request):
                client.set_client_metadata({**client.client_metadata, **client_metadata})
                client.save()
                return client

        :param client: the instance of OAuth client
        :param client_metadata: a dict of the client claims to update
        :param request: formatted request instance
        :return: client instance
        rf   )r   r"   rB   r   r   r   r   r?      s   z)ClientConfigurationEndpoint.update_clientc                 C   re   )zeReturn server metadata which includes supported grant types,
        response types and etc.
        rf   )r   r   r   r   rF      s   z/ClientConfigurationEndpoint.get_server_metadataN)__name__
__module____qualname__ENDPOINT_NAMEr   rE   r   r   r   r)   r$   r%   r&   r>   rD   r+   r-   r   r   r    r!   r2   r?   rF   r   r   r   r   r      s*     *r   N)authlib.constsr   authlib.joser   rfc7591.claimsr   rfc6749r   r   r   r	   r
   rfc7591r   r   r   r   r   r   <module>   s    