From 7881959c54464401c31558b07b01f22233102e28 Mon Sep 17 00:00:00 2001
From: Ivan Alglave <ivanalglave@outlook.fr>
Date: Wed, 8 Feb 2023 12:52:27 +0100
Subject: [PATCH] fix: added and endpoint to post/delete people in the inner
 groups of a group

---
 src/groups/dao/groups.dao.ts    | 47 ++++++++++++++++++++++++++++++++-
 src/groups/groups.controller.ts | 13 +++++++++
 src/groups/groups.service.ts    | 19 ++++++++-----
 src/shared/Roles.ts             | 14 ++++++++++
 4 files changed, 86 insertions(+), 7 deletions(-)
 create mode 100644 src/shared/Roles.ts

diff --git a/src/groups/dao/groups.dao.ts b/src/groups/dao/groups.dao.ts
index 1604ef2..5be7864 100644
--- a/src/groups/dao/groups.dao.ts
+++ b/src/groups/dao/groups.dao.ts
@@ -2,12 +2,14 @@ import {
   Injectable,
   NotFoundException,
   InternalServerErrorException,
+  BadRequestException,
 } from '@nestjs/common';
 import { InjectModel } from '@nestjs/mongoose';
 import { Model } from 'mongoose';
 import { CreateGroupDto } from '../dto/create-group.dto';
 import { UpdateGroupDto } from '../dto/update-group.dto';
 import { Group } from '../schemas/group.schema';
+import * as Roles from 'src/shared/Roles';
 
 @Injectable()
 export class GroupsDao {
@@ -62,6 +64,49 @@ export class GroupsDao {
       );
     });
 
+  findByIdAndUpdateRole = (
+    id: string,
+    role: string,
+    personId: string,
+    action: string,
+  ): Promise<Group | void> =>
+    new Promise((resolve, reject) => {
+      let query = {};
+      let queryInner = {};
+      switch (role) {
+        case Roles.ROLE_RESPONSIBLE:
+          queryInner = { responsibles: personId };
+          break;
+        case Roles.ROLE_SECRETARY:
+          queryInner = { secretaries: personId };
+          break;
+        case Roles.ROLE_STUDENT:
+          queryInner = { students: personId };
+          break;
+        default:
+          reject(new BadRequestException('Bad role'));
+      }
+      switch (action) {
+        case 'post':
+          query = { $push: queryInner };
+          break;
+        case 'delete':
+          query = { $pull: queryInner };
+          break;
+        default:
+          reject(new BadRequestException('Bad action'));
+      }
+      this._groupModel.findByIdAndUpdate(
+        id,
+        query,
+        { new: true },
+        (err, value) => {
+          if (err) reject(err.message);
+          resolve(value);
+        },
+      );
+    });
+
   findByIdAndRemove = (id: string): Promise<Group | void> =>
     new Promise((resolve, reject) => {
       this._groupModel.findByIdAndDelete(id, {}, (err) => {
@@ -72,7 +117,7 @@ export class GroupsDao {
 
   findByParentAndRemove = (parent: string): Promise<Group | void> =>
     new Promise((resolve, reject) => {
-      this._groupModel.remove({parent : {$regex : parent}}, (err) => {
+      this._groupModel.remove({ parent: { $regex: parent } }, (err) => {
         if (err) reject(err.message);
         resolve();
       });
diff --git a/src/groups/groups.controller.ts b/src/groups/groups.controller.ts
index 662eb3e..18cf22e 100644
--- a/src/groups/groups.controller.ts
+++ b/src/groups/groups.controller.ts
@@ -42,6 +42,19 @@ export class GroupsController {
     return this._groupsService.update(params.id, updateGroupDto);
   }
 
+  @Put(':id/:role')
+  updateOneByRole(
+    @Param() params: { id: string; role: string },
+    @Body() body: { personId: string; action: string },
+  ): Promise<GroupEntity | void> {
+    return this._groupsService.updateOneByRole(
+      params.id,
+      params.role,
+      body.personId,
+      body.action,
+    );
+  }
+
   @Delete(':id')
   delete(@Param() params: { id: string }): Promise<GroupEntity | void> {
     return this._groupsService.delete(params.id);
diff --git a/src/groups/groups.service.ts b/src/groups/groups.service.ts
index 86ba385..bf52da3 100644
--- a/src/groups/groups.service.ts
+++ b/src/groups/groups.service.ts
@@ -19,15 +19,22 @@ export class GroupsService {
   update = (id: string, group: UpdateGroupDto): Promise<GroupEntity | void> =>
     this._groupsDao.findByIdAndUpdate(id, group);
 
+  updateOneByRole = (
+    id: string,
+    role: string,
+    personId: string,
+    action: string,
+  ): Promise<GroupEntity | void> =>
+    this._groupsDao.findByIdAndUpdateRole(id, role, personId, action);
+
   delete(id: string): Promise<GroupEntity | void> {
-    return this._groupsDao.findById(id).then(res => {
-      if(res){
-        let parent = res.parent + "-" + res.name;
+    return this._groupsDao.findById(id).then((res) => {
+      if (res) {
+        const parent = res.parent + '-' + res.name;
         this._groupsDao.findByIdAndRemove(id).then(() => {
           this._groupsDao.findByParentAndRemove(parent);
-        })
+        });
       }
-    })
-
+    });
   }
 }
diff --git a/src/shared/Roles.ts b/src/shared/Roles.ts
new file mode 100644
index 0000000..317633e
--- /dev/null
+++ b/src/shared/Roles.ts
@@ -0,0 +1,14 @@
+export const ROLE_STUDENT = 'student';
+export const ROLE_SECRETARY = 'secretary';
+export const ROLE_RESPONSIBLE = 'responsible';
+export const ROLE_ADMIN = 'admin';
+
+export const ROLES = [
+  ROLE_STUDENT,
+  ROLE_SECRETARY,
+  ROLE_RESPONSIBLE,
+  ROLE_ADMIN,
+];
+
+export const isRoleValid = (potentialRole: string): boolean =>
+  ROLES.includes(potentialRole);
-- 
GitLab