Skip to content
Snippets Groups Projects

Compare revisions

Changes are shown as if the source revision was being merged into the target revision. Learn more about comparing revisions.

Source

Select target project
No results found
Select Git revision
  • add_route_assignments
  • ask-user-to-delete-exercises-on-duplicates
  • bedran_exercise-list
  • jw_sonar
  • jw_sonar_backup
  • main
  • update-dependencies
  • v6.0.0
  • 2.0.0
  • 2.1.0
  • 2.2.0
  • 3.0.0
  • 3.0.1
  • 3.1.0
  • 3.1.1
  • 3.1.2
  • 3.1.3
  • 3.2.0
  • 3.3.0
  • 3.4.0
  • 3.4.1
  • 3.4.2
  • 3.5.0
  • 3.5.1
  • 3.5.2
  • 3.5.3
  • 4.0.0
  • 4.1.0
  • 5.0.0
  • 5.0.1
  • 6.0.0-dev
  • v1.0.1
32 results

Target

Select target project
  • Dojo_Project_Nguyen/backend/dojobackendapi
  • dojo_project/projects/backend/dojobackendapi
2 results
Select Git revision
  • add_route_assignments
  • ask-user-to-delete-exercises-on-duplicates
  • bedran_exercise-list
  • jw_sonar
  • jw_sonar_backup
  • main
  • update-dependencies
  • v6.0.0
  • 2.0.0
  • 2.1.0
  • 2.2.0
  • 3.0.0
  • 3.0.1
  • 3.1.0
  • 3.1.1
  • 3.1.2
  • 3.1.3
  • 3.2.0
  • 3.3.0
  • 3.4.0
  • 3.4.1
  • 3.4.2
  • 3.5.0
  • 3.5.1
  • 3.5.2
  • 3.5.3
  • 4.0.0
  • 4.1.0
  • 5.0.0
  • 5.0.1
  • 6.0.0-dev
  • v1.0.1
