JSPM

  • ESM via JSPM
  • ES Module Entrypoint
  • Export Map
  • Keywords
  • License
  • Repository URL
  • TypeScript Types
  • README
  • Created
  • Published
  • Downloads 87
  • Score
    100M100P100Q71525F
  • License Apache-2.0

A lightweight, zero-dependency TypeScript library for creating, verifying and decoding JSON Web Tokens (JWT).

Package Exports

  • @sourceregistry/node-jwt
  • @sourceregistry/node-jwt/promises

Readme

๐Ÿ” @sourceregistry/node-jwt

npm version License CI Codecov

A minimal, secure, and production-ready JWT (JSON Web Token) library for Node.js with zero dependencies. Supports all standard signing algorithms (HMAC, RSA, ECDSA, EdDSA, RSASSA-PSS), automatic algorithm detection, JWK/JWKS, and full claim validation.

โœจ Why another JWT library? Most JWT libraries are bloated, have security pitfalls, or lack proper TypeScript support. This library is:

  • Tiny
  • Secure by default
  • TypeScript-first with full JSDoc
  • Zero external dependencies
  • 100% test coverage
  • Dual API: Sync and Promise-based
  • Automatic algorithm detection based on key type
  • Full JWK/JWKS support (import/export, toPublicJWK, x5c/x5t, RFC 7638 thumbprints, kid-based key selection)

๐Ÿ“ฆ Installation

npm install @sourceregistry/node-jwt

Requires Node.js โ‰ฅ 16


๐Ÿš€ Quick Start

Sync API (default)

import { sign, verify, decode } from '@sourceregistry/node-jwt';

// Sign (algorithm auto-detected)
const token = sign(
  { sub: '1234567890', name: 'John Doe', iat: Math.floor(Date.now() / 1000) },
  'your-secret-key'
);

// Verify
const result = verify(token, 'your-secret-key', { issuer: 'https://example.com' });
if (result.valid) {
  console.log('Payload:', result.payload);
} else {
  console.error('JWT Error:', result.error.code, result.error.reason);
}

// Decode (unsafe)
const { header, payload, signature } = decode(token);

Promise API (/promises)

import { sign, verify, decode } from '@sourceregistry/node-jwt/promises';

// Sign (algorithm auto-detected)
const token = await sign(
  { sub: '1234567890', name: 'John Doe', iat: Math.floor(Date.now() / 1000) },
  'your-secret-key'
);

// Verify
try {
  const { payload } = await verify(token, 'your-secret-key', {
    issuer: 'https://example.com',
    audience: 'my-app',
    algorithms: ['HS256']
  });
  console.log('Payload:', payload);
} catch (error) {
  console.error('JWT Error:', error.code, error.reason);
}

// Decode (unsafe)
const { header, payload, signature } = await decode(token);

๐Ÿง  Algorithm Autodetection (New)

When options.alg is omitted, the library automatically selects the correct JWT algorithm based on the signing key.

๐Ÿ”‘ Autodetection Rules

Key Type Detection Logic Selected Algorithm
Symmetric (string / Buffer) Default HMAC HS256
RSA private key PKCS#1 v1.5 RS256
RSA-PSS private key Hash algorithm in key PS256 / PS384 / PS512
EC P-256 (prime256v1) Curve name ES256
EC P-384 (secp384r1) Curve name ES384
EC P-521 (secp521r1) Curve name ES512
EC secp256k1 Curve name ES256K
Ed25519 Key type EdDSA

๐Ÿ’ก Node.js exposes OpenSSL curve names (prime256v1, secp384r1, etc.). These are automatically normalized to JOSE algorithms.

โŒ Autodetection Errors

Autodetection fails for unsupported keys:

  • Unsupported EC curve
  • Unsupported RSA-PSS hash algorithm (e.g. sha1)
  • Unsupported asymmetric key type (e.g. DSA)

๐Ÿ”‘ Supported Algorithms

Algorithm Type Secret Type
HS256 / HS384 / HS512 HMAC string | Buffer
RS256 / RS384 / RS512 RSA Private / Public key
PS256 / PS384 / PS512 RSA-PSS Private / Public key
ES256 / ES384 / ES512 ECDSA Private / Public key
ES256K ECDSA (secp256k1) Private / Public key
EdDSA Ed25519 Private / Public key

Keys may be PEM, DER, JWK, or Node.js KeyObject.


๐Ÿงฉ JWK / JWKS Support

  • Import/export JWK: importJWK(), exportJWK()
  • Convert to public-only JWK: toPublicJWK()
  • Compute RFC 7638 thumbprint: getJWKThumbprint()
  • Support x5c/x5t (X.509 cert chain + SHA-1 thumbprint)
  • Normalize JWKS with auto-generated kid and x5t
  • Resolve keys from JWKS by kid for verification

๐Ÿ”น Example: JWKS Key Selection

import { JWKS, JWK } from '@sourceregistry/node-jwt';

const keyPair = generateKeyPairSync('rsa', { modulusLength: 2048 });
const jwk = JWK.toPublic(keyPair.publicKey);
const jwks = JWKS.normalize({ keys: [jwk] });

// Retrieve key by kid
const keyObject = JWKS.toKeyObject(jwks, jwk.kid);

๐Ÿ›ก๏ธ Security Features

  • โœ… Safe algorithm autodetection
  • โœ… Strict algorithm whitelisting (algorithms option)
  • โœ… Full RSASSA-PSS and Ed25519 support
  • โœ… Time claim validation (exp, nbf, iat) with clock skew
  • โœ… Claim validation (iss, sub, aud, jti)
  • โœ… Maximum token age enforcement
  • โœ… Timing-safe signature comparison
  • โœ… No insecure defaults

๐Ÿ“š API Reference

sign(payload, secret, options?)

  • alg (optional) โ€” If omitted, algorithm is auto-detected
  • kid โ€” Key ID
  • typ โ€” Token type (default: "JWT")

verify(token, secret, options?)

Includes algorithm whitelist protection and full claim validation.

Error Codes include:

  • INVALID_TOKEN
  • INVALID_ALGORITHM
  • ALGORITHM_NOT_ALLOWED
  • INVALID_SIGNATURE
  • TOKEN_EXPIRED
  • TOKEN_NOT_ACTIVE
  • TOKEN_TOO_OLD
  • MISSING_* / INVALID_*

decode(token)

Decode a JWT without verification (unsafe).


๐Ÿงช Testing

  • 100% branch coverage
  • All algorithms + autodetection paths
  • All failure modes
  • Sync + Promise APIs
  • Full JWK/JWKS coverage (import/export, x5c/x5t, thumbprint, kid selection)
npm test
npm run test:coverage

๐Ÿ“ฆ Exports

Import Description
@sourceregistry/node-jwt Sync API
@sourceregistry/node-jwt/promises Promise API

๐Ÿ™Œ Contributing

PRs welcome! Please add tests and maintain full coverage.

๐Ÿ” Security issues? Report responsibly: a.p.a.slaa@projectsource.nl

๐Ÿ”— GitHub: https://github.com/SourceRegistry/node-jwt ๐Ÿ“ฆ npm: https://www.npmjs.com/package/@sourceregistry/node-jwt