Présentation des règles JWS et JWT

Vous consultez la documentation d'Apigee Edge.
Consultez la documentation Apigee X.
en savoir plus

Cet article fournit des informations générales sur les jetons JWT (jeton Web JSON) et JWS (JSON Web Signature), ainsi que sur les règles Apigee JWS/JWT susceptibles d'intéresser les développeurs de proxy Apigee.

Introduction

Les jetons JWS et JWT sont couramment utilisés pour partager des revendications ou des assertions entre des applications connectées. Les stratégies JWS/JWT permettent aux proxys de l'API Edge:

  • Générer un jeton JWT ou JWS signé.
  • Valider un jeton JWT ou JWS signé et faire des revendications dans le JWS/JWT.
  • Décoder un jeton JWT ou JWS signé sans valider la signature.

Dans ces deux cas, la règle définit également des variables qui autorisent des règles supplémentaires, ou les services de backend eux-mêmes, à inspecter les revendications validées et à prendre des décisions en fonction de ces revendications.

Lorsque vous utilisez la règle de vérification JWS/JWT, un jeton JWS/JWT non valide est rejeté et génère une condition d'erreur. De même, lorsque vous utilisez la règle de décodage JWS/JWT, un jeton JWS/JWT mal mis en forme entraîne une condition d'erreur.

Vidéos

Regardez une courte vidéo pour découvrir rapidement le jeton JWT. Bien que cette vidéo soit spécifique à la génération d'un jeton JWT, de nombreux concepts sont les mêmes pour JWS.

Regardez une courte vidéo pour en savoir plus sur la structure JWT.

Cas d'utilisation

Vous pouvez utiliser les règles JWS/JWT pour :

  • Générez un nouveau JWS/JWT sur le côté proxy ou sur le point de terminaison cible d'un proxy Edge. Par exemple, vous pouvez créer un flux de requêtes proxy qui génère un JWS/JWT et le renvoie à un client. Vous pouvez également concevoir un proxy pour qu'il génère un jeton JWS/JWT sur le flux de requêtes cible et l'associe à la requête envoyée à la cible. Ces revendications sont ensuite disponibles pour permettre aux services de backend d'appliquer d'autres traitements de sécurité.
  • Vérifier et extraire les revendications d'un JWS/JWT obtenu à partir des requêtes client entrantes, depuis les réponses de service cible, les réponses de stratégie d'appel de service ou d'autres sources. Edge vérifiera la signature sur un JWS/JWT, que le JWS/JWT a été généré par un tiers ou par Edge lui-même, à l'aide des algorithmes RSA ou HMAC.
  • Décoder un jeton JWS/JWT. Le décodage est très utile lorsqu'il est utilisé avec la règle de vérification JWS/JWT, lorsque la valeur d'une revendication (JWT) ou d'en-tête (JWS/JWT) depuis JWS/JWT doit être connue avant de vérifier la valeur JWS/JWT.

Composantes d'un JWS/JWT

Un jeton JWS/JWT signé encode les informations en trois parties séparées par des points : l'en-tête, la charge utile et la signature :

header.payload.signature
  • La règle de génération JWS/JWT crée les trois parties.
  • La règle de vérification JWS/JWT examine les trois parties.
  • La règle de décodage JWS/JWT n'examine que l'en-tête et la charge utile.

Un JWS accepte également un format detached qui omet la charge utile du JWS :

header..signature

Dans le cas d'un JWS dissocié, la charge utile est envoyée séparément du JWS. Vous utilisez l'élément <DetachedContent> de la règle de vérification JWS pour spécifier la charge utile JWS brute non codée. La règle de vérification JWS vérifie ensuite le JWS en utilisant l'en-tête et la signature du jeton JWS et la charge utile spécifiée par l'élément <DetachedContent>.

Pour en savoir plus sur les jetons et sur la façon dont ils sont encodés et signés, consultez les sections:

Différences entre JWS et JWT

Vous pouvez utiliser un jeton JWT ou JWS pour partager des revendications ou des assertions entre des applications connectées. La principale différence entre les deux est la représentation de la charge utile :

  • JWT
    • La charge utile est toujours un objet JSON.
    • La charge utile est toujours associée au jeton JWT.
    • L'en-tête typ du jeton est toujours défini sur JWT.
  • JWS
    • La charge utile peut être représentée par n'importe quel format, tel qu'un objet JSON, un flux d'octets, etc.
    • La charge utile n'a pas besoin d'être associée au JWS.

Étant donné que le format JWT utilise toujours un objet JSON pour représenter la charge utile, les stratégies JWT de génération par périphérie et de vérification JWT permettent de gérer les noms de revendications enregistrés courants, tels que aud, iss, sub, etc. Cela signifie que vous pouvez utiliser des éléments de la règle de génération JWT pour définir ces revendications dans la charge utile, et des éléments de la règle de vérification JWT pour vérifier leurs valeurs. Consultez la section Noms de revendications enregistrés de la spécification JWT pour en savoir plus.

