Skip to content

Commit 5a3a009

Browse files
author
Olivier MICHAUD
committed
Add a JWT checking management
1 parent dbba723 commit 5a3a009

File tree

5 files changed

+200
-4
lines changed

5 files changed

+200
-4
lines changed

bin/server

+5
Original file line numberDiff line numberDiff line change
@@ -35,6 +35,10 @@ const argv = optimist
3535
default: null,
3636
describe: 'will bind incoming connections only on ports in range xxx:xxxx'
3737
})
38+
.options('jwt-shared-secret', {
39+
default: null,
40+
describe: 'JWT shared secret used to encode tokens'
41+
})
3842
.argv;
3943

4044
if (argv.help) {
@@ -47,6 +51,7 @@ const server = CreateServer({
4751
secure: argv.secure,
4852
domain: argv.domain,
4953
range: argv.range,
54+
jwt_shared_secret: argv['jwt-shared-secret']
5055
});
5156

5257
server.listen(argv.port, argv.address, () => {

package.json

+2-1
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,7 @@
1414
"esm": "3.0.34",
1515
"human-readable-ids": "1.0.3",
1616
"koa": "2.5.1",
17+
"koa-jwt": "4.0.0",
1718
"koa-router": "7.4.0",
1819
"localenv": "0.2.2",
1920
"optimist": "0.6.1",
@@ -29,6 +30,6 @@
2930
"scripts": {
3031
"test": "mocha --check-leaks --require esm './**/*.test.js'",
3132
"start": "./bin/server",
32-
"dev": "node-dev bin/server --port 3000"
33+
"dev": "node-dev bin/server --require esm --port 3000"
3334
}
3435
}

server.js

+11
Original file line numberDiff line numberDiff line change
@@ -5,11 +5,18 @@ import Debug from 'debug';
55
import http from 'http';
66
import { hri } from 'human-readable-ids';
77
import Router from 'koa-router';
8+
import jwt from'koa-jwt';
89

910
import ClientManager from './lib/ClientManager';
1011

1112
const debug = Debug('localtunnel:server');
1213

14+
function addJwtMiddleware(app, opt) {
15+
app.use(jwt({
16+
secret: opt.jwt_shared_secret
17+
}));
18+
}
19+
1320
export default function(opt) {
1421
opt = opt || {};
1522

@@ -28,6 +35,10 @@ export default function(opt) {
2835
const app = new Koa();
2936
const router = new Router();
3037

38+
if (opt.jwt_shared_secret){
39+
addJwtMiddleware(app, opt);
40+
}
41+
3142
router.get('/api/status', async (ctx, next) => {
3243
const stats = manager.stats;
3344
ctx.body = {

server.test.js

+28-3
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,9 @@
11
import request from 'supertest';
22
import assert from 'assert';
3-
import { Server as WebSocketServer } from 'ws';
4-
import WebSocket from 'ws';
3+
import WebSocket, {Server as WebSocketServer} from 'ws';
54
import net from 'net';
5+
import jwt from 'jsonwebtoken';
6+
67

78
import createServer from './server';
89

@@ -34,6 +35,30 @@ describe('Server', () => {
3435
assert.equal(res.body.message, 'Invalid subdomain. Subdomains must be lowercase and between 4 and 63 alphanumeric characters.');
3536
});
3637

38+
it('reject request without jwt if required', async () => {
39+
const server = createServer({jwt_shared_secret: 'thekey'});
40+
const res = await request(server).get('/subdomain');
41+
assert.equal(res.status, 401);
42+
});
43+
44+
it('reject request with invalid jwt if required', async () => {
45+
const server = createServer({jwt_shared_secret: 'thekey'});
46+
const jwtoken = jwt.sign({
47+
foo: 'bar'
48+
}, 'thebadkey');
49+
const res = await request(server).get('/subdomain').set('Authorization', `Bearer ${jwtoken}`);
50+
assert.equal(res.status, 401);
51+
});
52+
53+
it('accept request with valid jwt if required', async () => {
54+
const server = createServer({jwt_shared_secret: 'thekey'});
55+
const jwtoken = jwt.sign({
56+
foo: 'bar'
57+
}, 'thekey');
58+
const res = await request(server).get('/subdomain').set('Authorization', `Bearer ${jwtoken}`);
59+
assert.equal(res.status, 200);
60+
});
61+
3762
it('should upgrade websocket requests', async () => {
3863
const hostname = 'websocket-test';
3964
const server = createServer({
@@ -106,4 +131,4 @@ describe('Server', () => {
106131

107132
await new Promise(resolve => server.close(resolve));
108133
});
109-
});
134+
});

yarn.lock

+154
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,14 @@ accepts@^1.2.2:
99
mime-types "~2.1.18"
1010
negotiator "0.6.1"
1111

12+
aggregate-error@^3.0.0:
13+
version "3.1.0"
14+
resolved "https://registry.yarnpkg.com/aggregate-error/-/aggregate-error-3.1.0.tgz#92670ff50f5359bdb7a3e0d40d0ec30c5737687a"
15+
integrity sha512-4I7Td01quW/RpocfNayFdFVk1qSuoh0E7JrbRJ16nH01HhKFQ88INq9Sd+nd72zqRySlr9BmDA8xlEJ6vJMrYA==
16+
dependencies:
17+
clean-stack "^2.0.0"
18+
indent-string "^4.0.0"
19+
1220
ansi-regex@^2.0.0:
1321
version "2.1.1"
1422
resolved "https://registry.yarnpkg.com/ansi-regex/-/ansi-regex-2.1.1.tgz#c3b33ab5ee360d86e0e628f0468ae7ef27d654df"
@@ -58,6 +66,11 @@ [email protected]:
5866
version "1.3.1"
5967
resolved "https://registry.yarnpkg.com/browser-stdout/-/browser-stdout-1.3.1.tgz#baa559ee14ced73452229bad7326467c61fabd60"
6068

69+
70+
version "1.0.1"
71+
resolved "https://registry.yarnpkg.com/buffer-equal-constant-time/-/buffer-equal-constant-time-1.0.1.tgz#f8e71132f7ffe6e01a5c9697a4c6f3e48d5cc819"
72+
integrity sha1-+OcRMvf/5uAaXJaXpMbz5I1cyBk=
73+
6174
builtin-modules@^1.0.0:
6275
version "1.1.1"
6376
resolved "https://registry.yarnpkg.com/builtin-modules/-/builtin-modules-1.1.1.tgz#270f076c5a72c02f5b65a47df94c5fe3a278892f"
@@ -90,6 +103,11 @@ chalk@^1.1.3:
90103
strip-ansi "^3.0.0"
91104
supports-color "^2.0.0"
92105

106+
clean-stack@^2.0.0:
107+
version "2.2.0"
108+
resolved "https://registry.yarnpkg.com/clean-stack/-/clean-stack-2.2.0.tgz#ee8472dbb129e727b31e8a10a427dee9dfe4008b"
109+
integrity sha512-4diC9HaTE+KRAMWhDhrGOECgWZxoevMc5TlkObMqNSsVU62PYzXZ/SMTjzyGAFF1YusgxGcSWTEXBhp0CPwQ1A==
110+
93111
cli-table@^0.3.1:
94112
version "0.3.1"
95113
resolved "https://registry.yarnpkg.com/cli-table/-/cli-table-0.3.1.tgz#f53b05266a8b1a0b934b3d0821e6e2dc5914ae23"
@@ -213,6 +231,13 @@ dynamic-dedupe@^0.2.0:
213231
dependencies:
214232
xtend "~2.0.6"
215233

234+
235+
version "1.0.11"
236+
resolved "https://registry.yarnpkg.com/ecdsa-sig-formatter/-/ecdsa-sig-formatter-1.0.11.tgz#ae0f0fa2d85045ef14a817daa3ce9acd0489e5bf"
237+
integrity sha512-nagl3RYrbNv6kQkeJIpt6NJZy8twLB/2vtz6yN9Z4vRKHN4/QZJIEbqohALSgwKdnksuY3k5Addp5lg8sVoVcQ==
238+
dependencies:
239+
safe-buffer "^5.0.1"
240+
216241
217242
version "1.1.1"
218243
resolved "https://registry.yarnpkg.com/ee-first/-/ee-first-1.1.1.tgz#590c61156b0ae2f4f0255732a158b266bc56b21d"
@@ -369,6 +394,11 @@ indent-string@^2.1.0:
369394
dependencies:
370395
repeating "^2.0.0"
371396

397+
indent-string@^4.0.0:
398+
version "4.0.0"
399+
resolved "https://registry.yarnpkg.com/indent-string/-/indent-string-4.0.0.tgz#624f8f4497d619b2d9768531d58f4122854d7251"
400+
integrity sha512-EdDDZu4A2OyIK7Lr/2zG+w5jmbuk1DVBnEwREQvBzspBJkCEbRa8GxU1lghYcaGJCnRWibjDXlq779X1/y5xwg==
401+
372402
indexof@~0.0.1:
373403
version "0.0.1"
374404
resolved "https://registry.yarnpkg.com/indexof/-/indexof-0.0.1.tgz#82dc336d232b9062179d05ab3293a66059fd435d"
@@ -428,6 +458,39 @@ isexe@^2.0.0:
428458
version "2.0.0"
429459
resolved "https://registry.yarnpkg.com/isexe/-/isexe-2.0.0.tgz#e8fbf374dc556ff8947a10dcb0572d633f2cfa10"
430460

461+
jsonwebtoken@^8.5.1:
462+
version "8.5.1"
463+
resolved "https://registry.yarnpkg.com/jsonwebtoken/-/jsonwebtoken-8.5.1.tgz#00e71e0b8df54c2121a1f26137df2280673bcc0d"
464+
integrity sha512-XjwVfRS6jTMsqYs0EsuJ4LGxXV14zQybNd4L2r0UvbVnSF9Af8x7p5MzbJ90Ioz/9TI41/hTCvznF/loiSzn8w==
465+
dependencies:
466+
jws "^3.2.2"
467+
lodash.includes "^4.3.0"
468+
lodash.isboolean "^3.0.3"
469+
lodash.isinteger "^4.0.4"
470+
lodash.isnumber "^3.0.3"
471+
lodash.isplainobject "^4.0.6"
472+
lodash.isstring "^4.0.1"
473+
lodash.once "^4.0.0"
474+
ms "^2.1.1"
475+
semver "^5.6.0"
476+
477+
jwa@^1.4.1:
478+
version "1.4.1"
479+
resolved "https://registry.yarnpkg.com/jwa/-/jwa-1.4.1.tgz#743c32985cb9e98655530d53641b66c8645b039a"
480+
integrity sha512-qiLX/xhEEFKUAJ6FiBMbes3w9ATzyk5W7Hvzpa/SLYdxNtng+gcurvrI7TbACjIXlsJyr05/S1oUhZrc63evQA==
481+
dependencies:
482+
buffer-equal-constant-time "1.0.1"
483+
ecdsa-sig-formatter "1.0.11"
484+
safe-buffer "^5.0.1"
485+
486+
jws@^3.2.2:
487+
version "3.2.2"
488+
resolved "https://registry.yarnpkg.com/jws/-/jws-3.2.2.tgz#001099f3639468c9414000e99995fa52fb478304"
489+
integrity sha512-YHlZCB6lMTllWDtSPHz/ZXTsi8S00usEV6v1tjq8tOUZzw7DpSDWVXjXDre6ed1w/pd495ODpHZYSdkRTsa0HA==
490+
dependencies:
491+
jwa "^1.4.1"
492+
safe-buffer "^5.0.1"
493+
431494
keygrip@~1.0.2:
432495
version "1.0.2"
433496
resolved "https://registry.yarnpkg.com/keygrip/-/keygrip-1.0.2.tgz#ad3297c557069dea8bcfe7a4fa491b75c5ddeb91"
@@ -457,6 +520,15 @@ koa-is-json@^1.0.0:
457520
version "1.0.0"
458521
resolved "https://registry.yarnpkg.com/koa-is-json/-/koa-is-json-1.0.0.tgz#273c07edcdcb8df6a2c1ab7d59ee76491451ec14"
459522

523+
524+
version "4.0.0"
525+
resolved "https://registry.yarnpkg.com/koa-jwt/-/koa-jwt-4.0.0.tgz#4cac70cde5e225bc961a266303d4b6e873cba9bc"
526+
integrity sha512-n56AG98tWQDtvVZwtVFKuPn1pGPOvtkKFEotSPRsdqKmZJqRdppDRD0toiiK7kefMLnVBzFbocaPyaI5WK/iyQ==
527+
dependencies:
528+
jsonwebtoken "^8.5.1"
529+
koa-unless "^1.0.7"
530+
p-any "^2.1.0"
531+
460532
461533
version "7.4.0"
462534
resolved "https://registry.yarnpkg.com/koa-router/-/koa-router-7.4.0.tgz#aee1f7adc02d5cb31d7d67465c9eacc825e8c5e0"
@@ -468,6 +540,11 @@ [email protected]:
468540
path-to-regexp "^1.1.1"
469541
urijs "^1.19.0"
470542

543+
koa-unless@^1.0.7:
544+
version "1.0.7"
545+
resolved "https://registry.yarnpkg.com/koa-unless/-/koa-unless-1.0.7.tgz#b9df375e2b4da3043918d48622520c2c0b79f032"
546+
integrity sha1-ud83XitNowQ5GNSGIlIMLAt58DI=
547+
471548
472549
version "2.5.1"
473550
resolved "https://registry.yarnpkg.com/koa/-/koa-2.5.1.tgz#79f8b95f8d72d04fe9a58a8da5ebd6d341103f9c"
@@ -566,6 +643,11 @@ lodash.clonedeep@^3.0.0:
566643
lodash._baseclone "^3.0.0"
567644
lodash._bindcallback "^3.0.0"
568645

646+
lodash.includes@^4.3.0:
647+
version "4.3.0"
648+
resolved "https://registry.yarnpkg.com/lodash.includes/-/lodash.includes-4.3.0.tgz#60bb98a87cb923c68ca1e51325483314849f553f"
649+
integrity sha1-YLuYqHy5I8aMoeUTJUgzFISfVT8=
650+
569651
lodash.isarguments@^3.0.0:
570652
version "3.1.0"
571653
resolved "https://registry.yarnpkg.com/lodash.isarguments/-/lodash.isarguments-3.1.0.tgz#2f573d85c6a24289ff00663b491c1d338ff3458a"
@@ -574,6 +656,31 @@ lodash.isarray@^3.0.0:
574656
version "3.0.4"
575657
resolved "https://registry.yarnpkg.com/lodash.isarray/-/lodash.isarray-3.0.4.tgz#79e4eb88c36a8122af86f844aa9bcd851b5fbb55"
576658

659+
lodash.isboolean@^3.0.3:
660+
version "3.0.3"
661+
resolved "https://registry.yarnpkg.com/lodash.isboolean/-/lodash.isboolean-3.0.3.tgz#6c2e171db2a257cd96802fd43b01b20d5f5870f6"
662+
integrity sha1-bC4XHbKiV82WgC/UOwGyDV9YcPY=
663+
664+
lodash.isinteger@^4.0.4:
665+
version "4.0.4"
666+
resolved "https://registry.yarnpkg.com/lodash.isinteger/-/lodash.isinteger-4.0.4.tgz#619c0af3d03f8b04c31f5882840b77b11cd68343"
667+
integrity sha1-YZwK89A/iwTDH1iChAt3sRzWg0M=
668+
669+
lodash.isnumber@^3.0.3:
670+
version "3.0.3"
671+
resolved "https://registry.yarnpkg.com/lodash.isnumber/-/lodash.isnumber-3.0.3.tgz#3ce76810c5928d03352301ac287317f11c0b1ffc"
672+
integrity sha1-POdoEMWSjQM1IwGsKHMX8RwLH/w=
673+
674+
lodash.isplainobject@^4.0.6:
675+
version "4.0.6"
676+
resolved "https://registry.yarnpkg.com/lodash.isplainobject/-/lodash.isplainobject-4.0.6.tgz#7c526a52d89b45c45cc690b88163be0497f550cb"
677+
integrity sha1-fFJqUtibRcRcxpC4gWO+BJf1UMs=
678+
679+
lodash.isstring@^4.0.1:
680+
version "4.0.1"
681+
resolved "https://registry.yarnpkg.com/lodash.isstring/-/lodash.isstring-4.0.1.tgz#d527dfb5456eca7cc9bb95d5daeaf88ba54a5451"
682+
integrity sha1-1SfftUVuynzJu5XV2ur4i6VKVFE=
683+
577684
lodash.keys@^3.0.0:
578685
version "3.1.2"
579686
resolved "https://registry.yarnpkg.com/lodash.keys/-/lodash.keys-3.1.2.tgz#4dbc0472b156be50a0b286855d1bd0b0c656098a"
@@ -582,6 +689,11 @@ lodash.keys@^3.0.0:
582689
lodash.isarguments "^3.0.0"
583690
lodash.isarray "^3.0.0"
584691

692+
lodash.once@^4.0.0:
693+
version "4.1.1"
694+
resolved "https://registry.yarnpkg.com/lodash.once/-/lodash.once-4.1.1.tgz#0dd3971213c7c56df880977d504c88fb471a97ac"
695+
integrity sha1-DdOXEhPHxW34gJd9UEyI+0cal6w=
696+
585697
lodash.toarray@^4.4.0:
586698
version "4.4.0"
587699
resolved "https://registry.yarnpkg.com/lodash.toarray/-/lodash.toarray-4.4.0.tgz#24c4bfcd6b2fba38bfd0594db1179d8e9b656561"
@@ -692,6 +804,11 @@ [email protected]:
692804
version "2.0.0"
693805
resolved "https://registry.yarnpkg.com/ms/-/ms-2.0.0.tgz#5608aeadfc00be6c2901df5f9861788de0d597c8"
694806

807+
ms@^2.1.1:
808+
version "2.1.2"
809+
resolved "https://registry.yarnpkg.com/ms/-/ms-2.1.2.tgz#d09d1f357b443f493382a8eb3ccd183872ae6009"
810+
integrity sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==
811+
695812
696813
version "0.6.1"
697814
resolved "https://registry.yarnpkg.com/negotiator/-/negotiator-0.6.1.tgz#2b327184e8992101177b28563fb5e7102acd0ca9"
@@ -773,6 +890,28 @@ [email protected]:
773890
minimist "~0.0.1"
774891
wordwrap "~0.0.2"
775892

893+
p-any@^2.1.0:
894+
version "2.1.0"
895+
resolved "https://registry.yarnpkg.com/p-any/-/p-any-2.1.0.tgz#719489408e14f5f941a748f1e817f5c71cab35cb"
896+
integrity sha512-JAERcaMBLYKMq+voYw36+x5Dgh47+/o7yuv2oQYuSSUml4YeqJEFznBrY2UeEkoSHqBua6hz518n/PsowTYLLg==
897+
dependencies:
898+
p-cancelable "^2.0.0"
899+
p-some "^4.0.0"
900+
type-fest "^0.3.0"
901+
902+
p-cancelable@^2.0.0:
903+
version "2.0.0"
904+
resolved "https://registry.yarnpkg.com/p-cancelable/-/p-cancelable-2.0.0.tgz#4a3740f5bdaf5ed5d7c3e34882c6fb5d6b266a6e"
905+
integrity sha512-wvPXDmbMmu2ksjkB4Z3nZWTSkJEb9lqVdMaCKpZUGJG9TMiNp9XcbG3fn9fPKjem04fJMJnXoyFPk2FmgiaiNg==
906+
907+
p-some@^4.0.0:
908+
version "4.1.0"
909+
resolved "https://registry.yarnpkg.com/p-some/-/p-some-4.1.0.tgz#28e73bc1e0d62db54c2ed513acd03acba30d5c04"
910+
integrity sha512-MF/HIbq6GeBqTrTIl5OJubzkGU+qfFhAFi0gnTAK6rgEIJIknEiABHOTtQu4e6JiXjIwuMPMUFQzyHh5QjCl1g==
911+
dependencies:
912+
aggregate-error "^3.0.0"
913+
p-cancelable "^2.0.0"
914+
776915
parse-json@^2.2.0:
777916
version "2.2.0"
778917
resolved "https://registry.yarnpkg.com/parse-json/-/parse-json-2.2.0.tgz#f480f40434ef80741f8469099f8dea18f55a4dc9"
@@ -896,6 +1035,11 @@ resolve@^1.0.0:
8961035
dependencies:
8971036
path-parse "^1.0.5"
8981037

1038+
safe-buffer@^5.0.1:
1039+
version "5.2.1"
1040+
resolved "https://registry.yarnpkg.com/safe-buffer/-/safe-buffer-5.2.1.tgz#1eaf9fa9bdb1fdd4ec75f58f9cdb4e6b7827eec6"
1041+
integrity sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ==
1042+
8991043
safe-buffer@~5.1.0, safe-buffer@~5.1.1:
9001044
version "5.1.2"
9011045
resolved "https://registry.yarnpkg.com/safe-buffer/-/safe-buffer-5.1.2.tgz#991ec69d296e0313747d59bdfd2b745c35f8828d"
@@ -904,6 +1048,11 @@ safe-buffer@~5.1.0, safe-buffer@~5.1.1:
9041048
version "5.5.0"
9051049
resolved "https://registry.yarnpkg.com/semver/-/semver-5.5.0.tgz#dc4bbc7a6ca9d916dee5d43516f0092b58f7b8ab"
9061050

1051+
semver@^5.6.0:
1052+
version "5.7.1"
1053+
resolved "https://registry.yarnpkg.com/semver/-/semver-5.7.1.tgz#a954f931aeba508d307bbf069eff0c01c96116f7"
1054+
integrity sha512-sauaDf/PZdVgrLTNYHRtpXa1iRiKcaebiKQ1BJdpQlWH2lCvexQdX55snPFyK7QzpudqbCI0qXFfOasHdyNDGQ==
1055+
9071056
9081057
version "1.1.0"
9091058
resolved "https://registry.yarnpkg.com/setprototypeof/-/setprototypeof-1.1.0.tgz#d0bd85536887b6fe7c0d818cb962d9d91c54e656"
@@ -1012,6 +1161,11 @@ trim-newlines@^1.0.0:
10121161
version "1.0.0"
10131162
resolved "https://registry.yarnpkg.com/trim-newlines/-/trim-newlines-1.0.0.tgz#5887966bb582a4503a41eb524f7d35011815a613"
10141163

1164+
type-fest@^0.3.0:
1165+
version "0.3.1"
1166+
resolved "https://registry.yarnpkg.com/type-fest/-/type-fest-0.3.1.tgz#63d00d204e059474fe5e1b7c011112bbd1dc29e1"
1167+
integrity sha512-cUGJnCdr4STbePCgqNFbpVNCepa+kAVohJs1sLhxzdH+gnEoOd8VhbYa7pD3zZYGiURWM2xzEII3fQcRizDkYQ==
1168+
10151169
type-is@^1.5.5:
10161170
version "1.6.16"
10171171
resolved "https://registry.yarnpkg.com/type-is/-/type-is-1.6.16.tgz#f89ce341541c672b25ee7ae3c73dee3b2be50194"

0 commit comments

Comments
 (0)