# JWT

## Guia Rápido

Aqui vão os principais cuidados ao utilizar tokens JWT:

### 1. Utilizar uma assinatura forte

Quando assinamos o nosso token, precisamos utilizar um segredo de tamanho considerável.

Podemos assinar um token JWT de várias formas, mas as principais são utilizando chaves simétricas (**HS256, HMAC + SHA-256**) e assimétricas (**RS256, RSA + SHA-256**).

Como recomendação, é melhor utilizar assinatura **assimétrica**, uma vez que:

* Apenas um serviço consegue gerar o token (utilizando chave privada), enquanto outros serviços só conseguem verificar (chave pública).
* Se a chave privada for comprometida, rotacionar ela não quebra as outras aplicações com o token atual, afinal, as chaves públicas de verificação continuarão funcionando.

{% code title="JWT com chave assimétrica" lineNumbers="true" %}

```js
const fs = require('fs');
const jwt = require('jsonwebtoken');

// use 'utf8' to get string instead of byte array  (512 bit key)
const privateKEY = fs.readFileSync('./private.key', 'utf8');
const publicKEY = fs.readFileSync('./public.key', 'utf8');

const payload = {
  name: 'Gandalf'
}

// SIGN
const signOptions = {
  issuer: "Authorizaxtion/Resource/This server",
  subject: "iam@user.me",
  audience: "Client_Identity",
  expiresIn: "1d",
  algorithm: "RS256"
};

const token = jwt.sign(payload, privateKEY, signOptions);
console.log('\n\n=== TOKEN ===');
console.log(token);


// VERIFY
var verifyOptions = {
  issuer: "Authorizaxtion/Resource/This server",
  subject: "iam@user.me",
  audience: "Client_Identity",
  expiresIn: "1d",
  algorithm: "RS256"
};

const verified = jwt.verify(token, publicKEY, verifyOptions);
console.log('\n\n=== VERIFIED ===');
console.log(verified);


// DECODE
const decoded = jwt.decode(token, { complete: true });
console.log('\n\n=== DECODED ===');
console.log(decoded);

```

{% endcode %}

Veja um exemplo funcional no [Replit](https://replit.com/@bhrott/JWT-RS256-Nodejs#index.js).

### 2. Sempre definir o algorítmo no momento de fazer a verificação

Existe um tipo de vulnerabilidade que ocorre em algumas configurações de JWT que é o [None Algorithm](https://blog.pentesteracademy.com/hacking-jwt-tokens-the-none-algorithm-67c14bb15771).

Em resumo, o atacante muda o header do JWT para:

```json
{
  "typ": "JWT",
  "alg": "none"
}
```

E no backend a lib que usamos pega o valor do **alg** e ignora a chave de verificação.

Para que isto não aconteça, sempre devemos definir o alg no momento de verificar o token:

```js
var verifyOptions = {
  //...
  algorithm: "RS256"
};

const verified = jwt.verify(token, publicKEY, verifyOptions);
```

## Links Úteis

* [Site Oficial - jwt.io](https://jwt.io/)
* [RFC 7519](https://www.rfc-editor.org/rfc/rfc7519)
* [tokens.dev](https://token.dev/)
* [Portswigger Academy - JWT Attacks](https://portswigger.net/web-security/jwt)
* [Auth0 - JWT](https://auth0.com/docs/secure/tokens/json-web-tokens)

## Artigos

* [How to use Azure to crack API auth tokens](https://danaepp.com/how-to-use-azure-to-crack-api-auth-tokens)


---

# Agent Instructions: Querying This Documentation

If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://ben-hurs-organization.gitbook.io/guia-de-appsec/cheat-sheets/jwt.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
