Skip to content

Commit eee2718

Browse files
Merge pull request #143 from satyansh911/feat/role-based-scoping
Implemeted Role-Based-Scoping in Add Position Form
2 parents 65b2290 + ce67dce commit eee2718

2 files changed

Lines changed: 462 additions & 127 deletions

File tree

backend/routes/events.js

Lines changed: 40 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,11 @@
1-
// backend/routes/events.js
21
const express = require("express");
32
const router = express.Router();
43
const { Event, User, OrganizationalUnit } = require("../models/schema");
54
const { v4: uuidv4 } = require("uuid");
65
const isAuthenticated = require("../middlewares/isAuthenticated");
76
const isEventContact = require("../middlewares/isEventContact");
87
const authorizeRole = require("../middlewares/authorizeRole");
9-
const { ROLE_GROUPS } = require("../utils/roles");
8+
const { ROLE_GROUPS, ROLES } = require("../utils/roles");
109

1110
// Create a new event (new events can be created by admins only)
1211
router.post(
@@ -83,7 +82,45 @@ router.get("/events", async (req, res) => {
8382

8483
router.get("/units", isAuthenticated, async (req, res) => {
8584
try {
86-
const units = await OrganizationalUnit.find();
85+
const role = (req.user && req.user.role) || "";
86+
const userEmail = String(
87+
(req.user &&
88+
(req.user.username ||
89+
(req.user.personal_info && req.user.personal_info.email))) ||
90+
"",
91+
)
92+
.trim()
93+
.toLowerCase();
94+
95+
const categoryForRole = {
96+
[ROLES.GENSEC_SCITECH]: "scitech",
97+
[ROLES.GENSEC_ACADEMIC]: "academic",
98+
[ROLES.GENSEC_CULTURAL]: "cultural",
99+
[ROLES.GENSEC_SPORTS]: "sports",
100+
};
101+
102+
let units = [];
103+
104+
if (role === ROLES.PRESIDENT) {
105+
// President sees all units
106+
units = await OrganizationalUnit.find();
107+
} else if (categoryForRole[role]) {
108+
// GenSecs see units by category
109+
units = await OrganizationalUnit.find({
110+
category: categoryForRole[role],
111+
});
112+
} else if (role === ROLES.CLUB_COORDINATOR) {
113+
// Club Coordinator sees only their own unit (matched by contact email)
114+
const escapeRegex = (s) => s.replace(/[.*+?^${}()|[\]\\]/g, "\\$&");
115+
const coordUnit = await OrganizationalUnit.findOne({
116+
"contact_info.email": new RegExp(`^${escapeRegex(userEmail)}$`, "i"),
117+
});
118+
units = coordUnit ? [coordUnit] : [];
119+
} else {
120+
// Default: return all units (keeps previous behavior for non-admins if needed)
121+
units = await OrganizationalUnit.find();
122+
}
123+
87124
res.json(units);
88125
} catch (err) {
89126
console.error(err);
@@ -322,7 +359,6 @@ router.put("/:eventId", isAuthenticated, isEventContact, async (req, res) => {
322359
console.log("Number of fields to update:", Object.keys(updates).length);
323360
console.log("Fields being updated:", Object.keys(updates));
324361
console.log("========================\n");
325-
// 🔍 DEBUG LOGS - END
326362

327363
// Fetch the event BEFORE update to compare
328364
const eventBefore = await Event.findById(eventId);

0 commit comments

Comments
 (0)