Skip to content

Tdd/validacion opciones verify - #1051

Open
EdgarJ16 wants to merge 8 commits into
auth0:masterfrom
amoramongeCenfo:tdd/validacion-opciones-verify
Open

EdgarJ16 wants to merge 8 commits into
auth0:masterfrom
amoramongeCenfo:tdd/validacion-opciones-verify

Conversation

@EdgarJ16

@EdgarJ16 EdgarJ16 commented Oct 25, 2026 •

Copy link
Copy Markdown

Description

jwt.verify() validates the type of only four of the thirteen options it reads (clockTimestamp, nonce, maxAge and allowInvalidAsymmetricKeyTypes). jwt.sign(), by contrast, validates its options against a schema. As a result, a misconfigured verify() call can silently disable the expiration check.

Reproduction on v9.0.3 (commit b924272), with a token that expired 60 seconds ago:

jwt.verify(expiredToken, 'secret', { clockTolerance: 'abc' });        // returns the payload
jwt.verify(expiredToken, 'secret', { clockTolerance: '3600' });       // returns the payload
jwt.verify(expiredToken, 'secret', { clockTolerance: Infinity });     // returns the payload
jwt.verify(expiredToken, 'secret', { ignoreExpiration: 'false' });    // returns the payload

All four calls should throw TokenExpiredError. A string such as 'false' (for example, read from an environment variable) is truthy, so the expiration check is skipped. clockTolerance values that are not finite numbers make the comparison clockTimestamp >= exp + clockTolerance evaluate to false, so the token never expires.

This PR adds the missing validation at the top of verify(), next to the existing option checks and before the token is processed:

  • HU-01: clockTolerance must be a finite number, otherwise JsonWebTokenError: clockTolerance must be a finite number.
  • HU-02: ignoreExpiration and ignoreNotBefore must be booleans when defined, otherwise JsonWebTokenError: <option> must be a boolean.

Errors are returned through the callback when one is given, and thrown otherwise, consistent with the existing option validations.

Breaking changes. This is a behavior change for callers that pass invalid values today:

  • Non-numeric, NaN, ±Infinity and null values for clockTolerance are now rejected. Before, null behaved like 0.
  • Non-boolean values for ignoreExpiration and ignoreNotBefore (such as 0, 1, 'true', {}) are now rejected. Valid callers (true, false or the option omitted) are unaffected.

Alternatives considered. Coercing the values (for example 'false' to false) was rejected because it would hide the configuration error instead of reporting it. Moving all validation to a schema like sign() uses is a larger refactor and is left out of this PR.

Out of scope. Rejecting unknown option names (for example the typo algoritms) is tracked as a separate change (HU-03). The test file already includes its 3 test cases, which still fail in this PR on purpose.

References

  • Baseline analysis of the library: jsonwebtoken v9.0.3 quality evaluation (PSWE-06, Universidad Cenfotec).
  • Related behavior in sign(): sign_options_schema in sign.js.

Testing

New file: test/verify-options-validation.test.js (27 cases), written before the implementation and run first to confirm it failed (24 failing, 3 passing).

@EdgarJ16
EdgarJ16 requested a review from a team as a code owner October 25, 2026 15:05
Prepara el rechazo de opciones desconocidas en verify(): 46 pruebas
de 7 archivos pasaban opciones que verify() ignora en silencio.

- algorithm -> algorithms en option-maxAge y jwt.hs (no restringia
  la lista blanca de algoritmos)
- jetid -> jwtid en claim-jti (la prueba nunca ejercia jwtid)
- se retiran typ, exp y nbf de las opciones de verify
verify() ignoraba en silencio cualquier opcion que no leyera, de modo
que un error tipografico como "algoritms" descartaba la lista blanca
de algoritmos. Ahora solo se aceptan las 13 opciones documentadas y
cualquier otra produce JsonWebTokenError:
'"<nombre>" is not an allowed option', lanzado o por callback.

BREAKING CHANGE: verify() rechaza opciones no documentadas (por
ejemplo algorithm, typ, exp, nbf o expiresIn).
…ptions.js (HU-04)

Mueve fuera de verify() la lista de opciones permitidas y las reglas de
tipo de clockTimestamp, clockTolerance, ignoreExpiration,
ignoreNotBefore, nonce y allowInvalidAsymmetricKeyTypes. El modulo
devuelve el JsonWebTokenError o null, y verify() lo entrega por done.

Sin cambios de comportamiento: mismos mensajes y mismo orden. La
funcion externa de verify() baja de complejidad 27 a menos de 15; el
callback se mantiene en 57. El modulo nuevo tiene 100 % de cobertura.
@amoramongeCenfo
amoramongeCenfo force-pushed the tdd/validacion-opciones-verify branch from 541992e to 49be9d7 Compare October 26, 2026 02:05
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants