From 29ab2d5dfa85d82707802987e54b1b44d456dc0b Mon Sep 17 00:00:00 2001 From: richardo2016 Date: Wed, 17 Apr 2024 22:19:30 +0800 Subject: [PATCH] feat: add option `disable_auto_hex_key`. --- @types/basic.d.ts | 9 +++++++- src/index.ts | 10 +++++---- src/jwt.ts | 23 +++++++++++++-------- test/index.js | 52 +++++++++++++++++++++++++++++++++++------------ 4 files changed, 68 insertions(+), 26 deletions(-) diff --git a/@types/basic.d.ts b/@types/basic.d.ts index 705a3fb..4d55f1f 100644 --- a/@types/basic.d.ts +++ b/@types/basic.d.ts @@ -41,7 +41,14 @@ declare namespace FibSessionNS { cache_size?: number; cache_timeout?: number; } - interface Options extends StoreOptions, FibKvOptions { + type FibJwtOptions = { + /** + * @description if disable_auto_hex_key is set, we would make sure all keys are hex string/Buffer + */ + disable_auto_hex_key?: boolean + } + + interface Options extends StoreOptions, FibKvOptions, FibJwtOptions { expires?: number; } interface Store { diff --git a/src/index.ts b/src/index.ts index 5d77814..7a54eed 100644 --- a/src/index.ts +++ b/src/index.ts @@ -29,9 +29,11 @@ const Session = function (conn: FibKV.FibKVInstance | Class_DbConnection | FibPo // JWT(JSON Web Token) const jwt_algo = utils.jwt_algo(opts); const jwt_key = utils.jwt_key(opts); + const fib_jwt_opts = { disable_auto_hex_key: opts.disable_auto_hex_key }; + if (jwt_algo && jwt_key) { - this.getToken = jwt.getToken(jwt_algo); - this.setTokenCookie = jwt.setTokenCookie(jwt_algo, utils.sid(opts)); + this.getToken = jwt.getToken(jwt_algo, fib_jwt_opts); + this.setTokenCookie = jwt.setTokenCookie(jwt_algo, utils.sid(opts), fib_jwt_opts); } this.cookie_filter = (r: FibSessionNS.HttpRequest) => { @@ -39,7 +41,7 @@ const Session = function (conn: FibKV.FibKVInstance | Class_DbConnection | FibPo r.sessionid = sessionid; if (jwt_algo && jwt_key) { //JWT - jwt.filter(r, jwt_algo, jwt_key, utils.sid(opts), proxy); + jwt.filter(r, jwt_algo, jwt_key, utils.sid(opts), proxy, fib_jwt_opts); } else { let obj = {}; if (!sessionid || util.isEmpty(obj = store.get(sessionid))) { @@ -63,7 +65,7 @@ const Session = function (conn: FibKV.FibKVInstance | Class_DbConnection | FibPo r.sessionid = sessionid || undefined; if (jwt_algo && jwt_key) { - jwt.filter(r, jwt_algo, jwt_key, utils.sid(opts), proxy); + jwt.filter(r, jwt_algo, jwt_key, utils.sid(opts), proxy, fib_jwt_opts); } else { let obj = {}; if (!sessionid || !(obj = store.get(sessionid))) { diff --git a/src/jwt.ts b/src/jwt.ts index 0fa2209..9d0faa5 100644 --- a/src/jwt.ts +++ b/src/jwt.ts @@ -4,9 +4,9 @@ function inputIsBuffer (bufOrString: string | Class_Buffer): bufOrString is Clas return Buffer.isBuffer(bufOrString); } -export function getToken (jwt_algo: string) { +export function getToken (jwt_algo: string, opts?: FibSessionNS.FibJwtOptions) { return (obj: FibSessionNS.Object, key: string | Class_Buffer) => { - if (!inputIsBuffer(key)) + if (!opts?.disable_auto_hex_key && !inputIsBuffer(key)) key = new Buffer(key, 'hex') /** * jws.sign @@ -18,10 +18,10 @@ export function getToken (jwt_algo: string) { } } -export function setTokenCookie (jwt_algo: string, cookie_name: string) { +export function setTokenCookie (jwt_algo: string, cookie_name: string, opts?: FibSessionNS.FibJwtOptions) { return (r: FibSessionNS.HttpRequest, obj: FibSessionNS.Object, key: string | Class_Buffer) => { r.session = obj; - if (!inputIsBuffer(key)) + if (!opts?.disable_auto_hex_key && !inputIsBuffer(key)) key = new Buffer(key, 'hex') r.sessionid = jws.sign({alg: jwt_algo}, obj, key); @@ -34,8 +34,8 @@ export function setTokenCookie (jwt_algo: string, cookie_name: string) { }; } -export function getPayload (text: string, key: string | Class_Buffer, algo: string) { - if (!inputIsBuffer(key)) +export function getPayload (text: string, key: string | Class_Buffer, algo: string, opts?: FibSessionNS.FibJwtOptions) { + if (!opts?.disable_auto_hex_key && !inputIsBuffer(key)) key = new Buffer(key, 'hex') if (jws.verify(text, key, algo)) { @@ -50,10 +50,17 @@ export function getPayload (text: string, key: string | Class_Buffer, algo: stri } } -export function filter (r: FibSessionNS.HttpRequest, jwt_algo: string, jwt_key: string, cookie_name: string, proxy: FibSessionNS.SessionProxyGenerator) { +export function filter ( + r: FibSessionNS.HttpRequest, + jwt_algo: string, + jwt_key: string, + cookie_name: string, + proxy: FibSessionNS.SessionProxyGenerator, + opts?: FibSessionNS.FibJwtOptions +) { let obj; if (r.sessionid) { - obj = getPayload(r.sessionid, jwt_key, jwt_algo); + obj = getPayload(r.sessionid, jwt_key, jwt_algo, opts); } r.session = proxy(null, obj, r.sessionid, true, true); diff --git a/test/index.js b/test/index.js index 71c616e..e10f636 100644 --- a/test/index.js +++ b/test/index.js @@ -57,7 +57,7 @@ function resDataToObj (resData) { function session_test(description, opts, test_opts, _before, _after) { describe(`${description} - ${querystring.stringify(test_opts, null)}`, () => { - var { use_existed_kv = false } = test_opts; + var { use_existed_kv = false, disable_auto_hex_key } = test_opts; before(() => { kv_db = new kv(_before(), opts); @@ -66,9 +66,9 @@ function session_test(description, opts, test_opts, _before, _after) { function setup_session(_opts) { if (use_existed_kv) - session = new Session(kv_db, _opts); + session = new Session(kv_db, {..._opts, disable_auto_hex_key }); else - session = new Session(conn, _opts); + session = new Session(conn, {..._opts, disable_auto_hex_key }); session.setup(); } @@ -997,7 +997,11 @@ function session_test(description, opts, test_opts, _before, _after) { var b = true; for (var i = 0; res.cookies && i < res.cookies.length; i++) { if (res.cookies[i] && res.cookies[i].name == 'sessionID') { - assert.equal(res.cookies[i].value, 'eyJhbGciOiJIUzI1NiJ9.eyJpZCI6MTIzNDUsIm5hbWUiOiJGcmFuayJ9.adE0u7POp1NG1GHQjZUGb9lfovw9-GdEVusqh2Sc0-M'); + if (disable_auto_hex_key) { + assert.equal(res.cookies[i].value, 'eyJhbGciOiJIUzI1NiJ9.eyJpZCI6MTIzNDUsIm5hbWUiOiJGcmFuayJ9.AeI5krHDMPiNFc4IikrdrYbm9qdsDwdz8p1X9GwADEE'); + } else { + assert.equal(res.cookies[i].value, 'eyJhbGciOiJIUzI1NiJ9.eyJpZCI6MTIzNDUsIm5hbWUiOiJGcmFuayJ9.adE0u7POp1NG1GHQjZUGb9lfovw9-GdEVusqh2Sc0-M'); + } b = false; } } @@ -1021,7 +1025,11 @@ function session_test(description, opts, test_opts, _before, _after) { var jwt_token = session.getToken({ abc: 'xyz' }, 'test'); - assert.equal(jwt_token, 'eyJhbGciOiJIUzI1NiJ9.eyJhYmMiOiJ4eXoifQ.ltcUVSz3Np3ZSLpk7TwtTFFjlNY8X2nikCGcuF2ZMgE') + if (disable_auto_hex_key) { + assert.equal(jwt_token, 'eyJhbGciOiJIUzI1NiJ9.eyJhYmMiOiJ4eXoifQ.qiVRBz9pUjJUDBO6-083u1wCyGxzFJ6B0USk8iSrEUE') + } else { + assert.equal(jwt_token, 'eyJhbGciOiJIUzI1NiJ9.eyJhYmMiOiJ4eXoifQ.ltcUVSz3Np3ZSLpk7TwtTFFjlNY8X2nikCGcuF2ZMgE') + } }); }); describe('api in JWT', function () { @@ -1101,7 +1109,11 @@ function session_test(description, opts, test_opts, _before, _after) { let res = new http.Client().get(url.host + '/user?id=50&username=hoo'); save_id = res.cookies[0].value; //console.error('save_id:', res.cookies[0].value); - assert.equal(save_id, 'eyJhbGciOiJIUzI1NiJ9.eyJpZCI6IjUwIiwidXNlcm5hbWUiOiJob28ifQ.ubTia0QE_D-aT8ziMShJEwgnbujatqTJC7amOhxabzw'); + if (disable_auto_hex_key) { + assert.equal(save_id, 'eyJhbGciOiJIUzI1NiJ9.eyJpZCI6IjUwIiwidXNlcm5hbWUiOiJob28ifQ.W3sB7wnqxIPxhLuxE2qLWWO5aCY8O2F6sIWA05u9B-Q'); + } else { + assert.equal(save_id, 'eyJhbGciOiJIUzI1NiJ9.eyJpZCI6IjUwIiwidXNlcm5hbWUiOiJob28ifQ.ubTia0QE_D-aT8ziMShJEwgnbujatqTJC7amOhxabzw'); + } assert.deepEqual(request_session, { "id": "50", "username": "hoo" @@ -1113,7 +1125,12 @@ function session_test(description, opts, test_opts, _before, _after) { } }); //console.error('save_id2:', res.cookies[0].value); - assert.equal(request_sessionid, 'eyJhbGciOiJIUzI1NiJ9.eyJpZCI6IjgiLCJ1c2VybmFtZSI6Imxpb24ifQ.bN9IiVDgy2qfQgndBv5SfyLSEotTw1RjK3hgjR-VJpM'); + + if (disable_auto_hex_key) { + assert.equal(request_sessionid, 'eyJhbGciOiJIUzI1NiJ9.eyJpZCI6IjgiLCJ1c2VybmFtZSI6Imxpb24ifQ.aKU95JiljVGiJiw5OU4PmIk6Vm6wJoIrkXBSDbeCmac') + } else { + assert.equal(request_sessionid, 'eyJhbGciOiJIUzI1NiJ9.eyJpZCI6IjgiLCJ1c2VybmFtZSI6Imxpb24ifQ.bN9IiVDgy2qfQgndBv5SfyLSEotTw1RjK3hgjR-VJpM'); + } assert.deepEqual(request_session, { "id": "8", "username": "lion" @@ -1145,7 +1162,11 @@ function session_test(description, opts, test_opts, _before, _after) { let client = new http.Client(); let res = client.get(url.host + '/user?id=8&username=lion'); save_id = res.cookies[0].value; - assert.equal(save_id, 'eyJhbGciOiJIUzI1NiJ9.eyJpZCI6IjgiLCJ1c2VybmFtZSI6Imxpb24ifQ.bN9IiVDgy2qfQgndBv5SfyLSEotTw1RjK3hgjR-VJpM'); + if (disable_auto_hex_key) { + assert.equal(save_id, 'eyJhbGciOiJIUzI1NiJ9.eyJpZCI6IjgiLCJ1c2VybmFtZSI6Imxpb24ifQ.aKU95JiljVGiJiw5OU4PmIk6Vm6wJoIrkXBSDbeCmac') + } else { + assert.equal(save_id, 'eyJhbGciOiJIUzI1NiJ9.eyJpZCI6IjgiLCJ1c2VybmFtZSI6Imxpb24ifQ.bN9IiVDgy2qfQgndBv5SfyLSEotTw1RjK3hgjR-VJpM'); + } assert.equal(request_sessionid, save_id); assert.equal(request_session.username, 'lion'); res = client.get(url.host + '/get', { @@ -1153,7 +1174,11 @@ function session_test(description, opts, test_opts, _before, _after) { sessionID: save_id } }); - assert.equal(request_sessionid, 'eyJhbGciOiJIUzI1NiJ9.eyJpZCI6IjgiLCJ1c2VybmFtZSI6Imxpb24ifQ.bN9IiVDgy2qfQgndBv5SfyLSEotTw1RjK3hgjR-VJpM'); + if (disable_auto_hex_key) { + assert.equal(request_sessionid, 'eyJhbGciOiJIUzI1NiJ9.eyJpZCI6IjgiLCJ1c2VybmFtZSI6Imxpb24ifQ.aKU95JiljVGiJiw5OU4PmIk6Vm6wJoIrkXBSDbeCmac') + } else { + assert.equal(request_sessionid, 'eyJhbGciOiJIUzI1NiJ9.eyJpZCI6IjgiLCJ1c2VybmFtZSI6Imxpb24ifQ.bN9IiVDgy2qfQgndBv5SfyLSEotTw1RjK3hgjR-VJpM'); + } assert.equal(request_session.username, 'lion'); assert.equal(JSON.parse(res.data.toString()).username, 'lion'); assert.deepEqual(session.get(request_sessionid), {}); @@ -1255,8 +1280,9 @@ function session_test(description, opts, test_opts, _before, _after) { } ;[ - { use_existed_kv: true }, - { use_existed_kv: false }, + // { use_existed_kv: true }, + { use_existed_kv: true, disable_auto_hex_key: true }, + // { use_existed_kv: false }, ].forEach((test_opts) => { session_test( 'SQLite', { @@ -1318,5 +1344,5 @@ function session_test(description, opts, test_opts, _before, _after) { }); }); -const hr = test.run(console.DEBUG); -process.exit(hr); \ No newline at end of file +test.run(console.DEBUG); +process.exit(); \ No newline at end of file