Socket
Socket
Sign inDemoInstall

@connectedcars/jwtutils

Package Overview
Dependencies
114
Maintainers
1
Versions
33
Alerts
File Explorer

Advanced tools

Install Socket

Detect and block malicious and high-risk dependencies

Install

Comparing version 1.0.4 to 1.0.5

2

package.json
{
"name": "@connectedcars/jwtutils",
"version": "1.0.4",
"version": "1.0.5",
"description": "Zero dependency JWT encoding/decoding for Node",

@@ -5,0 +5,0 @@ "main": "src/index.js",

@@ -8,10 +8,35 @@ # node-jwtutils

This module only supports asymmetric encryption algorithms such as RS256,
RS384, RS512, ES256, ES384 and ES512. It currently does not implement symmetric
encryption as this is a really bad idea for any production use.
Features:
## Usage
* Encode and decode any RS256, RS384, RS512, ES256, ES384 and ES512 signed tokens
* Support for multiple issuers and keys per issuer.
* Express middleware to validate JWT's
## Background
Most other JWT implementations tend be complex and have a large array of
dependencies because they implement the seldom used JOSE standard.
This often makes the whole JWT encoding/decoding complicated and hard to
understand, something it really should not be.
So the focus of this module has been to make a simple, secure, fast and
flexible set of utility methods to work with JWT's. The code itself is also
easy to understand and less than 200 lines of code, making it much easier to
security audit the code.
Also note doing your own crypto is a bad idea so this module only deals with
the encoding/decoding of the JWT, the underlaying crypto operations are done
by Node's build-in crypto api that uses openssl.
Currently only asymmetric encryption algorithms are supported as this would
also be the only recommend option for production use.
## Samples
* [Integrates with Google Identity Platform](sample/googleoauth2v2/README.md)
## Basic usage
``` javascript
const jwtUtils = require('jwtutils')
const { JwtUtils, JwtVerifyError } = require('@connectedcars/jwtutils')

@@ -51,4 +76,4 @@ let jwtHeader = {

// let jwt = jwtUtils.encode(pemEncodedPrivateKey, jwtHeader, jwtBody, privateKeyPassword)
let jwt = jwtUtils.encode(pemEncodedPrivateKey, jwtHeader, jwtBody)
// let jwt = JwtUtils.encode(pemEncodedPrivateKey, jwtHeader, jwtBody, privateKeyPassword)
let jwt = JwtUtils.encode(pemEncodedPrivateKey, jwtHeader, jwtBody)

@@ -74,3 +99,3 @@ // Don't use this key for anything but testing as this is the key from jwt.io

try {
let decodedJwtBody = jwtUtils.decode(jwt, pubKeys, allowedAudinces)
let decodedJwtBody = JwtUtils.decode(jwt, pubKeys, allowedAudinces)
} catch (e) {

@@ -86,7 +111,7 @@ if (e instanceof JwtVerifyError) {

## Express authentication middleware
## Usage of express middleware
``` javascript
const express = require('express')
const jwtAuthMiddleware = require('./jwtauthmiddleware')
const { JwtAuthMiddleware, JwtVerifyError } = require('@connectedcars/jwtutils')

@@ -104,3 +129,3 @@ // Configuration

// Register the middleware
app.use(jwtAuthMiddleware(pubKeys, audiences))
app.use(JwtAuthMiddleware(pubKeys, audiences))

@@ -107,0 +132,0 @@ // Register an error handler to return 401 errors

@@ -7,4 +7,3 @@ 'use strict'

const jwtAuthMiddleware = require('../../src/jwtauthmiddleware')
const JwtVerifyError = require('../../src/jwtverifyerror')
const { JwtAuthMiddleware, JwtVerifyError } = require('../../src/.')

@@ -14,20 +13,10 @@ const request = require('request')

const audiences = [
'807025168921-ti2uj07r2iammimbneq706at7497gtto.apps.googleusercontent.com'
]
if (process.argv.length <= 2) {
console.error('node index.js "google-oauth-cclientid"')
process.exit(255)
}
const rsaPublicKey =
'-----BEGIN PUBLIC KEY-----\n' +
'MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQDdlatRjRjogo3WojgGHFHYLugd\n' +
'UWAY9iR3fy4arWNA1KoS8kVw33cJibXr8bvwUAUparCwlvdbH6dvEOfou0/gCFQs\n' +
'HUfQrSDv+MuSUMAe8jzKE4qW+jK+xQU9a03GUnKHkkle+Q0pX/g6jXZ7r1/xAK5D\n' +
'o2kQ+X5xK9cipRgEKwIDAQAB\n' +
'-----END PUBLIC KEY-----'
const audiences = [process.argv[2]]
const pubKeys = {}
const pubKeys = {
'http://localhost:3000/auth': {
'1@RS256': rsaPublicKey
}
}
const app = express()

@@ -38,3 +27,3 @@ app.use('/', express.static(path.join(__dirname, 'public')))

'/api',
jwtAuthMiddleware(pubKeys, audiences, user => {
JwtAuthMiddleware(pubKeys, audiences, user => {
// Use e-mail as subject for google tokens

@@ -41,0 +30,0 @@ if (user.issuer === 'https://accounts.google.com') {

@@ -20,6 +20,10 @@ # Sample Express app that integrates with Google Identity Platform

Replace audiences with own client id in index.js
## Run sample application
``` bash
node index.js '<OAuth Client ID>'
```
## Links
* Scopes: https://developers.google.com/identity/protocols/googlescopes

@@ -5,6 +5,15 @@ 'use strict'

const jwtDecode = require('./jwtdecode')
const JwtVerifyError = require('./jwtverifyerror')
const JwtAuthMiddleware = require('./jwtauthmiddleware')
module.exports = {
JwtUtils: {
encode: jwtEncode,
decode: jwtDecode
},
JwtVerifyError: JwtVerifyError,
JwtAuthMiddleware: JwtAuthMiddleware,
// Support old interface
encode: jwtEncode,
decode: jwtDecode
}
'use strict'
const expect = require('unexpected')
const jwtUtils = require('./index')
const JwtVerifyError = require('./jwtverifyerror')
const { JwtUtils, JwtVerifyError } = require('./index')
const oldJwtUtils = require('./index')

@@ -86,2 +86,9 @@ const rsaPublicKey =

describe('encode/decode', () => {
it('success old inteface', () => {
let jwt = oldJwtUtils.encode(rsaPrivateKey, jwtHeader, jwtBody)
let decodedJwtBody = oldJwtUtils.decode(jwt, pubKeys, [
'https://host/oauth/token'
])
expect(jwtBody, 'to equal', decodedJwtBody)
})
it('success with RSA at RS256, RS384 and RS512', () => {

@@ -91,4 +98,4 @@ for (let algo of ['RS256', 'RS384', 'RS512']) {

customJwtHeader.alg = algo
let jwt = jwtUtils.encode(rsaPrivateKey, customJwtHeader, jwtBody)
let decodedJwtBody = jwtUtils.decode(jwt, pubKeys, [
let jwt = JwtUtils.encode(rsaPrivateKey, customJwtHeader, jwtBody)
let decodedJwtBody = JwtUtils.decode(jwt, pubKeys, [
'https://host/oauth/token'

@@ -103,4 +110,4 @@ ])

customJwtHeader.alg = algo
let jwt = jwtUtils.encode(ecPrivateKey, customJwtHeader, jwtBody)
let decodedJwtBody = jwtUtils.decode(jwt, pubKeys, [
let jwt = JwtUtils.encode(ecPrivateKey, customJwtHeader, jwtBody)
let decodedJwtBody = JwtUtils.decode(jwt, pubKeys, [
'https://host/oauth/token'

@@ -114,4 +121,4 @@ ])

delete customJwtHeader.kid
let jwt = jwtUtils.encode(rsaPrivateKey, customJwtHeader, jwtBody)
let decodedJwtBody = jwtUtils.decode(jwt, pubKeys, [
let jwt = JwtUtils.encode(rsaPrivateKey, customJwtHeader, jwtBody)
let decodedJwtBody = JwtUtils.decode(jwt, pubKeys, [
'https://host/oauth/token'

@@ -127,4 +134,4 @@ ])

]
let jwt = jwtUtils.encode(rsaPrivateKey, jwtHeader, customJwtBody)
let decodedJwtBody = jwtUtils.decode(jwt, pubKeys, [
let jwt = JwtUtils.encode(rsaPrivateKey, jwtHeader, customJwtBody)
let decodedJwtBody = JwtUtils.decode(jwt, pubKeys, [
'https://host/oauth/token'

@@ -135,6 +142,6 @@ ])

it('unknown aud', () => {
let jwt = jwtUtils.encode(rsaPrivateKey, jwtHeader, jwtBody)
let jwt = JwtUtils.encode(rsaPrivateKey, jwtHeader, jwtBody)
expect(
() => {
jwtUtils.decode(jwt, pubKeys, ['https://myhost/oauth/token'])
JwtUtils.decode(jwt, pubKeys, ['https://myhost/oauth/token'])
},

@@ -149,6 +156,6 @@ 'to throw',

customJwtBody.exp -= 800
let jwt = jwtUtils.encode(rsaPrivateKey, jwtHeader, customJwtBody)
let jwt = JwtUtils.encode(rsaPrivateKey, jwtHeader, customJwtBody)
expect(
() => {
jwtUtils.decode(jwt, pubKeys, ['https://host/oauth/token'])
JwtUtils.decode(jwt, pubKeys, ['https://host/oauth/token'])
},

@@ -162,6 +169,6 @@ 'to throw',

delete customJwtBody.exp
let jwt = jwtUtils.encode(rsaPrivateKey, jwtHeader, customJwtBody)
let jwt = JwtUtils.encode(rsaPrivateKey, jwtHeader, customJwtBody)
expect(
() => {
jwtUtils.decode(jwt, pubKeys, ['https://host/oauth/token'])
JwtUtils.decode(jwt, pubKeys, ['https://host/oauth/token'])
},

@@ -175,6 +182,6 @@ 'to throw',

delete customJwtBody.iss
let jwt = jwtUtils.encode(rsaPrivateKey, jwtHeader, customJwtBody)
let jwt = JwtUtils.encode(rsaPrivateKey, jwtHeader, customJwtBody)
expect(
() => {
jwtUtils.decode(jwt, pubKeys, ['https://host/oauth/token'])
JwtUtils.decode(jwt, pubKeys, ['https://host/oauth/token'])
},

@@ -188,6 +195,6 @@ 'to throw',

customJwtBody.iat += 1200
let jwt = jwtUtils.encode(rsaPrivateKey, jwtHeader, customJwtBody)
let jwt = JwtUtils.encode(rsaPrivateKey, jwtHeader, customJwtBody)
expect(
() => {
jwtUtils.decode(jwt, pubKeys, ['https://host/oauth/token'])
JwtUtils.decode(jwt, pubKeys, ['https://host/oauth/token'])
},

@@ -201,6 +208,6 @@ 'to throw',

customJwtBody.nbf = customJwtBody.iat + 1200
let jwt = jwtUtils.encode(rsaPrivateKey, jwtHeader, customJwtBody)
let jwt = JwtUtils.encode(rsaPrivateKey, jwtHeader, customJwtBody)
expect(
() => {
jwtUtils.decode(jwt, pubKeys, ['https://host/oauth/token'])
JwtUtils.decode(jwt, pubKeys, ['https://host/oauth/token'])
},

@@ -214,6 +221,6 @@ 'to throw',

customJwtBody.iss += 'unknown@test.com'
let jwt = jwtUtils.encode(rsaPrivateKey, jwtHeader, customJwtBody)
let jwt = JwtUtils.encode(rsaPrivateKey, jwtHeader, customJwtBody)
expect(
() => {
jwtUtils.decode(jwt, pubKeys, ['https://host/oauth/token'])
JwtUtils.decode(jwt, pubKeys, ['https://host/oauth/token'])
},

@@ -229,3 +236,3 @@ 'to throw',

() => {
jwtUtils.encode(rsaPrivateKey, customJwtHeader, jwtBody)
JwtUtils.encode(rsaPrivateKey, customJwtHeader, jwtBody)
},

@@ -239,6 +246,6 @@ 'to throw',

customJwtHeader.kid = 3
let jwt = jwtUtils.encode(rsaPrivateKey, customJwtHeader, jwtBody)
let jwt = JwtUtils.encode(rsaPrivateKey, customJwtHeader, jwtBody)
expect(
() => {
jwtUtils.decode(jwt, pubKeys, ['https://host/oauth/token'])
JwtUtils.decode(jwt, pubKeys, ['https://host/oauth/token'])
},

@@ -252,6 +259,6 @@ 'to throw',

customJwtHeader.kid = 2
let jwt = jwtUtils.encode(rsaPrivateKey, customJwtHeader, jwtBody)
let jwt = JwtUtils.encode(rsaPrivateKey, customJwtHeader, jwtBody)
expect(
() => {
jwtUtils.decode(jwt, pubKeys, ['https://host/oauth/token'])
JwtUtils.decode(jwt, pubKeys, ['https://host/oauth/token'])
},

@@ -265,5 +272,5 @@ 'to throw',

customJwtHeader.kid = 2
let jwt = jwtUtils.encode(rsaPrivateKey, customJwtHeader, jwtBody)
let jwt = JwtUtils.encode(rsaPrivateKey, customJwtHeader, jwtBody)
try {
jwtUtils.decode(jwt, pubKeys, ['https://host/oauth/token'])
JwtUtils.decode(jwt, pubKeys, ['https://host/oauth/token'])
} catch (e) {

@@ -278,6 +285,6 @@ if (e instanceof JwtVerifyError) {

customJwtHeader.kid = 4
let jwt = jwtUtils.encode(rsaPrivateKey, customJwtHeader, jwtBody)
let jwt = JwtUtils.encode(rsaPrivateKey, customJwtHeader, jwtBody)
expect(
() => {
jwtUtils.decode(jwt, pubKeys, ['https://host/oauth/token'])
JwtUtils.decode(jwt, pubKeys, ['https://host/oauth/token'])
},

@@ -284,0 +291,0 @@ 'to throw',

'use strict'
const jwtUtils = require('./index')
const jwtDecode = require('./jwtdecode')
const JwtVerifyError = require('./jwtverifyerror')

@@ -16,3 +16,3 @@

let jwt = request.headers.authorization.substring(7)
let decodedJwtBody = jwtUtils.decode(jwt, pubKeys, audiences)
let decodedJwtBody = jwtDecode(jwt, pubKeys, audiences)
if (!decodedJwtBody.sub) {

@@ -19,0 +19,0 @@ return next(new JwtVerifyError(`Missing 'sub' in body`))

const express = require('express')
const app = express()
const http = require('http')
const jwtUtils = require('./index')
const jwtAuthMiddleware = require('./jwtauthmiddleware')
const { JwtUtils, JwtAuthMiddleware, JwtVerifyError } = require('./index')
const expect = require('unexpected')
const JwtVerifyError = require('./jwtverifyerror')

@@ -54,3 +52,3 @@ const ecPrivateKey =

'/mapped',
jwtAuthMiddleware(pubKeys, ['http://localhost/'], user => {
JwtAuthMiddleware(pubKeys, ['http://localhost/'], user => {
// Add test e-mail

@@ -60,3 +58,3 @@ user.eMail = 'test@domain.tld'

)
app.use('/', jwtAuthMiddleware(pubKeys, ['http://localhost/']))
app.use('/', JwtAuthMiddleware(pubKeys, ['http://localhost/']))
app.use((err, req, res, next) => {

@@ -82,3 +80,3 @@ if (err instanceof JwtVerifyError) {

it('should return ok', () => {
let jwt = jwtUtils.encode(ecPrivateKey, jwtHeader, jwtBody)
let jwt = JwtUtils.encode(ecPrivateKey, jwtHeader, jwtBody)
let responsePromise = doRequest('GET', 'localhost', port, '/', {

@@ -95,3 +93,3 @@ Authorization: 'Bearer ' + jwt,

it('should return ok with a new e-mail', () => {
let jwt = jwtUtils.encode(ecPrivateKey, jwtHeader, jwtBody)
let jwt = JwtUtils.encode(ecPrivateKey, jwtHeader, jwtBody)
let responsePromise = doRequest('GET', 'localhost', port, '/mapped', {

@@ -110,3 +108,3 @@ Authorization: 'Bearer ' + jwt,

delete customJwtBody.sub
let jwt = jwtUtils.encode(ecPrivateKey, jwtHeader, customJwtBody)
let jwt = JwtUtils.encode(ecPrivateKey, jwtHeader, customJwtBody)
let responsePromise = doRequest('GET', 'localhost', port, '/', {

@@ -123,3 +121,3 @@ Authorization: 'Bearer ' + jwt,

it('should fail because of malform JSON', () => {
let jwt = jwtUtils.encode(ecPrivateKey, jwtHeader, jwtBody)
let jwt = JwtUtils.encode(ecPrivateKey, jwtHeader, jwtBody)
let responsePromise = doRequest('GET', 'localhost', port, '/', {

@@ -138,3 +136,3 @@ Authorization: 'Bearer ' + jwt.substr(2),

customJwtHeader.kid = 2
let jwt = jwtUtils.encode(ecPrivateKey, customJwtHeader, jwtBody)
let jwt = JwtUtils.encode(ecPrivateKey, customJwtHeader, jwtBody)
let responsePromise = doRequest('GET', 'localhost', port, '/', {

@@ -141,0 +139,0 @@ Authorization: 'Bearer ' + jwt,

'use strict'
const crypto = require('crypto')
const JwtVerifyError = require('./jwtverifyerror.js')
const base64UrlSafe = require('./base64urlsafe')
const JwtVerifyError = require('./jwtverifyerror')

@@ -8,0 +8,0 @@ function jwtDecode(jwt, publicKeys, audiences, nbfIatSkrew = 300) {

'use strict'
const expect = require('unexpected')
const jwtUtils = require('./index')
const { JwtUtils } = require('./index')

@@ -20,3 +20,3 @@ const pubKeys = {}

() => {
jwtUtils.decode({}, pubKeys, audiences)
JwtUtils.decode({}, pubKeys, audiences)
},

@@ -30,3 +30,3 @@ 'to throw',

() => {
jwtUtils.decode(testJwt, [], audiences)
JwtUtils.decode(testJwt, [], audiences)
},

@@ -40,3 +40,3 @@ 'to throw',

() => {
jwtUtils.decode('hello.test', pubKeys, audiences)
JwtUtils.decode('hello.test', pubKeys, audiences)
},

@@ -50,3 +50,3 @@ 'to throw',

() => {
jwtUtils.decode(testJwt.substr(10), pubKeys, audiences)
JwtUtils.decode(testJwt.substr(10), pubKeys, audiences)
},

@@ -60,3 +60,3 @@ 'to throw',

() => {
jwtUtils.decode(testJwtWrongAlg, pubKeys, audiences)
JwtUtils.decode(testJwtWrongAlg, pubKeys, audiences)
},

@@ -63,0 +63,0 @@ 'to throw',

'use strict'
const expect = require('unexpected')
const jwtUtils = require('./index')
const { JwtUtils } = require('./index')

@@ -78,3 +78,3 @@ const rsaPrivateKeyEncrypted =

() => {
jwtUtils.encode('', '', '')
JwtUtils.encode('', '', '')
},

@@ -88,3 +88,3 @@ 'to throw',

() => {
jwtUtils.encode('', {}, {})
JwtUtils.encode('', {}, {})
},

@@ -99,3 +99,3 @@ 'to throw',

customJwtHeader.alg = algo
let jwt = jwtUtils.encode(
let jwt = JwtUtils.encode(
rsaPrivateKeyEncrypted,

@@ -106,3 +106,3 @@ customJwtHeader,

)
let decodedJwtBody = jwtUtils.decode(jwt, pubKeys, [
let decodedJwtBody = JwtUtils.decode(jwt, pubKeys, [
'https://host/oauth/token'

@@ -109,0 +109,0 @@ ])

SocketSocket SOC 2 Logo

Product

  • Package Alerts
  • Integrations
  • Docs
  • Pricing
  • FAQ
  • Roadmap

Packages

Stay in touch

Get open source security insights delivered straight into your inbox.


  • Terms
  • Privacy
  • Security

Made with ⚡️ by Socket Inc