Visão geral das políticas JWS e JWT

Esta página se aplica à Apigee e à Apigee híbrida.

Confira a documentação da Apigee Edge.

Neste tópico, fornecemos informações gerais sobre JWT (JSON Web Token) e JWS (JSON Web Signature) e as políticas JWS/JWT da Apigee que podem ser de interesse para desenvolvedores de proxy da Apigee.

Introdução

JWS e JWT são comumente usados para compartilhar declarações ou asserções entre aplicativos conectados. As políticas de JWS/JWT permitem que os proxies da API Apigee:

Nos últimos dois casos, a política também define variáveis de fluxo. Isso permite que as políticas subsequentes no fluxo da Apigee inspecionem as declarações no JWT ou na JWS e tomem decisões com base nelas ou propaguem essas informações para os serviços de back-end.

Ao usar a política VerifyJWS ou VerifyJWT, um JWS/JWT inválido será rejeitado e resultará em uma condição de erro. Da mesma forma, ao usar a política DecodeJWS ou DecodeJWT, um JWS/JWT malformado resultará em uma condição de erro.

Vídeos

Assista a um vídeo curto para uma introdução rápida ao JWT. Este vídeo é específico para gerar um JWT, mas muitos dos conceitos são os mesmos para JWS.

Um vídeo curto para saber mais sobre a estrutura do JWT.

Casos de uso

As políticas JWS/JWT podem ser usadas para:

  • Gerar um novo JWS/JWT no lado do proxy ou do endpoint de destino de um proxy da Apigee. Por exemplo, é possível criar um fluxo de solicitação de proxy que gere um JWS/JWT e o retorne a um cliente. Ou é possível projetar um proxy para que ele gere um JWS/JWT no fluxo de solicitação de destino e o anexe à solicitação enviada ao destino. O JWS/JWT e as respectivas declarações ficariam disponíveis para permitir que os serviços de back-end aplicassem mais processamento de segurança.
  • Verifique e extraia declarações de um JWS/JWT obtido de solicitações de cliente de entrada, de respostas de serviço de destino, de respostas de política de chamada de serviço ou de outras fontes. Para um JWS/JWT assinado, a Apigee usará um dos algoritmos RSA, ECDSA ou HMAC para verificar a assinatura, seja o JWS/JWT gerado pela Apigee ou por terceiros. Para um JWT criptografado, a Apigee descriptografará o JWT usando um dos algoritmos de criptografia JWA compatíveis. Consulte IETF RFC 7518.
  • Decodificar um JWS/JWT. A decodificação é mais útil quando usada em conjunto com a política de verificação de JWS/JWT, nos casos em que o valor de uma declaração (JWT) ou cabeçalho (JWS/JWT) no JWS/JWT precisa ser conhecido antes de verificar um JWS/JWT assinado ou descriptografar um JWT criptografado.

Partes de um JWS/JWT

Um JWS/JWT assinado codifica as informações em três partes separadas por pontos:

Header.Payload.Signature
  • A política Generate JWS/JWT cria as três partes.
  • A política Verify JWS/JWT examina as três partes.
  • A política DecodeJWS examina apenas o cabeçalho. A política DecodeJWT examina apenas o cabeçalho e o payload.

Uma JWS também aceita um formato removido que omite o payload da JWS:

Header..Signature

Com um JWS desanexado, o payload é enviado separadamente do JWS. Use o elemento <DetachedContent> da política Verify JWS para especificar o payload bruto não codificado do JWS. Em seguida, a política Verify JWS verifica o JWS usando o cabeçalho e a assinatura no JWS e o payload especificado pelo elemento <DetachedContent>.

Um JWT criptografado codifica as informações em cinco partes separadas por pontos:

Header.Key.InitializationVector.Payload.AuthenticationTag

As políticas GenerateJWT e VerifyJWT criarão ou examinarão todas essas partes. O DecodeJWT pode examinar apenas o cabeçalho não criptografado.

Para saber mais sobre tokens e como eles são codificados, assinados ou criptografados, consulte os documentos de padrões relevantes:

Diferenças entre JWS e JWT