Outre la prise en charge de certains noms de revendications enregistrés, la règle de génération JWT permet d'ajouter directement des revendications avec des noms arbitraires au jeton JWT. Chaque revendication est une simple paire nom/valeur, dont la valeur peut être un nombre, booléen, une chaîne, une carte ou un tableau.

Étant donné qu'un JWS peut utiliser n'importe quelle représentation de données pour la charge utile, vous ne pouvez pas ajouter de revendications à la charge utile. La règle de génération JWS permet d'ajouter des revendications avec des noms arbitraires dans l'en-tête de JWS. En outre, les règles JWS acceptent une charge utile dissociée, où le JWS omet la charge utile. Une charge utile dissociée vous permet d'envoyer séparément le JWS et la charge utile. Elle est requise par plusieurs normes de sécurité.

À propos des algorithmes de signature

Les règles de validation JWS/JWT et de génération JWT/JWT sont compatibles avec les algorithmes RSA, RSASSA-PSS, ECDSA et HMAC, à l'aide de sommes de contrôle SHA2 avec une puissance de bits de 256, 384 ou 512. La règle de décodage JWS/JWT fonctionne quel que soit l'algorithme utilisé pour signer le jeton JWS/JWT.

Algorithme HMAC

L'algorithme HMAC s'appuie sur une clé secrète partagée, appelée "clé secrète", pour créer la signature (également appelée signature JWS/JWT) et pour valider la signature.

La longueur minimale de la clé secrète dépend de la puissance en bits de l'algorithme :

  • HS256 : longueur de clé minimale de 32 octets
  • HS386 : longueur de clé minimale de 48 octets
  • HS512 : longueur de clé minimale de 64 octets

algorithme RSA

L'algorithme RSA utilise une paire de clés publique/privée pour la signature cryptographique. Avec les signatures RSA, la partie signataire utilise une clé privée RSA pour signer le JWS/JWT et la partie de vérification utilise la clé publique RSA correspondante pour valider la signature sur le JWS/JWT. Aucune taille n'est requise pour la clé.

Algorithme RSASSA-PSS

L'algorithme RSASSA-PSS est une mise à jour de l'algorithme RSA. À l'instar de RSS, RSASSA-PSS utilise une paire de clés publique/privée RSA pour la signature cryptographique. Le format de la clé est le même que pour le format RSS. La partie signataire utilise une clé privée pour signer le jeton JWS/JWT, et la partie de validation utilise la clé publique correspondante pour vérifier la signature sur JWS/JWT. Aucune taille n'est requise pour la clé.

Algorithme ECDSA

L'algorithme de signature numérique à courbe elliptique (ECDSA) est un algorithme de cryptographie à courbe elliptique avec une courbe P-256, P-384 et P-521. Lorsque vous utilisez des algorithmes ECDSA, l'algorithme détermine le type de clé publique et privée que vous devez spécifier :

Algorithme Courbe Configuration de la clé
ES256 P-256 Une clé générée à partir de la courbe P-256 (également appelée secp256r1 ou prime256v1)
ES384 P-384 Clé générée à partir de la courbe P-384 (également appelée "secp384r1")
ES512 P-521 Clé générée à partir de la courbe P-521 (également appelée "secp521r1")

Algorithmes de chiffrement de clé

Les règles JWS/JWT sont compatibles avec tous les algorithmes de chiffrement de clé acceptés par OpenSSL.

Utiliser un jeu de clés Web JSON (JWKS) pour vérifier un JWS/JWT

Lorsque vous validez un jeton JWS/JWT signé, vous devez fournir la clé publique associée à la clé privée utilisée pour signer le jeton. Vous disposez de deux options pour fournir la clé publique aux règles de validation JWS/JWT :

  • utiliser la valeur de clé publique réelle (généralement fournie dans une variable de flux) ;
  • utiliser une clé publique encapsulée dans un JWKS.

À propos des JWKS

Une JWKS est une structure JSON qui représente un ensemble de clés JSON Web (JWK). Une JWK est une structure de données JSON qui représente une clé cryptographique. Les JWK et JWKS sont décrites dans la RFC7517. Consultez les exemples de JKWS en annexe A. Exemples de jeux de clés JSON Web

Structure des JWKS

