feat: Nambahin API untuk hapusin member dari project

This commit is contained in:
Rafi Athallah
2026-06-26 10:46:18 +07:00
parent 5e77286fcc
commit 5e930ccbff
4 changed files with 197 additions and 1 deletions
@@ -571,6 +571,54 @@ class ProjectService {
}
}
async removeMember(payload, actor = {}) {
try {
if (!actor?.id) {
return error(new BadRequestError("Admin ID is required"));
}
if (actor.role !== "admin" && actor.role !== "mentor") {
return error(
new ForbiddenError("Access denied: only mentors/admins can remove members"),
);
}
const { id_project, id_user } = payload;
if (!id_project || !id_user) {
return error(new BadRequestError("Project ID and User ID are required"));
}
const project = await projectRepository.findById(id_project);
if (!project) {
return error(new NotFoundError("Project not found"));
}
const user = await projectRepository.findUserByIdAndActive(id_user);
if (!user) {
return error(new NotFoundError("User not found or inactive"));
}
const existingMembership = await projectRepository.findMembership(id_project, id_user);
if (!existingMembership || existingMembership.status !== 'active') {
return error(new BadRequestError("User is not an active member of this project"));
}
const membership = await projectRepository.updateMembershipStatus(existingMembership.id, 'removed');
await notificationService.createNotificationForIntern(
id_user,
"Dikeluarkan dari Proyek",
`Anda telah dikeluarkan dari proyek '${project.project_name}'.`
).catch(err => console.error("Failed to send project removal notification:", err));
return data(membership);
} catch (err) {
return error(err);
}
}
async generateUniqueProjectSlug(projectName, excludeProjectId = null) {
const baseSlug = slugify(projectName, 'project');