Use um JWT ou JWS para compartilhar declarações ou afirmações entre aplicativos conectados. A principal diferença entre os dois é a representação do payload:

  • JWT
    • O payload é sempre um objeto JSON.
    • O payload é sempre anexado ao JWT.
    • O cabeçalho typ do token sempre é definido como JWT.
    • O payload pode ser assinado ou criptografado.
  • JWS
    • O payload pode ser representado por qualquer formato, como um objeto JSON, fluxo de bytes, fluxo de octetos e outros.
    • O payload não precisa ser anexado à JWS.
    • O cabeçalho e o payload sempre são assinados. A JWS não é compatível com criptografia.

Como o formato JWT sempre usa um objeto JSON para representar o payload, as políticas GenerateJWT e VerifyJWT da Apigee foram criadas para processar nomes comuns de declarações registrados, como aud, iss, sub e outros. Isso significa que é possível usar elementos da política GenerateJWT para definir essas declarações no payload e elementos da política VerifyJWT para verificar os respectivos valores. Consulte a seção Nomes de declarações registrados da especificação do JWT para saber mais.

Além de permitir determinados nomes de declarações registrados, a política GenerateJWT permite diretamente adicionar declarações com nomes arbitrários ao payload ou ao cabeçalho do JWT. Cada declaração é um par simples de nome/valor, em que o valor pode ser do tipo number, boolean, string, map ou array.

Ao usar GenerateJWS, você fornece uma variável de contexto que representa o payload. Como uma JWS pode usar qualquer representação de dados para o payload, não há o conceito de "declaração de payload" em uma JWS, e a política GenerateJWS não permite adicionar declarações com nomes arbitrários ao payload. É possível usar a política GenerateJWS para adicionar declarações com nomes arbitrários ao cabeçalho da JWS. Além disso, as políticas de JWS são compatíveis com um payload removido, em que a JWS omite o payload. Um payload removido permite que enviar a JWS e o payload separadamente. Usar um payload removido pode ser mais eficiente em termos de espaço, especialmente para payloads grandes, e é exigido por vários padrões de segurança.

Assinatura versus criptografia

A Apigee pode gerar JWT assinado ou criptografado. Escolha o JWT assinado quando o payload não precisar ser secreto, mas for importante fornecer garantias de integridade e não repúdio aos leitores. Um JWT assinado garante aos leitores que o payload não foi alterado desde que o JWT foi assinado e que o JWT foi assinado pelo titular da chave privada. Escolha um JWT criptografado quando o payload precisar ser secreto. Um JWT criptografado fornece confidencialidade para o payload, já que somente o proprietário da chave apropriado pode descriptografá-lo.

É possível usar JWTs criptografados e assinados juntos, especialmente quando o JWT usa um algoritmo de criptografia assimétrica (RSA, ECDSA). Nesse caso, não é possível determinar a identidade do produtor desse JWT porque a chave de criptografia é pública. Para resolver esse problema, combine a assinatura com a criptografia. Um padrão típico é assim:

  • Assine um payload para produzir uma JWS ou JWT assinado.
  • Criptografe o resultado assinado para produzir um JWT criptografado.

A incorporação de um payload assinado em um JWT criptografado usando essa abordagem oferece garantias de não repúdio e confidencialidade. As políticas da Apigee podem produzir, decodificar e verificar essas combinações.

Algoritmos de assinatura

Para JWT assinado, as políticas de verificação e geração de JWS/JWT são compatíveis com algoritmos RSA, RSASSA-PSS, ECDSA e HMAC, usando checksums SHA2 de força de bits de 256, 384 ou 512. As políticas DecodeJWS e DecodeJWT funcionam independentemente do algoritmo usado para assinar o JWS/JWT.

Algoritmos HMAC

Os algoritmos HMAC dependem de uma senha compartilhada, conhecida como chave secreta, para criar a assinatura (também chamado de "assinar o JWS/JWT") e para verificar a assinatura.

O comprimento mínimo da chave secreta depende da força do bit do algoritmo:

  • HS256: comprimento mínimo de chave de 32 bytes
  • HS384: 48 bytes de comprimento mínimo da chave
  • HS512: tamanho mínimo da chave de 64 bytes

Algoritmos RSA

Os algoritmos RSA usam um par de chaves pública/privada para a assinatura criptográfica. A especificação do JWA usa os apelidos RS256, RS384 e RS512 para representar essas opções. Com assinaturas RSA, a parte assinante usa uma chave privada RSA para assinar o JWS/JWT. A parte verificadora usa a chave pública RSA correspondente para verificar a assinatura no JWS/JWT. Não há requisitos de tamanho para as chaves.

Algoritmos RSASSA-PSS