La RFC7517 décrit les éléments de clé JWKS pour chaque type de clé, tels que "RSA" ou "EC". Par exemple, en fonction du type de clé, ces paramètres peuvent inclure :

  • kty : le type de clé, tel que "RSA" ou "EC".
  • kid (l'ID de clé) : peut être n'importe quelle valeur arbitraire (aucun doublon dans un jeu de clés). Si le jeton JWT entrant a un ID de clé présent dans l'ensemble de JWKS, la règle utilise la clé publique appropriée pour valider la signature JWS/JWT.

Voici des exemples d'éléments facultatifs et leurs valeurs :

  • alg : l'algorithme de la clé. Il doit correspondre à l'algorithme de signature dans JWS/JWT.
  • use : si présent, doit être "sig".

Les JWKS suivantes contiennent les éléments et les valeurs requis et seraient valides sur Edge (depuis https://www.googleapis.com/oauth2/v3/certs) :

{  
   "keys":[  
      {  
         "kty":"RSA",
         "alg":"RS256",
         "use":"sig",
         "kid":"ca04df587b5a7cead80abee9ea8dcf7586a78e01",
         "n":"iXn-WmrwLLBa-QDiToBozpu4Y4ThKdwORWFXQa9I75pKOvPUjUjE2Bk05TUSt7-V7KDjCq0_Nkd-X9rMRV5LKgCa0_F8YgI30QS3bUm9orFryrdOc65PUIVFVxIwMZuGDY1hj6HEJVWIr0CZdcgNIll06BasclckkUK4O-Eh7MaQrqb646ghFlG3zlgk9b2duHbDOq3s39ICPinRQWC6NqTYfqg7E8GN_NLY9srUCc_MswuUfMJ2cKT6edrhLuIwIj_74YGkpOwilr2VswKsvJ7dcoiJxheKYvKDKtZFkbKrWETTJSGX2Xeh0DFB0lqbKLVvqkM2lFU2Qx1OgtTnrw",
         "e":"AQAB"
      },
      {
          "kty":"EC",
          "alg":"ES256",
          "use":"enc",
          "kid":"k05TUSt7-V7KDjCq0_N"
          "crv":"P-256",
          "x":"Xej56MungXuFZwmk_xccvsMpCtXmqhvEEMCmHyAmKF0",
          "y":"Bozpu4Y4ThKdwORWFXQa9I75pKOvPUjUjE2Bk05TUSt",
      }
   ]
}

Concevoir votre proxy pour utiliser les JWKS

Lorsqu'un JWS/JWT est obtenu auprès d'un émetteur, il insère souvent un ID de clé (ou enfant) dans l'en-tête JWS/JWT. La clé indique au destinataire du jeton JWS/JWT comment rechercher la clé publique ou secrète nécessaire à la validation de la signature sur le jeton JWS/JWT signé.

Supposons, par exemple, qu'un émetteur signe un jeton JWT avec une clé privée. "ID de clé" identifie la clé publique correspondante à utiliser pour vérifier le jeton JWT. La liste des clés publiques est généralement disponible à un point de terminaison bien connu, par exemple : https://www.googleapis.com/oauth2/v3/certs.

Voici la séquence de base que Edge (ou toute plate-forme fonctionnant avec JWKS) doit effectuer pour fonctionner avec un JWS/JWT doté d'un JWKS:

  1. Examinez l'en-tête JWS/JWT pour trouver l'ID de clé (kid).
  2. Examinez l'en-tête JWS/JWT pour trouver l'algorithme de signature (alg), tel que RS256.
  3. Récupérez la liste des clés et des ID à partir des JWKS du point de terminaison connu pour un émetteur donné.
  4. Extrayez la clé publique de la liste des clés ayant l'ID de clé indiqué dans l'en-tête JWS/JWT et l'algorithme correspondant, si la clé JWKS spécifie l'algorithme.
  5. Utilisez cette clé publique pour valider la signature sur le JWS/JWT.

En tant que développeur de proxys d'API Edge, vous devez effectuer les opérations suivantes pour effectuer la vérification JWS/JWT:

  1. Récupérez la liste de clés et d'ID à partir du point de terminaison bien connu d'un émetteur donné. Vous pouvez utiliser une stratégie d'appel de service pour cette étape.
  2. Dans la règle de vérification JWS/JWT, spécifiez l'emplacement de JWS/JWT dans l'élément <Source> et la charge utile JWKS dans l'élément <PublicKey/JWKS>. Par exemple, pour la stratégie VerifyJWT :
    <VerifyJWT name="JWT-Verify-RS256">
        <Algorithm>RS256</Algorithm>
        <Source>json.jwt</Source>
        <IgnoreUnresolvedVariables>false</IgnoreUnresolvedVariables>
        <PublicKey>
            <JWKS ref="public.jwks"/>
        </PublicKey>
        <Subject>apigee-seattle-hatrack-montage</Subject>
        <Issuer>urn://apigee-edge-JWT-policy-test</Issuer>
        <Audience>urn://c60511c0-12a2-473c-80fd-42528eb65a6a</Audience>
        <AdditionalClaims>
            <Claim name="show">And now for something completely different.</Claim>    
        </AdditionalClaims>
    </VerifyJWT>
    

La règle de vérification JWT effectue tout le reste :

  • Si une clé dont l'ID de clé correspond à l'ID de clé (kid) revendiqué dans le JWT est introuvable dans JWKS, la règle de vérification JWT génère une erreur et ne valide pas le jeton JWT.
  • Si le jeton JWT entrant ne comporte pas d'ID de clé (kid) dans l'en-tête, il est impossible de mapper l'ID de clé à la clé de vérification.

En tant que concepteur du proxy, vous devez déterminer la clé à utiliser. Dans certains cas, il peut s'agir d'une clé fixe codée en dur.