32 results
Show changes
Commits on Source (5)
...@@ -5,6 +5,13 @@ import * as Gitlab from '@gitbeaker/rest'; ...@@ -5,6 +5,13 @@ import * as Gitlab from '@gitbeaker/rest';
class UserManager { class UserManager {
async getFiltered(filters: Prisma.UserWhereInput | undefined, include: Prisma.UserInclude | undefined = undefined): Promise<Array<User> | undefined> {
return await db.user.findMany({
where : filters,
include: include
}) as unknown as Array<User> ?? undefined;
}
async getByMail(mail: string, include: Prisma.UserInclude | undefined = undefined): Promise<User | undefined> { async getByMail(mail: string, include: Prisma.UserInclude | undefined = undefined): Promise<User | undefined> {
return await db.user.findUnique({ return await db.user.findUnique({
where : { where : {
...@@ -14,10 +21,10 @@ class UserManager { ...@@ -14,10 +21,10 @@ class UserManager {
}) as unknown as User ?? undefined; }) as unknown as User ?? undefined;
} }
async getById(id: number, include: Prisma.UserInclude | undefined = undefined): Promise<User | undefined> { async getById(id: string | number, include: Prisma.UserInclude | undefined = undefined): Promise<User | undefined> {
return await db.user.findUnique({ return await db.user.findUnique({
where : { where : {
id: id id: Number(id)
}, },
include: include include: include
}) as unknown as User ?? undefined; }) as unknown as User ?? undefined;
......
...@@ -5,6 +5,7 @@ import ExerciseManager from '../managers/ExerciseManager'; ...@@ -5,6 +5,7 @@ import ExerciseManager from '../managers/ExerciseManager';
import AssignmentManager from '../managers/AssignmentManager'; import AssignmentManager from '../managers/AssignmentManager';
import TagManager from '../managers/TagManager'; import TagManager from '../managers/TagManager';
import TagProposalManager from '../managers/TagProposalManager'; import TagProposalManager from '../managers/TagProposalManager';
import UserManager from '../managers/UserManager';
type GetFunction = (id: string | number, ...args: Array<unknown>) => Promise<unknown> type GetFunction = (id: string | number, ...args: Array<unknown>) => Promise<unknown>
...@@ -29,6 +30,7 @@ class ParamsCallbackManager { ...@@ -29,6 +30,7 @@ class ParamsCallbackManager {
initBoundParams(req: express.Request) { initBoundParams(req: express.Request) {
if ( !req.boundParams ) { if ( !req.boundParams ) {
req.boundParams = { req.boundParams = {
user : undefined,
assignment : undefined, assignment : undefined,
exercise : undefined, exercise : undefined,
tag : undefined, tag : undefined,
...@@ -38,13 +40,31 @@ class ParamsCallbackManager { ...@@ -38,13 +40,31 @@ class ParamsCallbackManager {
} }
registerOnBackend(backend: Express) { registerOnBackend(backend: Express) {
this.listenParam('userId', backend, (UserManager.getById as GetFunction).bind(UserManager), [ {
assignments: true,
exercises : {
include: {
members : true,
assignment: {
include: {
staff: true
}
}
}
}
} ], 'user');
this.listenParam('assignmentNameOrUrl', backend, (AssignmentManager.get as GetFunction).bind(AssignmentManager), [ { this.listenParam('assignmentNameOrUrl', backend, (AssignmentManager.get as GetFunction).bind(AssignmentManager), [ {
exercises: true, exercises: true,
staff : true staff : true
} ], 'assignment'); } ], 'assignment');
this.listenParam('exerciseIdOrUrl', backend, (ExerciseManager.get as GetFunction).bind(ExerciseManager), [ { this.listenParam('exerciseIdOrUrl', backend, (ExerciseManager.get as GetFunction).bind(ExerciseManager), [ {
assignment: true, assignment: {
include: {
staff: true
}
},
members : true, members : true,
results : true results : true
} ], 'exercise'); } ], 'exercise');
......
...@@ -6,6 +6,7 @@ import AssignmentRoutes from './AssignmentRoutes.js'; ...@@ -6,6 +6,7 @@ import AssignmentRoutes from './AssignmentRoutes.js';
import GitlabRoutes from './GitlabRoutes.js'; import GitlabRoutes from './GitlabRoutes.js';
import ExerciseRoutes from './ExerciseRoutes.js'; import ExerciseRoutes from './ExerciseRoutes.js';
import TagsRoutes from './TagRoutes'; import TagsRoutes from './TagRoutes';
import UserRoutes from './UserRoutes';
class AdminRoutesManager implements RoutesManager { class AdminRoutesManager implements RoutesManager {
...@@ -16,6 +17,7 @@ class AdminRoutesManager implements RoutesManager { ...@@ -16,6 +17,7 @@ class AdminRoutesManager implements RoutesManager {
AssignmentRoutes.registerOnBackend(backend); AssignmentRoutes.registerOnBackend(backend);
ExerciseRoutes.registerOnBackend(backend); ExerciseRoutes.registerOnBackend(backend);
TagsRoutes.registerOnBackend(backend); TagsRoutes.registerOnBackend(backend);
UserRoutes.registerOnBackend(backend);
} }
} }
......
...@@ -70,20 +70,68 @@ class ExerciseRoutes implements RoutesManager { ...@@ -70,20 +70,68 @@ class ExerciseRoutes implements RoutesManager {
backend.get('/exercises', SecurityMiddleware.check(true, SecurityCheckType.ADMIN), this.getAllExercises.bind(this) as RequestHandler); backend.get('/exercises', SecurityMiddleware.check(true, SecurityCheckType.ADMIN), this.getAllExercises.bind(this) as RequestHandler);
backend.get('/exercises/:exerciseIdOrUrl/assignment', SecurityMiddleware.check(false, SecurityCheckType.EXERCISE_SECRET), this.getAssignment.bind(this) as RequestHandler); backend.get('/exercises/:exerciseIdOrUrl/assignment', SecurityMiddleware.check(false, SecurityCheckType.EXERCISE_SECRET), this.getAssignment.bind(this) as RequestHandler);
backend.get('/exercises/:exerciseIdOrUrl', SecurityMiddleware.check(true, SecurityCheckType.ADMIN, SecurityCheckType.EXERCISE_MEMBERS), this.getExercise.bind(this) as RequestHandler);
backend.get('/exercises/:exerciseIdOrUrl/members', SecurityMiddleware.check(true, SecurityCheckType.ADMIN, SecurityCheckType.EXERCISE_MEMBERS), this.getExerciseMembers.bind(this) as RequestHandler); backend.get('/exercises/:exerciseIdOrUrl/members', SecurityMiddleware.check(true, SecurityCheckType.ADMIN, SecurityCheckType.EXERCISE_MEMBERS), this.getExerciseMembers.bind(this) as RequestHandler);
backend.get('/exercises/:exerciseIdOrUrl/results', SecurityMiddleware.check(true, SecurityCheckType.ADMIN, SecurityCheckType.EXERCISE_MEMBERS), this.getExerciseResults.bind(this) as RequestHandler); backend.get('/exercises/:exerciseIdOrUrl/results', SecurityMiddleware.check(true, SecurityCheckType.ADMIN, SecurityCheckType.EXERCISE_MEMBERS), this.getExerciseResults.bind(this) as RequestHandler);
backend.delete('/exercises/:exerciseIdOrUrl', SecurityMiddleware.check(true, SecurityCheckType.ADMIN, SecurityCheckType.EXERCISE_MEMBERS), this.deleteExercise.bind(this) as RequestHandler); backend.delete('/exercises/:exerciseIdOrUrl', SecurityMiddleware.check(true, SecurityCheckType.ADMIN, SecurityCheckType.EXERCISE_MEMBERS), this.deleteExercise.bind(this) as RequestHandler);
backend.get('/users/:userId/exercises', SecurityMiddleware.check(true), this.getUserExercises.bind(this) as RequestHandler);
backend.get('/exercises/:exerciseIdOrLink/results', SecurityMiddleware.check(true), this.getExerciseResultsByIdOrLink.bind(this) as RequestHandler);
backend.post('/exercises/:exerciseIdOrUrl/results', SecurityMiddleware.check(false, SecurityCheckType.EXERCISE_SECRET), ParamsValidatorMiddleware.validate(this.resultValidator), this.createResult.bind(this) as RequestHandler); backend.post('/exercises/:exerciseIdOrUrl/results', SecurityMiddleware.check(false, SecurityCheckType.EXERCISE_SECRET), ParamsValidatorMiddleware.validate(this.resultValidator), this.createResult.bind(this) as RequestHandler);
} }
private async getExerciseResultsByIdOrLink(req: express.Request, res: express.Response) {
const exerciseIdOrLink = req.params.exerciseIdOrLink;
const exercise = await db.exercise.findFirst({
where: {
OR: [ { id: exerciseIdOrLink }, { gitlabLink: exerciseIdOrLink } ]
}
});
if ( !exercise ) {
return res.status(StatusCodes.NOT_FOUND).send('Exercise not found');
}
const results = await db.result.findMany({
where: { exerciseId: exercise.id }
});
return res.status(StatusCodes.OK).json(results);
}
private async getAllExercises(req: express.Request, res: express.Response) {
const exos = await db.exercise.findMany();
return req.session.sendResponse(res, StatusCodes.OK, exos);
}
private async getUserExercises(req: express.Request, res: express.Response) {
if ( req.boundParams.user ) {
if ( req.session.profile.isAdmin || req.session.profile.id === req.boundParams.user.id ) {
return req.session.sendResponse(res, StatusCodes.OK, req.boundParams.user.exercises.filter(exercise => !exercise.deleted));
} else {
return req.session.sendResponse(res, StatusCodes.FORBIDDEN);
}
} else {
return req.session.sendResponse(res, StatusCodes.NOT_FOUND);
}
}
private getExerciseName(assignment: Assignment, members: Array<Gitlab.UserSchema>, suffix: number): string { private getExerciseName(assignment: Assignment, members: Array<Gitlab.UserSchema>, suffix: number): string {
const memberNames: string = members.map(member => member.username).sort((a, b) => a.localeCompare(b)).join(' + '); const memberNames: string = members.map(member => member.username).sort((a, b) => a.localeCompare(b)).join(' + ');
const suffixString: string = suffix > 0 ? ` - ${ suffix }` : ''; const suffixString: string = suffix > 0 ? ` - ${ suffix }` : '';
return `DojoEx - ${ assignment.name } - ${ memberNames }${ suffixString }`; return `DojoEx - ${ assignment.name } - ${ memberNames }${ suffixString }`;
} }
private async getExercise(req: express.Request, res: express.Response) {
return req.session.sendResponse(res, StatusCodes.OK, req.boundParams.exercise!);
}
private async getExerciseMembers(req: express.Request, res: express.Response) { private async getExerciseMembers(req: express.Request, res: express.Response) {
const repoId = req.boundParams.exercise!.gitlabId; const repoId = req.boundParams.exercise!.gitlabId;
...@@ -133,13 +181,6 @@ class ExerciseRoutes implements RoutesManager { ...@@ -133,13 +181,6 @@ class ExerciseRoutes implements RoutesManager {
return `dojo-ex_${ (assignment.gitlabLastInfo as unknown as Gitlab.ProjectSchema).path }_${ exerciseId }`; return `dojo-ex_${ (assignment.gitlabLastInfo as unknown as Gitlab.ProjectSchema).path }_${ exerciseId }`;
} }
// Get all exercise
private async getAllExercises(req: express.Request, res: express.Response) {
const exos = await db.exercise.findMany();
return req.session.sendResponse(res, StatusCodes.OK, exos);
}
private async checkExerciseLimit(assignment: Assignment, members: Array<Gitlab.UserSchema>): Promise<Array<Gitlab.UserSchema>> { private async checkExerciseLimit(assignment: Assignment, members: Array<Gitlab.UserSchema>): Promise<Array<Gitlab.UserSchema>> {
const exercises: Array<Exercise> | undefined = await ExerciseManager.getFromAssignment(assignment.name, false, { members: true }); const exercises: Array<Exercise> | undefined = await ExerciseManager.getFromAssignment(assignment.name, false, { members: true });
...@@ -225,33 +266,42 @@ class ExerciseRoutes implements RoutesManager { ...@@ -225,33 +266,42 @@ class ExerciseRoutes implements RoutesManager {
await repoCreationFnExec(async () => Promise.all([ ...new Set([ ...assignment.staff, ...params.members ].map(member => member.id)) ].map(GlobalHelper.addRepoMember(repository.id))), 'Add repository members error'); await repoCreationFnExec(async () => Promise.all([ ...new Set([ ...assignment.staff, ...params.members ].map(member => member.id)) ].map(GlobalHelper.addRepoMember(repository.id))), 'Add repository members error');
const exercise: Exercise = await repoCreationFnExec(() => db.exercise.create({ let exercise: Exercise = await repoCreationFnExec(() => db.exercise.create({
data: { data: {
id : exerciseId, id : exerciseId,
assignmentName : assignment.name, assignmentName : assignment.name,
name : repository.name, name : repository.name,
secret : secret, secret : secret,
gitlabId : repository.id, gitlabId : repository.id,
gitlabLink : repository.web_url, gitlabLink : repository.web_url,
gitlabCreationInfo: repository as unknown as Prisma.JsonObject, gitlabCreationInfo: repository as unknown as Prisma.JsonObject,
gitlabCreationDate: new Date(), gitlabCreationDate: new Date(),
gitlabLastInfo : repository as unknown as Prisma.JsonObject, gitlabLastInfo : repository as unknown as Prisma.JsonObject,
gitlabLastInfoDate: new Date(), gitlabLastInfoDate: new Date(),
members : { members : {
connectOrCreate: [ ...params.members.map(gitlabUser => { connectOrCreate: [ ...params.members.map(gitlabUser => {
return { return {
create: { create: {
id : gitlabUser.id, id : gitlabUser.id,
gitlabUsername: gitlabUser.name gitlabUsername: gitlabUser.name
}, },
where : { where : {
id: gitlabUser.id id: gitlabUser.id
} }
}; };
}) ] }) ]
} }
} }
})) as Exercise; })) as Exercise;
exercise = await ExerciseManager.get(exercise.id, {
members : true,
assignment: {
include: {
staff: true
}
}
}) as Exercise;
req.session.sendResponse(res, StatusCodes.OK, exercise); req.session.sendResponse(res, StatusCodes.OK, exercise);
return; return;
......
import { Express } from 'express-serve-static-core';
import express, { RequestHandler } from 'express';
import { StatusCodes } from 'http-status-codes';
import RoutesManager from '../express/RoutesManager.js';
import SecurityMiddleware from '../middlewares/SecurityMiddleware';
import * as ExpressValidator from 'express-validator';
import ParamsValidatorMiddleware from '../middlewares/ParamsValidatorMiddleware';
import { Prisma, UserRole } from '@prisma/client';
import UserManager from '../managers/UserManager';
class UserRoutes implements RoutesManager {
private readonly usersGetValidator: ExpressValidator.Schema = {
role: {
trim : true,
notEmpty: false,
optional: true
}
};
registerOnBackend(backend: Express) {
backend.get('/users', SecurityMiddleware.check(true), ParamsValidatorMiddleware.validate(this.usersGetValidator), this.getUsers.bind(this) as RequestHandler);
}
private async getUsers(req: express.Request, res: express.Response) {
let roleFilter: Prisma.UserWhereInput | undefined = undefined;
if ( req.query.role ) {
if ( req.query.role === UserRole.ADMIN ) {
roleFilter = {
role: UserRole.ADMIN
};
} else if ( req.query.role === UserRole.TEACHING_STAFF ) {
roleFilter = {
OR: [ {
role: UserRole.ADMIN
}, {
role: UserRole.TEACHING_STAFF
} ]
};
} else if ( req.query.role === UserRole.STUDENT ) {
roleFilter = {
role: UserRole.STUDENT
};
} else {
return req.session.sendResponse(res, StatusCodes.FORBIDDEN);
}
} else if ( !req.session.profile.isAdmin ) {
return req.session.sendResponse(res, StatusCodes.FORBIDDEN);
}
return req.session.sendResponse(res, StatusCodes.OK, await UserManager.getFiltered(roleFilter));
}
}
export default new UserRoutes();
import Session from '../../controllers/Session.js'; import Session from '../../controllers/Session.js';
import { Assignment, Exercise, Tag } from '../DatabaseTypes'; import { Assignment, Exercise, Tag, User } from '../DatabaseTypes';
import { TagProposal } from '@prisma/client'; import { TagProposal } from '@prisma/client';
// to make the file a module and avoid the TypeScript error // to make the file a module and avoid the TypeScript error
export {}; export {};
...@@ -10,7 +10,7 @@ declare global { ...@@ -10,7 +10,7 @@ declare global {
export interface Request { export interface Request {
session: Session, session: Session,
boundParams: { boundParams: {
assignment: Assignment | undefined, exercise: Exercise | undefined, tag: Tag | undefined, tagProposal: TagProposal | undefined user: User | undefined, assignment: Assignment | undefined, exercise: Exercise | undefined, tag: Tag | undefined, tagProposal: TagProposal | undefined
} }
} }
} }
......