Os algoritmos RSASSA-PSS são uma atualização dos Algoritmos RSA e usam os apelidos PS256, PS384 e PS512. Assim como as variantes RS*, a RSASSA-PSS usa um par de chaves pública/privada RSA para a assinatura criptográfica. Os limites de formato, mecanismo e tamanho da chave são os mesmos dos algoritmos RS*.

Algoritmos ECDSA

O conjunto de algoritmos do algoritmo de assinatura digital de curva elíptica (ECDSA, na sigla em inglês) é composto por algoritmos de criptografia de curvas elípticas com uma curva P-256, P-384 ou P-521. Quando você usa algoritmos ECDSA, o algoritmo determina o tipo de chave pública e privada que você precisa especificar:

Algoritmo Curva Requisito de chave
ES256 P-256 Uma chave gerada da curva P-256 (também conhecida como secp256r1 ou prime256v1)
ES384 P-384 Uma chave gerada da curva P-384 (também conhecida como secp384r1)
ES512 P-521 Uma chave gerada da curva P-521 (também conhecida como secp521r1)

Algoritmos de criptografia

Ao usar GenerateJWT e VerifyJWT para lidar com JWT criptografado, as políticas aceitam estes algoritmos:

  • dir
  • RSA-OAEP-256
  • A128KW, A192KW, A256KW
  • A128GCMKW, A192GCMKW, A256GCMKW
  • PBES2-HS256+A128KW, PBES2-HS384+A192KW, PBES2-HS512+A256KW
  • ECDH-ES, ECDH-ES+A128KW, ECDH-ES+A192KW, ECDH-ES+A256KW

Chaves e representações de chaves

Os padrões JOSE, que abrangem JWS, JWT assinado e criptografado e mais, descrevem como usar chaves criptográficas para assinar ou criptografar informações. Os elementos fundamentais de qualquer operação criptográfica incluem o algoritmo e a chave. Diferentes algoritmos exigem diferentes tipos de chave e, em alguns casos, diferentes tamanhos das chaves.

Algoritmos simétricos, como a família HS* para assinatura ou o algoritmo A128KW para criptografia, exigem chaves simétricas ou compartilhadas: a mesma chave é usada para assinatura e verificação ou a mesma chave é usada para criptografia e descriptografia. Algoritmos assimétricos, como os algoritmos RS*, PS* e ES* para assinatura ou os algoritmos ECDH* para criptografia, usam pares de chaves. Há uma chave pública e uma chave privada, e elas são correspondentes. Na assinatura, o signatário usa a chave privada, e qualquer parte pode usar a chave pública para verificar a assinatura. Na criptografia, o criptografador usa a chave pública para fazer a criptografia, e o descriptografador usa a chave privada para fazer a descriptografia. As chaves públicas, como o nome sugere, são compartilháveis publicamente e não precisam ser mantidas em segredo.

Há maneiras diferentes de serializar as chaves criptográficas em formato de texto. As políticas da Apigee aceitam chaves serializadas em vários formatos: formato codificado em PEM, JWKS ou, para chaves compartilhadas, formato codificado em UTF-8 ou base64.

Formato PEM

Para chaves públicas ou privadas, é comum usar a codificação PEM, definida no IETF RFC 7468. Veja a seguir um exemplo de chave privada representada no formato PEM:

-----BEGIN PRIVATE KEY-----
MIGEAgEAMBAGByqGSM49AgEGBSuBBAAKBG0wawIBAQQgVcB/UNPxalR9zDYAjQIf
jojUDiQuGnSJrFEEzZPT/92hRANCAASc7UJtgnF/abqWM60T3XNJEzBv5ez9TdwK
H0M6xpM2q+53wmsN/eYLdgtjgBd3DBmHtPilCkiFICXyaA8z9LkJ
-----END PRIVATE KEY-----

Há formatos PEM semelhantes para chaves públicas ou chaves privadas criptografadas.

Formato JWKS

Uma chave JSON da Web (JWK, na sigla em inglês) é uma estrutura de dados JSON que representa uma única chave criptográfica. Um conjunto de chaves JSON da Web (JWKS, na sigla em inglês) é uma estrutura JSON que representa um conjunto de JWKs. JWK e JWKS são descritos no RFC7517 (em inglês). Consulte exemplos de JWKS no Apêndice A. Exemplo de conjuntos de chaves JSON da Web.

