From 2dc4636296cb8007498678dc249b961e93ecab4f Mon Sep 17 00:00:00 2001 From: Jonasz Bigda Date: Sat, 21 Nov 2020 19:21:41 +0100 Subject: [PATCH] Implementation of refresh tokens. new route .../user/refreshtoken --- README.md | 8 +++ node_modules/cookie/HISTORY.md | 5 ++ node_modules/cookie/README.md | 4 ++ node_modules/cookie/index.js | 6 ++- node_modules/cookie/package.json | 87 ++++++++++++++++++++++---------- package-lock.json | 25 +++++---- package.json | 1 + routes/routeUser.js | 18 +++++-- services/services.js | 9 ++-- 9 files changed, 116 insertions(+), 47 deletions(-) diff --git a/README.md b/README.md index 329253d..43d8444 100644 --- a/README.md +++ b/README.md @@ -198,6 +198,14 @@
+- ### **/user/refreshtoken** + + - #### **POST** + + Takes no parameters as it reads the **refreshToken** from a cookie. If refresh token is valid, then returns new auth token in a header and sets new refresh token cookie. **500** on error. + +
+ * ### **/user/register** - #### **POST** diff --git a/node_modules/cookie/HISTORY.md b/node_modules/cookie/HISTORY.md index da2bf24..ce080e0 100644 --- a/node_modules/cookie/HISTORY.md +++ b/node_modules/cookie/HISTORY.md @@ -1,3 +1,8 @@ +0.4.1 / 2020-04-21 +================== + + * Fix `maxAge` option to reject invalid values + 0.4.0 / 2019-05-15 ================== diff --git a/node_modules/cookie/README.md b/node_modules/cookie/README.md index 857fb77..18b2c2c 100644 --- a/node_modules/cookie/README.md +++ b/node_modules/cookie/README.md @@ -10,6 +10,10 @@ Basic HTTP cookie parser and serializer for HTTP servers. ## Installation +This is a [Node.js](https://nodejs.org/en/) module available through the +[npm registry](https://www.npmjs.com/). Installation is done using the +[`npm install` command](https://docs.npmjs.com/getting-started/installing-npm-packages-locally): + ```sh $ npm install cookie ``` diff --git a/node_modules/cookie/index.js b/node_modules/cookie/index.js index 16f56c0..760f32e 100644 --- a/node_modules/cookie/index.js +++ b/node_modules/cookie/index.js @@ -120,7 +120,11 @@ function serialize(name, val, options) { if (null != opt.maxAge) { var maxAge = opt.maxAge - 0; - if (isNaN(maxAge)) throw new Error('maxAge should be a Number'); + + if (isNaN(maxAge) || !isFinite(maxAge)) { + throw new TypeError('option maxAge is invalid') + } + str += '; Max-Age=' + Math.floor(maxAge); } diff --git a/node_modules/cookie/package.json b/node_modules/cookie/package.json index 553eb59..08ed28f 100644 --- a/node_modules/cookie/package.json +++ b/node_modules/cookie/package.json @@ -1,24 +1,54 @@ { - "name": "cookie", - "description": "HTTP server cookie parsing and serialization", - "version": "0.4.0", - "author": "Roman Shtylman ", + "_from": "cookie", + "_id": "cookie@0.4.1", + "_inBundle": false, + "_integrity": "sha512-ZwrFkGJxUR3EIoXtO+yVE69Eb7KlixbaeAWfBQB9vVsNn/o+Yw69gBWSSDK825hQNdN+wF8zELf3dFNl/kxkUA==", + "_location": "/cookie", + "_phantomChildren": {}, + "_requested": { + "type": "tag", + "registry": true, + "raw": "cookie", + "name": "cookie", + "escapedName": "cookie", + "rawSpec": "", + "saveSpec": null, + "fetchSpec": "latest" + }, + "_requiredBy": [ + "#USER", + "/" + ], + "_resolved": "https://registry.npmjs.org/cookie/-/cookie-0.4.1.tgz", + "_shasum": "afd713fe26ebd21ba95ceb61f9a8116e50a537d1", + "_spec": "cookie", + "_where": "C:\\Users\\Jonasz\\Desktop\\Menui\\menui_backend", + "author": { + "name": "Roman Shtylman", + "email": "shtylman@gmail.com" + }, + "bugs": { + "url": "https://github.com/jshttp/cookie/issues" + }, + "bundleDependencies": false, "contributors": [ - "Douglas Christopher Wilson " + { + "name": "Douglas Christopher Wilson", + "email": "doug@somethingdoug.com" + } ], - "license": "MIT", - "keywords": [ - "cookie", - "cookies" - ], - "repository": "jshttp/cookie", + "deprecated": false, + "description": "HTTP server cookie parsing and serialization", "devDependencies": { "beautify-benchmark": "0.2.4", "benchmark": "2.1.4", - "eslint": "5.16.0", - "eslint-plugin-markdown": "1.0.0", - "istanbul": "0.4.5", - "mocha": "6.1.4" + "eslint": "6.8.0", + "eslint-plugin-markdown": "1.0.2", + "mocha": "7.1.1", + "nyc": "15.0.1" + }, + "engines": { + "node": ">= 0.6" }, "files": [ "HISTORY.md", @@ -26,19 +56,24 @@ "README.md", "index.js" ], - "engines": { - "node": ">= 0.6" + "homepage": "https://github.com/jshttp/cookie#readme", + "keywords": [ + "cookie", + "cookies" + ], + "license": "MIT", + "name": "cookie", + "repository": { + "type": "git", + "url": "git+https://github.com/jshttp/cookie.git" }, "scripts": { "bench": "node benchmark/index.js", "lint": "eslint --plugin markdown --ext js,md .", - "test": "mocha --reporter spec --bail --check-leaks test/", - "test-ci": "istanbul cover node_modules/mocha/bin/_mocha --report lcovonly -- --reporter spec --check-leaks test/", - "test-cov": "istanbul cover node_modules/mocha/bin/_mocha -- --reporter dot --check-leaks test/", + "test": "mocha --reporter spec --bail --check-leaks --ui qunit test/", + "test-ci": "nyc --reporter=text npm test", + "test-cov": "nyc --reporter=html --reporter=text npm test", "version": "node scripts/version-history.js && git add HISTORY.md" - } - -,"_resolved": "https://registry.npmjs.org/cookie/-/cookie-0.4.0.tgz" -,"_integrity": "sha512-+Hp8fLp57wnUSt0tY0tHEXh4voZRDnoIrZPqlo3DPiI4y9lwg/jqx+1Om94/W6ZaPDOUbnjOt/99w66zk+l1Xg==" -,"_from": "cookie@0.4.0" -} \ No newline at end of file + }, + "version": "0.4.1" +} diff --git a/package-lock.json b/package-lock.json index 5a3f73c..34fb3d4 100644 --- a/package-lock.json +++ b/package-lock.json @@ -2037,9 +2037,9 @@ "dev": true }, "aws-sdk": { - "version": "2.789.0", - "resolved": "https://registry.npmjs.org/aws-sdk/-/aws-sdk-2.789.0.tgz", - "integrity": "sha512-Jqq+M4N0EgkyS4OPf05UHa7IWUcpuBdnpwMRgBnu4Ju6PxpOTh1UQcmYepVmIN3m6YVpLwFctEYzAMJFM3LT1A==", + "version": "2.797.0", + "resolved": "https://registry.npmjs.org/aws-sdk/-/aws-sdk-2.797.0.tgz", + "integrity": "sha512-fFc/2Xr7NkSXlZ9+2rCOFovA9NO1OnIyEaJFVwMM9gaqzucwRAfNNT0Pa1Kua5dhWrcf/mX0Z4mCDnTBf0/5mA==", "requires": { "buffer": "4.9.2", "events": "1.1.1", @@ -2307,9 +2307,9 @@ } }, "base64-js": { - "version": "1.5.0", - "resolved": "https://registry.npmjs.org/base64-js/-/base64-js-1.5.0.tgz", - "integrity": "sha512-Jrdy04F2EKcNggUDfubMUPNAZg2vMquLQSm8sKLYJvz40ClFL1S8GKyDshGkNsbNNE5Z+fQavzU7nSK1I9JUGA==" + "version": "1.5.1", + "resolved": "https://registry.npmjs.org/base64-js/-/base64-js-1.5.1.tgz", + "integrity": "sha512-AKpaYlHn8t4SVbOHCy+b5+KKgvR4vrsD8vbvrbiQJps7fKDTkjkDry6ji0rUJjC0kzbNePLwzxq8iypo41qeWA==" }, "bcrypt-pbkdf": { "version": "1.0.2", @@ -2790,9 +2790,9 @@ } }, "cookie": { - "version": "0.4.0", - "resolved": "https://registry.npmjs.org/cookie/-/cookie-0.4.0.tgz", - "integrity": "sha512-+Hp8fLp57wnUSt0tY0tHEXh4voZRDnoIrZPqlo3DPiI4y9lwg/jqx+1Om94/W6ZaPDOUbnjOt/99w66zk+l1Xg==" + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/cookie/-/cookie-0.4.1.tgz", + "integrity": "sha512-ZwrFkGJxUR3EIoXtO+yVE69Eb7KlixbaeAWfBQB9vVsNn/o+Yw69gBWSSDK825hQNdN+wF8zELf3dFNl/kxkUA==" }, "cookie-signature": { "version": "1.0.6", @@ -3360,6 +3360,13 @@ "type-is": "~1.6.18", "utils-merge": "1.0.1", "vary": "~1.1.2" + }, + "dependencies": { + "cookie": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/cookie/-/cookie-0.4.0.tgz", + "integrity": "sha512-+Hp8fLp57wnUSt0tY0tHEXh4voZRDnoIrZPqlo3DPiI4y9lwg/jqx+1Om94/W6ZaPDOUbnjOt/99w66zk+l1Xg==" + } } }, "express-rate-limit": { diff --git a/package.json b/package.json index 1399bef..c37dbac 100644 --- a/package.json +++ b/package.json @@ -15,6 +15,7 @@ "axios": "^0.20.0", "bcryptjs": "^2.4.3", "body-parser": "^1.19.0", + "cookie": "^0.4.1", "cors": "^2.8.5", "dotenv": "^8.2.0", "esm": "^3.2.25", diff --git a/routes/routeUser.js b/routes/routeUser.js index 894d325..f555c86 100644 --- a/routes/routeUser.js +++ b/routes/routeUser.js @@ -19,6 +19,7 @@ const { validateRefreshToken, } = require("../services/services.js"); const { resetPassword } = require("../services/mailServices.js"); +const cookie = require("cookie"); var router = express.Router(); @@ -32,18 +33,25 @@ router.post("/login", async (req, res) => { await checkPassword(req.body.password, user.password); const safeUser = await prepareSafeUser(user); var token = generateAuthToken(safeUser); - var refreshToken = generateRefreshToken(user._id); - res.header("x-auth-token", token).header("ref", refreshToken).status(202).send(safeUser); + var refreshToken = generateRefreshToken(user); + res.header("x-auth-token", token) + .header("Set-Cookie", cookie.serialize("refreshToken", refreshToken, { httpOnly: true })) + .status(202).send(safeUser); } catch (error) { handleError(error, res); } }); //REFRESH_TOKEN -router.post("refreshtoken", async (req, res) => { +router.post("/refreshtoken", async (req, res) => { try { - const refreshToken = req.headers["ref"]; - validateRefreshToken(refreshToken); + const cookies = cookie.parse(req.headers.cookie); + const user = validateRefreshToken(cookies.refreshToken); + const newAccessToken = generateAuthToken(user); + const newRefreshToken = generateRefreshToken(user); + res.header("x-auth-token", newAccessToken) + .header("Set-Cookie", cookie.serialize("refreshToken", newRefreshToken, { httpOnly: true })) + .status(202).send("Auth token refreshed."); } catch (error) { handleError(error, res); } diff --git a/services/services.js b/services/services.js index 396e0fd..e9f0512 100644 --- a/services/services.js +++ b/services/services.js @@ -47,11 +47,7 @@ function generateAuthToken(user) { const token = jwt.sign( { email: user.email, - firstname: user.firstname, - lastname: user.lastname, - billing: user.billing, id: user.id, - restaurants: user.restaurants, }, jwtSecret, { expiresIn: "15m" } @@ -59,9 +55,10 @@ function generateAuthToken(user) { return token; } -function generateRefreshToken(userId) { +function generateRefreshToken(user) { const token = jwt.sign({ - id: userId + email: user.email, + id: user.id, }, jwtSecret, { expiresIn: "1h" });