diff --git a/.env b/.env index 259d7ec..6aeabba 100644 --- a/.env +++ b/.env @@ -4,11 +4,19 @@ NODE_ENV=production PORT=3001 -# REACT_APP_API_URL=http://localhost:3001 -REACT_APP_API_URL='https://mm-code-api-b4f2aff44087.herokuapp.com' +REACT_APP_API_URL=http://localhost:3001 +# REACT_APP_API_URL='https://mm-code-api-b4f2aff44087.herokuapp.com' REACT_APP_SECRET_KEY=abcdef123456 -# Client_SIDE_BASE_URL=http://localhost:3000 -Client_SIDE_BASE_URL=https://www.mmcode.io \ No newline at end of file +Client_SIDE_BASE_URL="http://localhost:3000" +# Client_SIDE_BASE_URL=https://www.mmcode.io + +GOOGLE_CLIENT_SECRET="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" +GOOGLE_CLIENT_ID="617409105699-u5senri6ujm3b655n5gkb0g6f7r8r5j1.apps.googleusercontent.com" + +GITHUB_CLIENT_ID="613427a2df3476638f43" +GITHUB_CLIENT_SECRET="417c54c316a47b3ead02087f71bce99b75c856bf" + +SECRET_KEY=melly diff --git a/.gitignore b/.gitignore index 40b878d..713d500 100644 --- a/.gitignore +++ b/.gitignore @@ -1 +1,2 @@ -node_modules/ \ No newline at end of file +node_modules/ +.env diff --git a/Auth/auth.js b/Auth/auth.js index 81b507c..29e4b08 100644 --- a/Auth/auth.js +++ b/Auth/auth.js @@ -1,8 +1,7 @@ const passport = require('passport'); -const GoogleStrategy = require('./googleStrategy'); // Import the exported Google strategy -const githubStrategy = require('./githubStrategy'); // Import the exported GitHub strategy +const GoogleStrategy = require('./googleStrategy'); +const githubStrategy = require('./githubStrategy'); -// Use the Google and GitHub strategies with their respective names passport.use('google', GoogleStrategy); passport.use('github', githubStrategy); @@ -15,5 +14,4 @@ passport.serializeUser(function(user, done) { passport.deserializeUser(function(user, done) { done(null, user); }); -// Export the configured passport module.exports = passport; diff --git a/Auth/githubStrategy.js b/Auth/githubStrategy.js index 797fe90..40c8efc 100644 --- a/Auth/githubStrategy.js +++ b/Auth/githubStrategy.js @@ -6,7 +6,7 @@ const db = require('../config/db/db'); // Import your database configuration const githubStrategy = new GitHubStrategy({ clientID: process.env.GITHUB_CLIENT_ID, clientSecret: process.env.GITHUB_CLIENT_SECRET, - callbackURL: `https://mm-code-api-b4f2aff44087.herokuapp.com/auth/github/callback`, + callbackURL: `${process.env.REACT_APP_API_URL}/auth/github/callback`, scope: ['user:email'], }, async function (accessToken, refreshToken, profile, done) { diff --git a/Auth/googleStrategy.js b/Auth/googleStrategy.js index b05a357..58dd9dd 100644 --- a/Auth/googleStrategy.js +++ b/Auth/googleStrategy.js @@ -1,10 +1,14 @@ const GoogleStrategy = require('passport-google-oauth20').Strategy; const db = require('../config/db/db'); // Import your database configuration +const passport = require('passport'); + + + const googleStrategy = new GoogleStrategy({ clientID: process.env.GOOGLE_CLIENT_ID, clientSecret: process.env.GOOGLE_CLIENT_SECRET, - callbackURL: `https://mm-code-api-b4f2aff44087.herokuapp.com/auth/google/callback`, + callbackURL: `${process.env.REACT_APP_API_URL}/auth/google/callback`, passReqToCallback: true, }, function (request, accessToken, refreshToken, profile, done) { @@ -18,7 +22,7 @@ const googleStrategy = new GoogleStrategy({ if (result.rows.length === 0) { const insertUserQuery = 'INSERT INTO users (full_name, email, accounts) VALUES ($1, $2, $3)'; - const insertUserValues = [profile.displayName, profile.emails[0].value, 'Google']; // Set the account provider to 'Google' + const insertUserValues = [profile.displayName, profile.emails[0].value, 'Google']; db.query(insertUserQuery, insertUserValues, (err) => { if (err) { diff --git a/app/app.js b/app/app.js index c737c5e..68f4074 100644 --- a/app/app.js +++ b/app/app.js @@ -7,23 +7,22 @@ const passport = require('passport'); const morgan = require('morgan'); const bodyParser = require('body-parser'); require('dotenv').config(); +const session = require('express-session'); const authRoutes = require('../app/routes/authRoutes'); const githubRoutes = require('../app/routes/githubRoutes'); -const googleRoutes = require('../app/routes/googleRoute'); // Replace with the correct path to your Google OAuth route file - +const googleRoutes = require('../app/routes/googleRoute'); const GoogleStrategy = require('../Auth/googleStrategy'); const GithubStrategy = require('../Auth/githubStrategy'); passport.use(GoogleStrategy); - passport.use(GithubStrategy); app.set('view engine', 'ejs'); app.use(cookieParser()); app.use( cors({ - origin: 'https://www.mmcode.io', + origin: ["https://www.mmcode.io"], methods: ['GET', 'POST'], credentials: true, }) @@ -42,22 +41,30 @@ app.use( secure: true, }) ); + app.set('trust proxy', 1); + + app.use(passport.initialize()); app.use(passport.session()); -passport.serializeUser((user, done) => { - // Serialize the user to the session +passport.serializeUser(function(user, done) { done(null, user); }); -passport.deserializeUser((user, done) => { - // Deserialize the user from the session - done(null, user); +passport.deserializeUser(function(id, done) { + User.findById(id, function(err, user) { + done(err, user); + }); }); - app.use('/', authRoutes); app.use('/', githubRoutes); app.use('/', googleRoutes); + +app.use((err, req, res, next) => { + console.error(err.stack); + res.status(500).send('Something went wrong!'); +}); + module.exports = app; diff --git a/app/controllers/authController.js b/app/controllers/authController.js index 9e0b596..c300b56 100644 --- a/app/controllers/authController.js +++ b/app/controllers/authController.js @@ -1,4 +1,4 @@ -const db = require('../../config/db/db'); + function platform(req, res) { req.session.randomValue = Math.random(); const storedRandomValue = req.session.randomValue; @@ -9,55 +9,16 @@ function platform(req, res) { function homePage(req, res) { res.send("Home page running well.") -} -function getUser(req, res) { - if (req.isAuthenticated()) { - const userId = req.user.id; // Assuming you have a unique identifier for users - db.query('SELECT full_name, email FROM users WHERE id = $1', [userId]) - .then(result => { - if (result.rows.length === 0) { - // User not found in the database, use backup method - const userData = { - displayName: req.user.displayName || req.user.username, // Use username if displayName is not available - email: req.user.email, - }; - req.session.userData = userData; - res.json(userData); - } else { - // User found in the database - const userData = { - displayName: result.rows[0].full_name, - email: result.rows[0].email, - }; - req.session.userData = userData; - res.json(userData); - } - }) - .catch(error => { - console.error('Error fetching user data from the database:', error); - res.status(500).json({ error: 'Internal server error' }); - }); - } else { - res.status(401).json({ error: 'Not authenticated' }); - } } -function checkSession(req, res) { - try { - if (req.isAuthenticated()) { - res.sendStatus(200); - } else { - res.sendStatus(401); - } - } catch (e) { - return res.status(500).json({ msg: "Error found" }); - } -} + + function logout(req, res) { + res.clearCookie('token'); req.logout(); res.status(200).json({ success : true }); } @@ -65,7 +26,5 @@ function logout(req, res) { module.exports = { homePage, platform, - getUser, - checkSession, logout, }; diff --git a/app/controllers/googleController.js b/app/controllers/googleController.js index 342d4c2..1882bd1 100644 --- a/app/controllers/googleController.js +++ b/app/controllers/googleController.js @@ -1,22 +1,38 @@ const passport = require("passport"); +const jwt = require('jsonwebtoken'); +const secretKey = process.env.SECRET_KEY; -// Google OAuth authentication function googleAuth(req, res) { passport.authenticate('google', { scope: ['email', 'profile'] })(req, res); } -// Callback after Google OAuth authentication function googleCallback(req, res, next) { passport.authenticate('google', { successRedirect: `${process.env.Client_SIDE_BASE_URL}/platform`, failureRedirect: '/auth/google/failure' + }, (err, user) => { + if (err) { + return next(err); + } + if (!user) { + return res.redirect(`${process.env.Client_SIDE_BASE_URL}/login`); + } + + const token = jwt.sign(user, secretKey, { expiresIn: '24h' }); + + res.cookie('token', token, { + httpOnly: true, + secure: process.env.NODE_ENV === 'production', + maxAge: 24 * 60 * 60 * 1000, + sameSite: 'none', + }); + + return res.redirect(`${process.env.Client_SIDE_BASE_URL}/platform`); })(req, res, next); } -// Failure route function googleFailure(req, res) { res.redirect(`${process.env.Client_SIDE_BASE_URL}/login`); - // Note: You should not use `res.send` after `res.redirect` as it will not be executed. } module.exports = { diff --git a/app/controllers/tokens.js b/app/controllers/tokens.js new file mode 100644 index 0000000..bf5d77f --- /dev/null +++ b/app/controllers/tokens.js @@ -0,0 +1,29 @@ +const jwt = require('jsonwebtoken'); + +const secretKey = process.env.SECRET_KEY; + +function generateToken(user) { + const token = jwt.sign({ user }, secretKey, { expiresIn: '24h' }); + return token; +} + +function verifyToken(req, res, next) { + const token = req.header('Authorization'); + + if (!token) { + return res.status(401).json({ error: 'Access denied. No token provided.' }); + } + + try { + const decoded = jwt.verify(token, secretKey); + req.user = decoded; + next(); + } catch (error) { + return res.status(403).json({ error: 'Invalid token.' }); + } +} + +module.exports = { + generateToken, + verifyToken, +}; diff --git a/app/routes/authRoutes.js b/app/routes/authRoutes.js index edb013a..92ffe1c 100644 --- a/app/routes/authRoutes.js +++ b/app/routes/authRoutes.js @@ -1,13 +1,52 @@ const express = require('express'); const router = express.Router(); const authController = require('../controllers/authController'); -// const { isLoggedIn } = require('../middleware/authenticationMiddleware'); +const jwt = require('jsonwebtoken'); +const secretKey = process.env.SECRET_KEY; + +router.get('/', authController.homePage); -router.get('/', authController.homePage) router.get('/platform', authController.platform); -router.get('/user', authController.getUser); -// router.get('/protected', isLoggedIn, authController.protected); -router.get('/check-session', authController.checkSession) + +router.get('/user', (req, res) => { + const token = req.cookies.token; + + if (!token) { + return res.status(401).json({ error: 'Unauthorized' }); + } + + try { + const decoded = jwt.verify(token, secretKey ); + const userData = { + displayName: decoded.displayName || decoded.username || decoded.fullName, + email: decoded.email, + }; + + res.json({ message: 'User authenticated', userData }); + } catch (error) { + console.error('Authentication Error:', error); + res.status(401).json({ error: 'Unauthorized' }); + } +}); + +router.get('/checkSession', (req, res) => { + const token = req.cookies.token; + + if (!token) { + return res.status(401).json({ error: 'Unauthorized' }); + } + + const decodedToken = jwt.verify(token, secretKey ); + + if (!decodedToken) { + return res.status(401).json({ error: 'Unauthorized' }); + } + + return res.status(200).json({ message: 'User is authenticated' }); +}) + router.get('/logout', authController.logout); module.exports = router; + + diff --git a/app/routes/googleRoute.js b/app/routes/googleRoute.js index 1cbd2ac..f366a27 100644 --- a/app/routes/googleRoute.js +++ b/app/routes/googleRoute.js @@ -2,9 +2,11 @@ const express = require('express'); const router = express.Router(); const googleController = require('../controllers/googleController'); const authenticationMiddleware = require('../middleware/authenticationMiddleware'); +const passport = require('passport'); router.get('/auth/google', googleController.googleAuth); router.get('/auth/google/callback', googleController.googleCallback); -router.get('/auth/google/failure', authenticationMiddleware.isLoggedIn, googleController.googleFailure); +router.get('/auth/google/failure', googleController.googleFailure); module.exports = router; + \ No newline at end of file diff --git a/config/db/db.js b/config/db/db.js index 90902c4..434e672 100644 --- a/config/db/db.js +++ b/config/db/db.js @@ -1,6 +1,5 @@ const { Pool } = require('pg'); -// Create a new instance of the Pool class const pool = new Pool({ connectionString: 'postgres://hzxxyodc:lx9EgngCHzM-uAX0GnOpdwrZXX4vsSe5@surus.db.elephantsql.com/hzxxyodc', ssl: { @@ -8,10 +7,8 @@ const pool = new Pool({ } }); -// Test the connection to the database pool.query('SELECT NOW()') .then(res => console.log('Database for users connected! Current time: ', res.rows[0].now)) .catch(err => console.error('Database connection error: ', err.stack)); - -// Export the pool object for use in other modules + module.exports = pool; diff --git a/config/passport.js b/config/passport.js deleted file mode 100644 index e69de29..0000000 diff --git a/node_modules/.package-lock.json b/node_modules/.package-lock.json index a8b1334..99bccbb 100644 --- a/node_modules/.package-lock.json +++ b/node_modules/.package-lock.json @@ -935,6 +935,19 @@ "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", "integrity": "sha512-OO0pH2lK6a0hZnAdau5ItzHPI6pUlvI7jMVnxUQRtw4owF2wk8lOSabtGDCTP4Ggrg2MbGnWO9X8K1t4+fGMDw==" }, + "node_modules/fsevents": { + "version": "2.3.2", + "resolved": "https://registry.npmjs.org/fsevents/-/fsevents-2.3.2.tgz", + "integrity": "sha512-xiqMQR4xAeHTuB9uWm+fFRcIOgKBMiOBP+eXiyT7jsgVCq1bkVygt00oASowB7EdtpOHaaPgKt812P9ab+DDKA==", + "hasInstallScript": true, + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": "^8.16.0 || ^10.6.0 || >=11.0.0" + } + }, "node_modules/function-bind": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.1.tgz", @@ -1355,14 +1368,20 @@ } }, "node_modules/jsonwebtoken": { - "version": "9.0.1", - "resolved": "https://registry.npmjs.org/jsonwebtoken/-/jsonwebtoken-9.0.1.tgz", - "integrity": "sha512-K8wx7eJ5TPvEjuiVSkv167EVboBDv9PZdDoF7BgeQnBLVvZWW9clr2PsQHVJDTKaEIH5JBIwHujGcHp7GgI2eg==", + "version": "9.0.2", + "resolved": "https://registry.npmjs.org/jsonwebtoken/-/jsonwebtoken-9.0.2.tgz", + "integrity": "sha512-PRp66vJ865SSqOlgqS8hujT5U4AOgMfhrwYIuIhfKaoSCZcirrmASQr8CX7cUg+RMih+hgznrjp99o+W4pJLHQ==", "dependencies": { "jws": "^3.2.2", - "lodash": "^4.17.21", + "lodash.includes": "^4.3.0", + "lodash.isboolean": "^3.0.3", + "lodash.isinteger": "^4.0.4", + "lodash.isnumber": "^3.0.3", + "lodash.isplainobject": "^4.0.6", + "lodash.isstring": "^4.0.1", + "lodash.once": "^4.0.0", "ms": "^2.1.1", - "semver": "^7.3.8" + "semver": "^7.5.4" }, "engines": { "node": ">=12", @@ -1404,10 +1423,40 @@ "node": ">= 0.6" } }, - "node_modules/lodash": { - "version": "4.17.21", - "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.21.tgz", - "integrity": "sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg==" + "node_modules/lodash.includes": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/lodash.includes/-/lodash.includes-4.3.0.tgz", + "integrity": "sha512-W3Bx6mdkRTGtlJISOvVD/lbqjTlPPUDTMnlXZFnVwi9NKJ6tiAk6LVdlhZMm17VZisqhKcgzpO5Wz91PCt5b0w==" + }, + "node_modules/lodash.isboolean": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/lodash.isboolean/-/lodash.isboolean-3.0.3.tgz", + "integrity": "sha512-Bz5mupy2SVbPHURB98VAcw+aHh4vRV5IPNhILUCsOzRmsTmSQ17jIuqopAentWoehktxGd9e/hbIXq980/1QJg==" + }, + "node_modules/lodash.isinteger": { + "version": "4.0.4", + "resolved": "https://registry.npmjs.org/lodash.isinteger/-/lodash.isinteger-4.0.4.tgz", + "integrity": "sha512-DBwtEWN2caHQ9/imiNeEA5ys1JoRtRfY3d7V9wkqtbycnAmTvRRmbHKDV4a0EYc678/dia0jrte4tjYwVBaZUA==" + }, + "node_modules/lodash.isnumber": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/lodash.isnumber/-/lodash.isnumber-3.0.3.tgz", + "integrity": "sha512-QYqzpfwO3/CWf3XP+Z+tkQsfaLL/EnUlXWVkIk5FUPc4sBdTehEqZONuyRt2P67PXAk+NXmTBcc97zw9t1FQrw==" + }, + "node_modules/lodash.isplainobject": { + "version": "4.0.6", + "resolved": "https://registry.npmjs.org/lodash.isplainobject/-/lodash.isplainobject-4.0.6.tgz", + "integrity": "sha512-oSXzaWypCMHkPC3NvBEaPHf0KsA5mvPrOPgQWDsbg8n7orZ290M0BmC/jgRZ4vcJ6DTAhjrsSYgdsW/F+MFOBA==" + }, + "node_modules/lodash.isstring": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/lodash.isstring/-/lodash.isstring-4.0.1.tgz", + "integrity": "sha512-0wJxfxH1wgO3GrbuP+dTTk7op+6L41QCXbGINEmD+ny/G/eCqGzxyCsh7159S+mgDDcoarnBw6PC1PS5+wUGgw==" + }, + "node_modules/lodash.once": { + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/lodash.once/-/lodash.once-4.1.1.tgz", + "integrity": "sha512-Sb487aTOCr9drQVL8pIxOzVhafOjZN9UU54hiN8PU3uAiSV7lx1yYNpbNmex2PK6dSJoNTSJUUswT651yww3Mg==" }, "node_modules/lru-cache": { "version": "6.0.0", @@ -2151,9 +2200,9 @@ "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==" }, "node_modules/semver": { - "version": "7.5.3", - "resolved": "https://registry.npmjs.org/semver/-/semver-7.5.3.tgz", - "integrity": "sha512-QBlUtyVk/5EeHbi7X0fw6liDZc7BBmEaSYn01fMU1OUYbf6GPsbTtd8WmnqbI20SeycoHSeiybkE/q1Q+qlThQ==", + "version": "7.5.4", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.5.4.tgz", + "integrity": "sha512-1bCSESV6Pv+i21Hvpxp3Dx+pSD8lIPt8uVjRrxAUt/nbswYc+tK6Y2btiULjd4+fnq15PX+nqQDC7Oft7WkwcA==", "dependencies": { "lru-cache": "^6.0.0" }, diff --git a/package-lock.json b/package-lock.json index 9c09fed..398b7f7 100644 --- a/package-lock.json +++ b/package-lock.json @@ -22,7 +22,7 @@ "express-session": "^1.17.3", "fs": "^0.0.1-security", "google-auth-library": "^9.0.0", - "jsonwebtoken": "^9.0.1", + "jsonwebtoken": "^9.0.2", "morgan": "^1.10.0", "nodemailer": "^6.9.4", "nodemon": "^2.0.22", @@ -1398,14 +1398,20 @@ } }, "node_modules/jsonwebtoken": { - "version": "9.0.1", - "resolved": "https://registry.npmjs.org/jsonwebtoken/-/jsonwebtoken-9.0.1.tgz", - "integrity": "sha512-K8wx7eJ5TPvEjuiVSkv167EVboBDv9PZdDoF7BgeQnBLVvZWW9clr2PsQHVJDTKaEIH5JBIwHujGcHp7GgI2eg==", + "version": "9.0.2", + "resolved": "https://registry.npmjs.org/jsonwebtoken/-/jsonwebtoken-9.0.2.tgz", + "integrity": "sha512-PRp66vJ865SSqOlgqS8hujT5U4AOgMfhrwYIuIhfKaoSCZcirrmASQr8CX7cUg+RMih+hgznrjp99o+W4pJLHQ==", "dependencies": { "jws": "^3.2.2", - "lodash": "^4.17.21", + "lodash.includes": "^4.3.0", + "lodash.isboolean": "^3.0.3", + "lodash.isinteger": "^4.0.4", + "lodash.isnumber": "^3.0.3", + "lodash.isplainobject": "^4.0.6", + "lodash.isstring": "^4.0.1", + "lodash.once": "^4.0.0", "ms": "^2.1.1", - "semver": "^7.3.8" + "semver": "^7.5.4" }, "engines": { "node": ">=12", @@ -1447,10 +1453,40 @@ "node": ">= 0.6" } }, - "node_modules/lodash": { - "version": "4.17.21", - "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.21.tgz", - "integrity": "sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg==" + "node_modules/lodash.includes": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/lodash.includes/-/lodash.includes-4.3.0.tgz", + "integrity": "sha512-W3Bx6mdkRTGtlJISOvVD/lbqjTlPPUDTMnlXZFnVwi9NKJ6tiAk6LVdlhZMm17VZisqhKcgzpO5Wz91PCt5b0w==" + }, + "node_modules/lodash.isboolean": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/lodash.isboolean/-/lodash.isboolean-3.0.3.tgz", + "integrity": "sha512-Bz5mupy2SVbPHURB98VAcw+aHh4vRV5IPNhILUCsOzRmsTmSQ17jIuqopAentWoehktxGd9e/hbIXq980/1QJg==" + }, + "node_modules/lodash.isinteger": { + "version": "4.0.4", + "resolved": "https://registry.npmjs.org/lodash.isinteger/-/lodash.isinteger-4.0.4.tgz", + "integrity": "sha512-DBwtEWN2caHQ9/imiNeEA5ys1JoRtRfY3d7V9wkqtbycnAmTvRRmbHKDV4a0EYc678/dia0jrte4tjYwVBaZUA==" + }, + "node_modules/lodash.isnumber": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/lodash.isnumber/-/lodash.isnumber-3.0.3.tgz", + "integrity": "sha512-QYqzpfwO3/CWf3XP+Z+tkQsfaLL/EnUlXWVkIk5FUPc4sBdTehEqZONuyRt2P67PXAk+NXmTBcc97zw9t1FQrw==" + }, + "node_modules/lodash.isplainobject": { + "version": "4.0.6", + "resolved": "https://registry.npmjs.org/lodash.isplainobject/-/lodash.isplainobject-4.0.6.tgz", + "integrity": "sha512-oSXzaWypCMHkPC3NvBEaPHf0KsA5mvPrOPgQWDsbg8n7orZ290M0BmC/jgRZ4vcJ6DTAhjrsSYgdsW/F+MFOBA==" + }, + "node_modules/lodash.isstring": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/lodash.isstring/-/lodash.isstring-4.0.1.tgz", + "integrity": "sha512-0wJxfxH1wgO3GrbuP+dTTk7op+6L41QCXbGINEmD+ny/G/eCqGzxyCsh7159S+mgDDcoarnBw6PC1PS5+wUGgw==" + }, + "node_modules/lodash.once": { + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/lodash.once/-/lodash.once-4.1.1.tgz", + "integrity": "sha512-Sb487aTOCr9drQVL8pIxOzVhafOjZN9UU54hiN8PU3uAiSV7lx1yYNpbNmex2PK6dSJoNTSJUUswT651yww3Mg==" }, "node_modules/lru-cache": { "version": "6.0.0", @@ -2194,9 +2230,9 @@ "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==" }, "node_modules/semver": { - "version": "7.5.3", - "resolved": "https://registry.npmjs.org/semver/-/semver-7.5.3.tgz", - "integrity": "sha512-QBlUtyVk/5EeHbi7X0fw6liDZc7BBmEaSYn01fMU1OUYbf6GPsbTtd8WmnqbI20SeycoHSeiybkE/q1Q+qlThQ==", + "version": "7.5.4", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.5.4.tgz", + "integrity": "sha512-1bCSESV6Pv+i21Hvpxp3Dx+pSD8lIPt8uVjRrxAUt/nbswYc+tK6Y2btiULjd4+fnq15PX+nqQDC7Oft7WkwcA==", "dependencies": { "lru-cache": "^6.0.0" }, diff --git a/package.json b/package.json index 96f75bd..38438aa 100644 --- a/package.json +++ b/package.json @@ -24,7 +24,7 @@ "express-session": "^1.17.3", "fs": "^0.0.1-security", "google-auth-library": "^9.0.0", - "jsonwebtoken": "^9.0.1", + "jsonwebtoken": "^9.0.2", "morgan": "^1.10.0", "nodemailer": "^6.9.4", "nodemon": "^2.0.22",