O objetivo do JWKS é permitir que qualquer parte represente um conjunto de chaves em um formato padrão. Um caso de uso importante é compartilhar chaves públicas de maneira padrão, por um endpoint HTTP que fornece dados no formato JWKS. Quando uma empresa ou um sistema que gera JWS ou JWT assinado, como um provedor de identidade, publica chaves públicas, qualquer sistema ou aplicativo que possa ler as chaves públicas pode verificar as assinaturas geradas pela parte assinante. Por outro lado, qualquer sistema ou aplicativo que queira criptografar dados que precisam ser lidos apenas por uma parte ou empresa específica pode recuperar as chaves públicas pertencentes a essa parte ou empresa e gerar um JWT criptografado para esse propósito.

O RFC7517 descreve os elementos de cada tipo de chave do JWKS, como RSA ou EC. Estes elementos precisam sempre estar presentes:

  • kty: o tipo de chave, como RSA ou EC.
  • kid: o ID da chave. Pode ser qualquer valor de string exclusivo arbitrário. Não pode haver cópias dentro de um único conjunto de chaves. Se o JWT de entrada tiver um ID de chave que está presente no conjunto de JWKS, a política VerifyJWS ou VerifyJWT usará a chave pública correta para verificar a assinatura de JWS/JWT.

Veja a seguir exemplos de elementos opcionais e os valores deles:

  • alg: o algoritmo de chave. Ele precisa corresponder ao algoritmo de assinatura no JWS/JWT.
  • use: especifica o uso pretendido da chave. Os valores típicos são "sig" para assinatura e verificação ou "enc" para criptografia e descriptografia.

O JWKS a seguir (originalmente recuperado de https://www.googleapis.com/oauth2/v3/certs, mas desatualizado agora) contém os elementos e valores necessários e pode ser usado pela Apigee:

{
     "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",
        }
     ]
  }
  

Como especificar chaves para as políticas de JWS e JWT

Se você for gerar ou verificar JWS ou JWT, é necessário fornecer uma chave para uso nas operações criptográficas.

Ao gerar um JWT assinado, você precisa fornecer uma chave capaz de produzir a assinatura.

  • No caso de um algoritmo de assinatura RS*, PS* ou ES*, que usam chaves assimétricas, você precisa fornecer a chave privada para gerar a assinatura.
  • No caso de um algoritmo HS*, é necessário fornecer a chave simétrica que será usada ao gerar a assinatura.

Ao verificar um JWS/JWT assinado, você precisa fornecer uma chave capaz de verificar a assinatura.

  • No caso de um algoritmo de assinatura RS*, PS* ou ES*, é necessário fornecer a chave pública associada à chave privada que foi usada originalmente para assinar o token.
  • No caso de um algoritmo HS*, é necessário fornecer a mesma chave simétrica usada para assinar a JWS ou o JWT.

Você tem duas opções para fornecer as chaves das políticas de JWS e JWT:

  • Forneça a chave-valor diretamente (em geral, com uma variável de contexto); ou
  • Forneça a chave indiretamente, por um kid e um JWKS. É possível especificar o JWKS direta ou indiretamente por um URL HTTP em que a Apigee pode recuperar o JWKS.

A opção de URL do JWKS normalmente é usada apenas como uma fonte de chaves públicas que podem ser usadas com algoritmos assimétricos, porque os URLs do JWKS normalmente são públicos.

