
    Ki                     r    d 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e
      Zy)zauthlib.oauth2.rfc9068.token_validator.
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

Implementation of Validating JWT Access Tokens per `Section 4`_.

.. _`Section 7`: https://www.rfc-editor.org/rfc/rfc9068.html#name-validating-jwt-access-token
    )jwt)DecodeError)	JoseError)InsufficientScopeError)InvalidTokenError)BearerTokenValidator   )JWTAccessTokenClaimsc                   H     e Zd ZdZ fdZd ZdddefdZd Z	 d
d	Z	 xZ
S )JWTBearerTokenValidatora  JWTBearerTokenValidator can protect your resource server endpoints.

    :param issuer: The issuer from which tokens will be accepted.
    :param resource_server: An identifier for the current resource server,
        which must appear in the JWT ``aud`` claim.

    Developers needs to implement the missing methods::

        class MyJWTBearerTokenValidator(JWTBearerTokenValidator):
            def get_jwks(self): ...


        require_oauth = ResourceProtector()
        require_oauth.register_token_validator(
            MyJWTBearerTokenValidator(
                issuer="https://authorization-server.example.org",
                resource_server="https://resource-server.example.org",
            )
        )

    You can then protect resources depending on the JWT `scope`, `groups`,
    `roles` or `entitlements` claims::

        @require_oauth(
            scope="profile",
            groups="admins",
            roles="student",
            entitlements="captain",
        )
        def resource_endpoint(): ...
    c                 @    || _         || _        t        |   |i | y N)issuerresource_serversuper__init__)selfr   r   argskwargs	__class__s        r/home/jay/workspace/scripts/.codegraph-venv/lib/python3.12/site-packages/authlib/oauth2/rfc9068/token_validator.pyr   z JWTBearerTokenValidator.__init__4   s$    .$)&)    c                     t               )az  Return the JWKs that will be used to check the JWT access token signature.
        Developers MUST re-implement this method. Typically the JWKs are statically
        stored in the resource server configuration, or dynamically downloaded and
        cached using :ref:`specs/rfc8414`::

            def get_jwks(self):
                if "jwks" in cache:
                    return cache.get("jwks")

                server_metadata = get_server_metadata(self.issuer)
                jwks_uri = server_metadata.get("jwks_uri")
                cache["jwks"] = requests.get(jwks_uri).json()
                return cache["jwks"]
        )NotImplementedError)r   s    r   get_jwksz JWTBearerTokenValidator.get_jwks9   s     "##r   issstrreturnc                      || j                   k(  S r   )r   )r   claimsr   s      r   validate_issz$JWTBearerTokenValidator.validate_issJ   s     dkk!!r   c                 J   d| j                   dddid| j                  dddiddiddiddiddiddiddiddiddiddiddid}| j                         }	 t        j                  ||t
        |      S # t        $ r'}t        | j                  | j                        |d	}~ww xY w)
 T)	essentialvalidater$   )r$   valueF)r   expaudsub	client_idiatjti	auth_timeacramrscopegroupsrolesentitlements)key
claims_clsclaims_optionsrealmextra_attributesN)
r!   r   r   r   decoder
   r   r   r8   r9   )r   token_stringr6   jwksexcs        r   authenticate_tokenz*JWTBearerTokenValidator.authenticate_tokenP   s    
 "&43D3DE&!%0D0DE&%t,&&%u-''!5)"E*!5)(%0
  }}
	::/-	   	#jj43H3H	s   A2 2	B";"BB"c                    	 |j                          | j                  |j                  dg       |      r
t               | j                  |j                  d      |      r
t               | j                  |j                  d      |      r
t               | j                  |j                  d      |      r
t               y# t        $ r'}t        | j                  | j                        |d}~ww xY w)r#   r7   Nr0   r1   r2   r3   )r%   r   r   r8   r9   scope_insufficientgetr   )r   tokenscopesrequestr1   r2   r3   r=   s           r   validate_tokenz&JWTBearerTokenValidator.validate_token|   s    
	NN ""599Wb#96B(** ""599X#6?#%%""599W#5u=#%%""599^#<lK#%% L?  	#jj43H3H	s   C   	C0	"C++C0)NNN)__name__
__module____qualname____doc__r   r   boolr!   r>   rE   __classcell__)r   s   @r   r   r      s8    @*
$"" "$ "*Z MQ'&r   r   N)rI   authlib.joser   authlib.jose.errorsr   r   authlib.oauth2.rfc6750.errorsr   r    authlib.oauth2.rfc6750.validatorr   r    r
   r    r   r   <module>rQ      s0     + ) @ ; A (P&2 P&r   