From 74d87d8880c0730d3afd97c8b035330a3f2d106b Mon Sep 17 00:00:00 2001 From: Fred Date: Thu, 18 Jun 2026 13:13:17 +0800 Subject: [PATCH] Add lender API key check for score endpoint --- Server/src/config/swagger.ts | 8 +++++ Server/src/controllers/user.controller.ts | 8 +++++ .../src/middleware/lender-auth.middleware.ts | 32 +++++++++++++++++++ Server/src/routes/user.routes.ts | 8 ++++- 4 files changed, 55 insertions(+), 1 deletion(-) create mode 100644 Server/src/middleware/lender-auth.middleware.ts diff --git a/Server/src/config/swagger.ts b/Server/src/config/swagger.ts index 0576d73..c2e1ae7 100644 --- a/Server/src/config/swagger.ts +++ b/Server/src/config/swagger.ts @@ -19,6 +19,14 @@ const options: swaggerJsdoc.Options = { }, ], components: { + securitySchemes: { + LenderApiKey: { + type: "apiKey", + in: "header", + name: "x-api-key", + description: "Lender API key", + }, + }, schemas: { User: { type: "object", diff --git a/Server/src/controllers/user.controller.ts b/Server/src/controllers/user.controller.ts index e29c77f..9fcf53b 100644 --- a/Server/src/controllers/user.controller.ts +++ b/Server/src/controllers/user.controller.ts @@ -130,7 +130,15 @@ export const requestScoring = async ( * get: * tags: [Users] * summary: Get a user's credit score with breakdown (for lenders) + * security: + * - LenderApiKey: [] * parameters: + * - in: header + * name: x-api-key + * required: true + * schema: + * type: string + * description: API key for a registered lender * - in: path * name: wallet * required: true diff --git a/Server/src/middleware/lender-auth.middleware.ts b/Server/src/middleware/lender-auth.middleware.ts new file mode 100644 index 0000000..4e17520 --- /dev/null +++ b/Server/src/middleware/lender-auth.middleware.ts @@ -0,0 +1,32 @@ +import { NextFunction, Request, Response } from "express"; +import { prisma } from "../config/database"; + +export const validateLenderKey = async ( + req: Request, + res: Response, + next: NextFunction +) => { + try { + const apiKeyHeader = req.headers["x-api-key"]; + const apiKey = Array.isArray(apiKeyHeader) ? apiKeyHeader[0] : apiKeyHeader; + + if (!apiKey) { + return res.status(401).json({ + success: false, + error: "Missing x-api-key header", + }); + } + + const lender = await prisma.lender.findUnique({ where: { apiKey } }); + if (!lender) { + return res.status(401).json({ + success: false, + error: "Invalid lender API key", + }); + } + + return next(); + } catch (error) { + return next(error); + } +}; diff --git a/Server/src/routes/user.routes.ts b/Server/src/routes/user.routes.ts index e3ffcab..31e7aad 100644 --- a/Server/src/routes/user.routes.ts +++ b/Server/src/routes/user.routes.ts @@ -5,13 +5,19 @@ import { getCreditHistory, requestScoring, } from "../controllers/user.controller"; +import { validateLenderKey } from "../middleware/lender-auth.middleware"; import { validate, validateParams } from "../middleware/validation.middleware"; import { ScoringRequestSchema, WalletParamSchema } from "../middleware/schemas"; const router = Router(); router.post("/request", validate(ScoringRequestSchema), requestScoring); -router.get("/:wallet/score", validateParams(WalletParamSchema), getScore); +router.get( + "/:wallet/score", + validateLenderKey, + validateParams(WalletParamSchema), + getScore +); router.get("/:wallet/history", validateParams(WalletParamSchema), getCreditHistory); router.get("/:wallet/profile", validateParams(WalletParamSchema), getProfile);