Os exemplos a seguir ilustram maneiras de fornecer chaves diretamente em vários cenários.

  • Gere um JWT assinado com o algoritmo HS256. A chave necessária nesse caso é uma chave simétrica. Esta política fornece uma variável de contexto que contém a chave secreta codificada em base64url.

    <GenerateJWT name='gen-138'>
      <Algorithm>HS256</Algorithm>
      <IgnoreUnresolvedVariables>false</IgnoreUnresolvedVariables>
      <SecretKey encoding='base64url'>
        <Value ref='private.secretkey'/>
        <Id ref='variable-containing-desired-keyid'/>
      </SecretKey>
      . . .
      <OutputVariable>output_variable_name</OutputVariable>
    </GenerateJWT>
  • Verifique um JWT assinado com o algoritmo HS256. A chave necessária nesse caso é uma chave simétrica. Como no exemplo acima, essa política fornece uma variável de contexto que contém a chave secreta codificada em base64url.

    <VerifyJWT name='verify-138'>
      <Algorithm>HS256</Algorithm>
      <IgnoreUnresolvedVariables>false</IgnoreUnresolvedVariables>
      <SecretKey encoding='base64url'>
        <Value ref='private.secretkey'/>
      </SecretKey>
      . . .
      <OutputVariable>output_variable_name</OutputVariable>
    </VerifyJWT>
  • Verifique um JWT assinado com o algoritmo PS256. A chave necessária nesse caso é uma chave RSA pública. Essa política fornece uma variável de contexto que contém a chave pública codificada em PEM.

    <VerifyJWT name='JWT-001'>
      <Algorithm>PS256</Algorithm>
      <IgnoreUnresolvedVariables>false</IgnoreUnresolvedVariables>
      <PublicKey>
        <Value ref='variable-containing-pem-encoded-public-key'/>
      </PublicKey>
      . . .
    </VerifyJWT>
  • Gere um JWT assinado com o algoritmo PS256. A chave necessária nesse caso é uma chave RSA privada. Essa política fornece uma variável de contexto que contém a chave privada codificada em PEM.

    <GenerateJWT name='JWT-002'>
      <Algorithm>PS256</Algorithm>
      <IgnoreUnresolvedVariables>false</IgnoreUnresolvedVariables>
      <PrivateKey>
        <Value ref='private.variable-containing-pem-encoded-private-key'/>
      </PrivateKey>
       . . .
    </GenerateJWT>

JWKS como fonte de chaves ao verificar uma JWS ou um JWT assinado

Normalmente, quando um sistema ou aplicativo gera um JWS/JWT, o sistema ou aplicativo insere um identificador de chave (a declaração kid) no cabeçalho do JWS/JWT. A chave informa a qualquer leitor de JWS/JWT qual chave é necessária para verificar a assinatura no JWS/JWT assinado ou descriptografar o JWT criptografado.

Por exemplo, suponha que um emissor assine um JWT com uma chave privada. O "ID da chave" identifica a chave pública correspondente que precisa ser usada para verificar o JWT. A lista de chaves públicas normalmente está disponível em algum endpoint conhecido, como o endpoint do Google Identity ou o endpoint do Firebase Authentication. Outros provedores terão endpoints públicos próprios que publicam chaves no formato JWKS.

Ao usar a Apigee para verificar uma JWS ou um JWT assinado com chaves públicas compartilhadas por um endpoint do JWKS, você tem algumas opções:

  • Opção 1: na configuração da política, especifique o URI do endpoint do JWKS no elemento <PublicKey/JWKS>. Por exemplo, para a política VerifyJWT:

    <VerifyJWT name="JWT-Verify-RS256">
      <Algorithm>RS256</Algorithm>
      <Source>json.jwt</Source>
      <IgnoreUnresolvedVariables>false</IgnoreUnresolvedVariables>
      <PublicKey>
          <JWKS uri="https://www.googleapis.com/oauth2/v3/certs"/>
      </PublicKey>
      . . .
    </VerifyJWT>

    Nesse caso, a Apigee:

    1. examinará o cabeçalho do JWS/JWT para encontrar o algoritmo de assinatura (alg), como RS256, e rejeitará o JWT de entrada se esse algoritmo não corresponder ao algoritmo configurado na política;
    2. recuperará a lista de chaves com os respectivos IDs do endpoint do JWKS especificado ou de um cache interno se esse endpoint JWKS já tiver sido usado;
    3. Examine o cabeçalho JWS/JWT para encontrar o ID da chave (filho). Se o JWT de entrada não incluir um ID de chave (kid) no cabeçalho, o mapeamento de kid para a chave de verificação não será possível, e a Apigee gerará uma falha;
    4. extrairá do JWKS o JWK com o ID da chave anotado no cabeçalho do JWS/JWT. Um erro será gerado se uma chave com esse ID não estiver presente;
    5. verificará se o algoritmo da JWK corresponde àquele especificado na configuração da política. Rejeitará a verificação e gerará uma falha se os algoritmos não forem correspondentes;
    6. Use essa chave pública para verificar a assinatura no JWS/JWT. Rejeitará a verificação e gerará uma falha se a assinatura não for verificada.
  • Opção 2: na configuração da política, especifique uma variável que contenha o URI do endpoint do JWKS no elemento <PublicKey/JWKS>.

    Por exemplo, para a política VerifyJWT:

    <VerifyJWT name="JWT-Verify-RS256">
      <Algorithm>RS256</Algorithm>
      <Source>json.jwt</Source>
      <IgnoreUnresolvedVariables>false</IgnoreUnresolvedVariables>
      <PublicKey>
        <JWKS uriRef="variable-containing-a-uri"/>
      </PublicKey>
      . . .
    </VerifyJWT>

    Nesse caso, a Apigee executará as mesmas etapas acima, com a exceção de que a Apigee não recuperará o JWKS a partir de um URI codificado, mas a partir do URI especificado na variável referenciada pelo atributo uriRef. O armazenamento em cache ainda se aplica.

  • Opção 3: na configuração da política, especifique uma variável que contenha os dados codificados do JWKS no elemento <PublicKey/JWKS>.

    Por exemplo, para a política VerifyJWT:

    <VerifyJWT name="JWT-Verify-RS256">
      <Algorithm>RS256</Algorithm>
      <Source>json.jwt</Source>
      <IgnoreUnresolvedVariables>false</IgnoreUnresolvedVariables>
      <PublicKey>
        <JWKS ref="variable-that-holds-a-jwks"/>
      </PublicKey>
      . . .
    </VerifyJWT>

    Nesse caso, a Apigee executará as mesmas etapas acima, com a exceção de que a Apigee não recuperará o JWKS a partir de um URI, mas a partir da variável de contexto especificada no atributo ref. Normalmente, essa variável de contexto seria carregada por um ServiceCallout, uma KVM ou um arquivo de propriedades associado ao proxy.

