diff --git a/server/package-lock.json b/server/package-lock.json index fc820beca..3084a5361 100644 --- a/server/package-lock.json +++ b/server/package-lock.json @@ -14,6 +14,7 @@ "bcryptjs": "3.0.2", "bullmq": "5.41.2", "compression": "1.8.1", + "cookie-parser": "^1.4.7", "cors": "^2.8.5", "dockerode": "4.0.6", "dotenv": "^16.4.5", @@ -2362,6 +2363,28 @@ "node": ">= 0.6" } }, + "node_modules/cookie-parser": { + "version": "1.4.7", + "resolved": "https://registry.npmjs.org/cookie-parser/-/cookie-parser-1.4.7.tgz", + "integrity": "sha512-nGUvgXnotP3BsjiLX2ypbQnWoGUPIIfHQNZkkC668ntrzGWEZVW70HDEB1qnNGMicPje6EttlIgzo51YSwNQGw==", + "license": "MIT", + "dependencies": { + "cookie": "0.7.2", + "cookie-signature": "1.0.6" + }, + "engines": { + "node": ">= 0.8.0" + } + }, + "node_modules/cookie-parser/node_modules/cookie": { + "version": "0.7.2", + "resolved": "https://registry.npmjs.org/cookie/-/cookie-0.7.2.tgz", + "integrity": "sha512-yki5XnKuf750l50uGTllt6kKILY4nQ1eNIQatoXEByZ5dWgnKqbnqmTrBE5B4N7lrMJKQ2ytWMiTO2o0v6Ew/w==", + "license": "MIT", + "engines": { + "node": ">= 0.6" + } + }, "node_modules/cookie-signature": { "version": "1.0.6", "resolved": "https://registry.npmjs.org/cookie-signature/-/cookie-signature-1.0.6.tgz", diff --git a/server/package.json b/server/package.json index 9403748e4..929fab58a 100755 --- a/server/package.json +++ b/server/package.json @@ -21,6 +21,7 @@ "bcryptjs": "3.0.2", "bullmq": "5.41.2", "compression": "1.8.1", + "cookie-parser": "^1.4.7", "cors": "^2.8.5", "dockerode": "4.0.6", "dotenv": "^16.4.5", diff --git a/server/src/app.js b/server/src/app.js index dfc7d4542..9cabda6b6 100644 --- a/server/src/app.js +++ b/server/src/app.js @@ -4,6 +4,7 @@ import { responseHandler } from "./middleware/responseHandler.js"; import cors from "cors"; import helmet from "helmet"; import compression from "compression"; +import cookieParser from "cookie-parser"; import languageMiddleware from "./middleware/languageMiddleware.js"; import swaggerUi from "swagger-ui-express"; import { handleErrors } from "./middleware/handleErrors.js"; @@ -31,8 +32,8 @@ export const createApp = ({ services, controllers, envSettings, frontendPath, op }) ); app.use(express.json()); + app.use(cookieParser()); - // Apply input sanitization middleware app.use(sanitizeBody()); app.use(sanitizeQuery()); diff --git a/server/src/utils/cookieHelpers.js b/server/src/utils/cookieHelpers.js new file mode 100644 index 000000000..7005b66ca --- /dev/null +++ b/server/src/utils/cookieHelpers.js @@ -0,0 +1,26 @@ +/** + * Get standardized cookie options for authentication tokens + * @param {Object} options - Additional cookie options + * @returns {Object} Cookie options object + */ +export const getAuthCookieOptions = (options = {}) => { + return { + httpOnly: true, + secure: process.env.NODE_ENV === "production", + sameSite: "strict", + maxAge: 2 * 60 * 60 * 1000, // 2 hours (matches JWT TTL) + ...options, + }; +}; + +/** + * Clear cookie options for authentication tokens + * @returns {Object} Cookie clear options object + */ +export const getClearAuthCookieOptions = () => { + return { + httpOnly: true, + secure: process.env.NODE_ENV === "production", + sameSite: "strict", + }; +};