mirror of
https://github.com/bluewave-labs/Checkmate.git
synced 2026-05-18 23:48:43 -05:00
remove service regsitry, remove unused middleware
This commit is contained in:
+1
-1
@@ -73,7 +73,7 @@ export const createApp = ({ services, controllers, envSettings, frontendPath, op
|
||||
});
|
||||
|
||||
// Main app routes
|
||||
setupRoutes(app, controllers);
|
||||
setupRoutes(app, controllers, services);
|
||||
|
||||
// FE routes
|
||||
app.get("*", (req, res) => {
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
import { verifyJWT } from "../middleware/v1/verifyJWT.js";
|
||||
import { createVerifyJWT } from "../middleware/v1/verifyJWT.js";
|
||||
import { authApiLimiter } from "../middleware/v1/rateLimiter.js";
|
||||
|
||||
import AuthRoutes from "../routes/v1/authRoute.js";
|
||||
@@ -15,19 +15,20 @@ import NotificationRoutes from "../routes/v1/notificationRoute.js";
|
||||
|
||||
import IncidentRoutes from "../routes/v1/incidentRoute.js";
|
||||
|
||||
export const setupRoutes = (app: any, controllers: Record<string, any>) => {
|
||||
export const setupRoutes = (app: any, controllers: Record<string, any>, services: Record<string, any>) => {
|
||||
const verifyJWT = createVerifyJWT(services.settingsService);
|
||||
// V1
|
||||
const authRoutes = new AuthRoutes(controllers.authController);
|
||||
const authRoutes = new AuthRoutes(controllers.authController, verifyJWT);
|
||||
const monitorRoutes = new MonitorRoutes(controllers.monitorController);
|
||||
const settingsRoutes = new SettingsRoutes(controllers.settingsController);
|
||||
const checkRoutes = new CheckRoutes(controllers.checkController);
|
||||
const inviteRoutes = new InviteRoutes(controllers.inviteController);
|
||||
const inviteRoutes = new InviteRoutes(controllers.inviteController, verifyJWT);
|
||||
const maintenanceWindowRoutes = new MaintenanceWindowRoutes(controllers.maintenanceWindowController);
|
||||
const queueRoutes = new QueueRoutes(controllers.queueController);
|
||||
const logRoutes = new LogRoutes(controllers.logController);
|
||||
const statusPageRoutes = new StatusPageRoutes(controllers.statusPageController);
|
||||
const statusPageRoutes = new StatusPageRoutes(controllers.statusPageController, verifyJWT);
|
||||
const notificationRoutes = new NotificationRoutes(controllers.notificationController);
|
||||
const diagnosticRoutes = new DiagnosticRoutes(controllers.diagnosticController);
|
||||
const diagnosticRoutes = new DiagnosticRoutes(controllers.diagnosticController, verifyJWT);
|
||||
const incidentRoutes = new IncidentRoutes(controllers.incidentController);
|
||||
|
||||
app.use("/api/v1/auth", authApiLimiter, authRoutes.getRouter());
|
||||
|
||||
@@ -1,4 +1,3 @@
|
||||
import ServiceRegistry from "../service/system/serviceRegistry.js";
|
||||
import TranslationService from "../service/system/translationService.js";
|
||||
import StringService from "../service/system/stringService.js";
|
||||
import MongoDB from "../db/MongoDB.js";
|
||||
@@ -46,7 +45,7 @@ import { games, GameDig } from "gamedig";
|
||||
import jmespath from "jmespath";
|
||||
|
||||
// DB Modules
|
||||
import { NormalizeData, NormalizeDataUptimeDetails } from "../utils/dataUtils.js";
|
||||
import { NormalizeData } from "../utils/dataUtils.js";
|
||||
import { GenerateAvatarImage } from "../utils/imageProcessing.js";
|
||||
import { ParseBoolean } from "../utils/utils.js";
|
||||
|
||||
@@ -140,9 +139,6 @@ export const initializeServices = async ({
|
||||
envSettings: any;
|
||||
settingsService: any;
|
||||
}): Promise<InitializedSerivces> => {
|
||||
const serviceRegistry = new ServiceRegistry({ logger });
|
||||
(ServiceRegistry as any).instance = serviceRegistry;
|
||||
|
||||
const translationService = new TranslationService(logger);
|
||||
await translationService.initialize();
|
||||
|
||||
@@ -335,9 +331,5 @@ export const initializeServices = async ({
|
||||
incidentsRepository,
|
||||
};
|
||||
|
||||
Object.values(services).forEach((service) => {
|
||||
ServiceRegistry.register(service.serviceName, service);
|
||||
});
|
||||
|
||||
return services;
|
||||
};
|
||||
|
||||
@@ -1,7 +1,3 @@
|
||||
// import { NormalizeData } from "../../../utils/dataUtils.js";
|
||||
// import ServiceRegistry from "../../../service/system/serviceRegistry.js";
|
||||
// import StringService from "../../../service/system/stringService.js";
|
||||
|
||||
const SERVICE_NAME = "statusPageModule";
|
||||
|
||||
class StatusPageModule {
|
||||
|
||||
@@ -1,12 +1,9 @@
|
||||
import { logger } from "../../utils/logger.js";
|
||||
import ServiceRegistry from "../../service/system/serviceRegistry.js";
|
||||
import StringService from "../../service/system/stringService.js";
|
||||
|
||||
const handleErrors = (error, req, res, next) => {
|
||||
const status = error.status || 500;
|
||||
const stringService = ServiceRegistry.get(StringService.SERVICE_NAME);
|
||||
const message = error.message || stringService.authIncorrectPassword;
|
||||
const service = error.service || stringService.unknownService;
|
||||
const message = error.message || "Server error";
|
||||
const service = error.service || "unknownService";
|
||||
logger.error({
|
||||
message: message,
|
||||
service: service,
|
||||
|
||||
@@ -1,57 +0,0 @@
|
||||
import jwt from "jsonwebtoken";
|
||||
const TOKEN_PREFIX = "Bearer ";
|
||||
const SERVICE_NAME = "allowedRoles";
|
||||
import ServiceRegistry from "../../service/system/serviceRegistry.js";
|
||||
import StringService from "../../service/system/stringService.js";
|
||||
import SettingsService from "../../service/system/settingsService.js";
|
||||
|
||||
const isAllowed = (allowedRoles) => {
|
||||
return (req, res, next) => {
|
||||
const token = req.headers["authorization"];
|
||||
const stringService = ServiceRegistry.get(StringService.SERVICE_NAME);
|
||||
// If no token is pressent, return an error
|
||||
if (!token) {
|
||||
const error = new Error(stringService.noAuthToken);
|
||||
error.status = 401;
|
||||
error.service = SERVICE_NAME;
|
||||
next(error);
|
||||
return;
|
||||
}
|
||||
|
||||
// If the token is improperly formatted, return an error
|
||||
if (!token.startsWith(TOKEN_PREFIX)) {
|
||||
const error = new Error(stringService.invalidAuthToken);
|
||||
error.status = 400;
|
||||
error.service = SERVICE_NAME;
|
||||
next(error);
|
||||
return;
|
||||
}
|
||||
// Parse the token
|
||||
try {
|
||||
const parsedToken = token.slice(TOKEN_PREFIX.length, token.length);
|
||||
const { jwtSecret } = ServiceRegistry.get(SettingsService.SERVICE_NAME).getSettings();
|
||||
var decoded = jwt.verify(parsedToken, jwtSecret);
|
||||
const userRoles = decoded.role;
|
||||
|
||||
// Check if the user has the required role
|
||||
if (userRoles.some((role) => allowedRoles.includes(role))) {
|
||||
next();
|
||||
return;
|
||||
} else {
|
||||
const error = new Error(stringService.insufficientPermissions);
|
||||
error.status = 403;
|
||||
error.service = SERVICE_NAME;
|
||||
next(error);
|
||||
return;
|
||||
}
|
||||
} catch (error) {
|
||||
error.status = 401;
|
||||
error.method = "isAllowed";
|
||||
error.service = SERVICE_NAME;
|
||||
next(error);
|
||||
return;
|
||||
}
|
||||
};
|
||||
};
|
||||
|
||||
export { isAllowed };
|
||||
Executable
+29
@@ -0,0 +1,29 @@
|
||||
import type { Request, Response, NextFunction } from "express";
|
||||
const SERVICE_NAME = "allowedRoles";
|
||||
import { AppError } from "@/utils/AppError.js";
|
||||
import type { UserRole } from "@/types/index.js";
|
||||
|
||||
const isAllowed = (allowedRoles: UserRole[]) => {
|
||||
return (req: Request, res: Response, next: NextFunction) => {
|
||||
try {
|
||||
const user = req.user;
|
||||
if (!user) {
|
||||
throw new AppError({ message: "Unauthorized", status: 403, service: SERVICE_NAME });
|
||||
}
|
||||
const userRoles = req.user?.role || [];
|
||||
|
||||
// Check if the user has the required role
|
||||
if (userRoles.some((role) => allowedRoles.includes(role))) {
|
||||
next();
|
||||
return;
|
||||
} else {
|
||||
throw new AppError({ message: "Unauthorized", status: 403, service: SERVICE_NAME });
|
||||
}
|
||||
} catch (error) {
|
||||
next(error);
|
||||
return;
|
||||
}
|
||||
};
|
||||
};
|
||||
|
||||
export { isAllowed };
|
||||
Executable → Regular
+43
-42
@@ -1,51 +1,52 @@
|
||||
import { NextFunction, Request, Response } from "express";
|
||||
|
||||
import jwt from "jsonwebtoken";
|
||||
import ServiceRegistry from "../../service/system/serviceRegistry.js";
|
||||
import SettingsService from "../../service/system/settingsService.js";
|
||||
import StringService from "../../service/system/stringService.js";
|
||||
import { AppError } from "@/utils/AppError.js";
|
||||
import { Settings } from "@/types/settings.js";
|
||||
|
||||
const SERVICE_NAME = "verifyJWT";
|
||||
const TOKEN_PREFIX = "Bearer ";
|
||||
|
||||
const verifyJWT = (req: Request, res: Response, next: NextFunction) => {
|
||||
const stringService = ServiceRegistry.get(StringService.SERVICE_NAME);
|
||||
const token = req.headers["authorization"];
|
||||
// Make sure a token is provided
|
||||
if (!token) {
|
||||
const error: any = new Error(stringService.noAuthToken);
|
||||
error.status = 401;
|
||||
error.service = SERVICE_NAME;
|
||||
next(error);
|
||||
return;
|
||||
}
|
||||
// Make sure it is properly formatted
|
||||
if (!token.startsWith(TOKEN_PREFIX)) {
|
||||
const error: any = new Error(stringService.invalidAuthToken); // Instantiate a new Error object for improperly formatted token
|
||||
error.status = 401;
|
||||
error.service = SERVICE_NAME;
|
||||
error.method = "verifyJWT";
|
||||
next(error);
|
||||
return;
|
||||
}
|
||||
|
||||
const parsedToken = token.slice(TOKEN_PREFIX.length, token.length);
|
||||
// Verify the token's authenticity
|
||||
const { jwtSecret } = ServiceRegistry.get(SettingsService.SERVICE_NAME).getSettings();
|
||||
jwt.verify(parsedToken, jwtSecret, (err: any, decoded: any) => {
|
||||
if (err) {
|
||||
const errorMessage = err.name === "TokenExpiredError" ? stringService.expiredAuthToken : stringService.invalidAuthToken;
|
||||
err.details = { msg: errorMessage };
|
||||
err.status = 401;
|
||||
err.service = SERVICE_NAME;
|
||||
err.method = "verifyJWT";
|
||||
next(err);
|
||||
export const createVerifyJWT = (settingsService: { getSettings: () => Settings }) => {
|
||||
return (req: Request, res: Response, next: NextFunction) => {
|
||||
const token = req.headers["authorization"];
|
||||
// Make sure a token is provided
|
||||
if (!token) {
|
||||
const error = new AppError({ message: "No token provided", status: 401, service: SERVICE_NAME });
|
||||
next(error);
|
||||
return;
|
||||
}
|
||||
// Make sure it is properly formatted
|
||||
if (!token.startsWith(TOKEN_PREFIX)) {
|
||||
const error = new AppError({ message: "Invalid token format", status: 401, service: SERVICE_NAME, method: "verifyJWT" });
|
||||
next(error);
|
||||
return;
|
||||
} else {
|
||||
// Token is valid, carry on
|
||||
req.user = decoded;
|
||||
next();
|
||||
}
|
||||
});
|
||||
};
|
||||
|
||||
export { verifyJWT };
|
||||
const parsedToken = token.slice(TOKEN_PREFIX.length, token.length);
|
||||
// Verify the token's authenticity
|
||||
const { jwtSecret } = settingsService.getSettings();
|
||||
if (!jwtSecret) {
|
||||
const error = new AppError({ message: "JWT secret not configured", status: 500, service: SERVICE_NAME });
|
||||
next(error);
|
||||
return;
|
||||
}
|
||||
jwt.verify(parsedToken, jwtSecret, (err: any, decoded: any) => {
|
||||
if (err) {
|
||||
const error = new AppError({
|
||||
message: "Failed to authenticate token",
|
||||
details: err,
|
||||
status: 401,
|
||||
service: SERVICE_NAME,
|
||||
method: "verifyJWT",
|
||||
});
|
||||
next(error);
|
||||
return;
|
||||
} else {
|
||||
// Token is valid, carry on
|
||||
req.user = decoded;
|
||||
next();
|
||||
}
|
||||
});
|
||||
};
|
||||
};
|
||||
|
||||
@@ -1,59 +0,0 @@
|
||||
import { logger } from "../../utils/logger.js";
|
||||
import ServiceRegistry from "../../service/system/serviceRegistry.js";
|
||||
import StringService from "../../service/system/stringService.js";
|
||||
import { ObjectId } from "mongodb";
|
||||
|
||||
const SERVICE_NAME = "verifyOwnership";
|
||||
|
||||
const verifyOwnership = (Model, paramName) => {
|
||||
const stringService = ServiceRegistry.get(StringService.SERVICE_NAME);
|
||||
return async (req, res, next) => {
|
||||
const userId = req.user._id;
|
||||
let documentId = req.params[paramName];
|
||||
|
||||
try {
|
||||
if (typeof documentId === "string") {
|
||||
documentId = ObjectId.createFromHexString(documentId);
|
||||
}
|
||||
const doc = await Model.findById(documentId);
|
||||
//If the document is not found, return a 404 error
|
||||
if (!doc) {
|
||||
logger.error({
|
||||
message: stringService.verifyOwnerNotFound,
|
||||
service: SERVICE_NAME,
|
||||
method: "verifyOwnership",
|
||||
});
|
||||
const error = new Error(stringService.verifyOwnerNotFound);
|
||||
error.status = 404;
|
||||
throw error;
|
||||
}
|
||||
|
||||
// Special case for User model, as it will not have a `userId` field as other docs will
|
||||
if (Model.modelName === "User") {
|
||||
if (userId.toString() !== doc._id.toString()) {
|
||||
const error = new Error(stringService.verifyOwnerUnauthorized);
|
||||
error.status = 403;
|
||||
throw error;
|
||||
}
|
||||
next();
|
||||
return;
|
||||
}
|
||||
|
||||
// If the userID does not match the document's userID, return a 403 error
|
||||
if (userId.toString() !== doc.userId.toString()) {
|
||||
const error = new Error("Unauthorized");
|
||||
error.status = 403;
|
||||
throw error;
|
||||
}
|
||||
next();
|
||||
return;
|
||||
} catch (error) {
|
||||
error.service = SERVICE_NAME;
|
||||
error.method = "verifyOwnership";
|
||||
next(error);
|
||||
return;
|
||||
}
|
||||
};
|
||||
};
|
||||
|
||||
export { verifyOwnership };
|
||||
@@ -1,66 +0,0 @@
|
||||
const jwt = require("jsonwebtoken");
|
||||
const logger = require("../../utils/logger.js");
|
||||
const SERVICE_NAME = "verifyAdmin";
|
||||
const TOKEN_PREFIX = "Bearer ";
|
||||
import ServiceRegistry from "../service/serviceRegistry.js";
|
||||
import SettingsService from "../service/settingsService.js";
|
||||
import StringService from "../service/stringService.js";
|
||||
/**
|
||||
* Verifies the JWT token
|
||||
* @function
|
||||
* @param {express.Request} req
|
||||
* @param {express.Response} res
|
||||
* @param {express.NextFunction} next
|
||||
* @returns {express.Response}
|
||||
*/
|
||||
const verifySuperAdmin = (req, res, next) => {
|
||||
const stringService = ServiceRegistry.get(StringService.SERVICE_NAME);
|
||||
const token = req.headers["authorization"];
|
||||
// Make sure a token is provided
|
||||
if (!token) {
|
||||
const error = new Error(stringService.noAuthToken);
|
||||
error.status = 401;
|
||||
error.service = SERVICE_NAME;
|
||||
next(error);
|
||||
return;
|
||||
}
|
||||
// Make sure it is properly formatted
|
||||
if (!token.startsWith(TOKEN_PREFIX)) {
|
||||
const error = new Error(stringService.invalidAuthToken); // Instantiate a new Error object for improperly formatted token
|
||||
error.status = 400;
|
||||
error.service = SERVICE_NAME;
|
||||
error.method = "verifySuperAdmin";
|
||||
next(error);
|
||||
return;
|
||||
}
|
||||
|
||||
const parsedToken = token.slice(TOKEN_PREFIX.length, token.length);
|
||||
// verify admin role is present
|
||||
const { jwtSecret } = ServiceRegistry.get(SettingsService.SERVICE_NAME).getSettings();
|
||||
|
||||
jwt.verify(parsedToken, jwtSecret, (err, decoded) => {
|
||||
if (err) {
|
||||
logger.error({
|
||||
message: err.message,
|
||||
service: SERVICE_NAME,
|
||||
method: "verifySuperAdmin",
|
||||
stack: err.stack,
|
||||
details: stringService.invalidAuthToken,
|
||||
});
|
||||
return res.status(401).json({ success: false, msg: stringService.invalidAuthToken });
|
||||
}
|
||||
|
||||
if (decoded.role.includes("superadmin") === false) {
|
||||
logger.error({
|
||||
message: stringService.invalidAuthToken,
|
||||
service: SERVICE_NAME,
|
||||
method: "verifySuperAdmin",
|
||||
stack: err.stack,
|
||||
});
|
||||
return res.status(401).json({ success: false, msg: stringService.unauthorized });
|
||||
}
|
||||
next();
|
||||
});
|
||||
};
|
||||
|
||||
module.exports = { verifySuperAdmin };
|
||||
@@ -1,18 +1,17 @@
|
||||
import { Router } from "express";
|
||||
import { verifyJWT } from "../../middleware/v1/verifyJWT.js";
|
||||
import { isAllowed } from "../../middleware/v1/isAllowed.js";
|
||||
import multer from "multer";
|
||||
|
||||
const upload = multer();
|
||||
|
||||
class AuthRoutes {
|
||||
constructor(authController) {
|
||||
constructor(authController, verifyJWT) {
|
||||
this.router = Router();
|
||||
this.authController = authController;
|
||||
this.initRoutes();
|
||||
this.initRoutes(verifyJWT);
|
||||
}
|
||||
|
||||
initRoutes() {
|
||||
initRoutes(verifyJWT) {
|
||||
this.router.post("/register", upload.single("profileImage"), this.authController.registerUser);
|
||||
this.router.post("/login", this.authController.loginUser);
|
||||
|
||||
|
||||
@@ -1,14 +1,14 @@
|
||||
import { Router } from "express";
|
||||
import { verifyJWT } from "../../middleware/v1/verifyJWT.js";
|
||||
import { isAllowed } from "../../middleware/v1/isAllowed.js";
|
||||
|
||||
class DiagnosticRoutes {
|
||||
constructor(diagnosticController) {
|
||||
constructor(diagnosticController, verifyJWT) {
|
||||
this.router = Router();
|
||||
this.diagnosticController = diagnosticController;
|
||||
this.initRoutes();
|
||||
this.initRoutes(verifyJWT);
|
||||
}
|
||||
initRoutes() {
|
||||
|
||||
initRoutes(verifyJWT) {
|
||||
this.router.get("/system", verifyJWT, isAllowed(["admin", "superadmin"]), this.diagnosticController.getSystemStats);
|
||||
}
|
||||
|
||||
|
||||
@@ -1,15 +1,14 @@
|
||||
import { Router } from "express";
|
||||
import { verifyJWT } from "../../middleware/v1/verifyJWT.js";
|
||||
import { isAllowed } from "../../middleware/v1/isAllowed.js";
|
||||
|
||||
class InviteRoutes {
|
||||
constructor(inviteController) {
|
||||
constructor(inviteController, verifyJWT) {
|
||||
this.router = Router();
|
||||
this.inviteController = inviteController;
|
||||
this.initRoutes();
|
||||
this.initRoutes(verifyJWT);
|
||||
}
|
||||
|
||||
initRoutes() {
|
||||
initRoutes(verifyJWT) {
|
||||
this.router.post("/send", verifyJWT, isAllowed(["admin", "superadmin"]), this.inviteController.sendInviteEmail);
|
||||
this.router.post("/verify", this.inviteController.verifyInviteToken);
|
||||
this.router.post("/", verifyJWT, isAllowed(["admin", "superadmin"]), this.inviteController.getInviteToken);
|
||||
|
||||
@@ -1,16 +1,15 @@
|
||||
import { Router } from "express";
|
||||
import { verifyJWT } from "../../middleware/v1/verifyJWT.js";
|
||||
import multer from "multer";
|
||||
const upload = multer();
|
||||
|
||||
class StatusPageRoutes {
|
||||
constructor(statusPageController) {
|
||||
constructor(statusPageController, verifyJWT) {
|
||||
this.router = Router();
|
||||
this.statusPageController = statusPageController;
|
||||
this.initRoutes();
|
||||
this.initRoutes(verifyJWT);
|
||||
}
|
||||
|
||||
initRoutes() {
|
||||
initRoutes(verifyJWT) {
|
||||
this.router.get("/", this.statusPageController.getStatusPage);
|
||||
this.router.get("/team", verifyJWT, this.statusPageController.getStatusPagesByTeamId);
|
||||
|
||||
|
||||
Reference in New Issue
Block a user