JWKS como fonte de chaves ao gerar um JWT criptografado

Ao gerar um JWT criptografado por um algoritmo assimétrico (RSA-OAEP-256 ou qualquer uma das variantes ECDH-*), você usa a chave pública para fazer a criptografia. Você tem opções para fornecer a chave para a política GenerateJWT.

Uma abordagem típica é especificar na configuração da política o URI do endpoint do JWKS no elemento <PublicKey/JWKS>. Exemplo:

<GenerateJWT name="GJWT-1">
  <Algorithms>
    <Key>RSA-OAEP-256</Key>
    <Content>A128GCM</Content>
  </Algorithms>
  <IgnoreUnresolvedVariables>false</IgnoreUnresolvedVariables>
  <PublicKey>
    <JWKS uri='https://www.example.com/.well-known/jwks.json'/>
    <Id ref='variable-containing-desired-keyid'/>
  </PublicKey>
    . . .
</GenerateJWT>

Nesse caso, a Apigee:

  1. montará o payload e o cabeçalho não codificados para o JWT com base na configuração da política;
  2. recuperará a lista de chaves com os respectivos IDs do endpoint do JWKS especificado ou de um cache interno se esse endpoint JWKS já tiver sido usado. No momento, o TTL do cache é de 5 minutos;
  3. extrairá do JWKS a JWK com o ID da chave anotado no elemento PublicKey/Id. Um erro será gerado se uma chave com esse ID não estiver presente;
  4. verificará se o algoritmo da JWK corresponde àquele especificado na configuração da política. Uma falha será gerada se os algoritmos não forem correspondentes;
  5. gerará uma sequência aleatória para ser usada como chave de criptografia de conteúdo;
  6. usará a chave pública selecionada para criptografar a chave de criptografia de conteúdo;
  7. usará a chave de criptografia de conteúdo para criptografar o payload;
  8. por fim, montará todas as partes em um JWT criptografado serializado.

Uma alternativa é usar o atributo uriRef para especificar uma variável que contenha o URI de um endpoint do JWKS. Exemplo:

<GenerateJWT name="GJWT-1">
  <Algorithms>
    <Key>RSA-OAEP-256</Key>
    <Content>A128GCM</Content>
  </Algorithms>
  <IgnoreUnresolvedVariables>false</IgnoreUnresolvedVariables>
  <PublicKey>
    <JWKS uriRef='variable-containing-jwks-uri'/>
    <Id ref='variable-containing-desired-keyid'/>
  </PublicKey>
  . . .
</GenerateJWT>

Nesse caso, a Apigee executará as mesmas etapas acima, com a exceção de que a Apigee recuperará o JWKS a partir do URI especificado na variável referenciada pelo atributo uriRef, no lugar de um URI codificado. A Apigee lerá o JWKS a partir de um cache interno se o endpoint do JWKS já tiver sido usado.