Skip to content

Commit 657328d

Browse files
fix(isJWT): validate Base64url-decoded header and payload are JSON objects (fixes #2511)
1 parent b1aea75 commit 657328d

2 files changed

Lines changed: 33 additions & 5 deletions

File tree

src/lib/isJWT.js

Lines changed: 24 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,15 +1,34 @@
11
import assertString from './util/assertString';
22
import isBase64 from './isBase64';
33

4+
function tryDecodeJSON(segment) {
5+
if (!isBase64(segment, { urlSafe: true })) return false;
6+
try {
7+
// Normalize base64url alphabet to base64, then restore stripped padding
8+
let b64 = segment.replace(/-/g, '+').replace(/_/g, '/');
9+
while (b64.length % 4) b64 += '=';
10+
const decoded = Buffer.from(b64, 'base64').toString('utf8');
11+
const parsed = JSON.parse(decoded);
12+
return typeof parsed === 'object' && parsed !== null && !Array.isArray(parsed);
13+
} catch (e) {
14+
return false;
15+
}
16+
}
17+
418
export default function isJWT(str) {
519
assertString(str);
620

721
const dotSplit = str.split('.');
8-
const len = dotSplit.length;
922

10-
if (len !== 3) {
11-
return false;
12-
}
23+
if (dotSplit.length !== 3) return false;
24+
25+
const header = dotSplit[0];
26+
const payload = dotSplit[1];
27+
const signature = dotSplit[2];
28+
29+
if (!tryDecodeJSON(header)) return false;
30+
if (!tryDecodeJSON(payload)) return false;
31+
if (!isBase64(signature, { urlSafe: true })) return false;
1332

14-
return dotSplit.reduce((acc, currElem) => acc && isBase64(currElem, { urlSafe: true }), true);
33+
return true;
1534
}

test/validators.test.js

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5549,6 +5549,15 @@ describe('Validators', () => {
55495549
'eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NSIsIm5hbWUiOiJKb2huIERvZSIsImlhdCI6MTYxNjY1Mzg3Mn0.eyJpc3MiOiJodHRwczovL2V4YW1wbGUuY29tIiwiaWF0IjoxNjE2NjUzODcyLCJleHAiOjE2MTY2NTM4ODJ9.a1jLRQkO5TV5y5ERcaPAiM9Xm2gBdRjKrrCpHkGr_8M',
55505550
'$Zs.ewu.su84',
55515551
'ks64$S/9.dy$§kz.3sd73b',
5552+
'foo.bar.',
5553+
'..',
5554+
'.t.',
5555+
'foo.bar.baz',
5556+
'Zm9v.YmFy.',
5557+
'eyJmb28iOiJiYXIifQ.YmFy.',
5558+
'Zm9v.eyJiYXIiOiJiYXoifQ.',
5559+
'W10=.eyJiYXIiOiJiYXoifQ.',
5560+
'eyJmb28iOiJiYXIifQ.W10=.',
55525561
],
55535562
error: [
55545563
[],

0 commit comments

Comments
 (0)