diff --git a/backend/src/controllers/assignments.ts b/backend/src/controllers/assignments.ts index 1520fc10..2750e3d8 100644 --- a/backend/src/controllers/assignments.ts +++ b/backend/src/controllers/assignments.ts @@ -1,6 +1,8 @@ import { Request, Response } from 'express'; import { createAssignment, getAllAssignments, getAssignment, getAssignmentsSubmissions } from '../services/assignments.js'; import { AssignmentDTO } from '@dwengo-1/common/interfaces/assignment'; +import {requireFields} from "./error-helper"; +import {BadRequestException} from "../exceptions/bad-request-exception"; // Typescript is annoying with parameter forwarding from class.ts interface AssignmentParams { @@ -9,69 +11,55 @@ interface AssignmentParams { } export async function getAllAssignmentsHandler(req: Request, res: Response): Promise { - const classid = req.params.classid; + const classId = req.params.classid; const full = req.query.full === 'true'; + requireFields({ classId }); - const assignments = await getAllAssignments(classid, full); + const assignments = await getAllAssignments(classId, full); - res.json({ - assignments: assignments, - }); + res.json({ assignments }); } export async function createAssignmentHandler(req: Request, res: Response): Promise { const classid = req.params.classid; - const assignmentData = req.body as AssignmentDTO; + const description = req.body.description; + const language = req.body.language; + const learningPath = req.body.learningPath; + const title = req.body.title; - if (!assignmentData.description || !assignmentData.language || !assignmentData.learningPath || !assignmentData.title) { - res.status(400).json({ - error: 'Missing one or more required fields: title, description, learningPath, language', - }); - return; - } + requireFields({ description, language, learningPath, title }); + const assignmentData = req.body as AssignmentDTO; const assignment = await createAssignment(classid, assignmentData); - if (!assignment) { - res.status(500).json({ error: 'Could not create assignment ' }); - return; - } - - res.status(201).json(assignment); + res.json({ assignment }); } export async function getAssignmentHandler(req: Request, res: Response): Promise { const id = Number(req.params.id); const classid = req.params.classid; + requireFields({ id, classid }); if (isNaN(id)) { - res.status(400).json({ error: 'Assignment id must be a number' }); - return; + throw new BadRequestException("Assignment id should be a number") } const assignment = await getAssignment(classid, id); - if (!assignment) { - res.status(404).json({ error: 'Assignment not found' }); - return; - } - - res.json(assignment); + res.json({ assignment }); } export async function getAssignmentsSubmissionsHandler(req: Request, res: Response): Promise { const classid = req.params.classid; const assignmentNumber = Number(req.params.id); const full = req.query.full === 'true'; + requireFields({ assignmentNumber, classid }); if (isNaN(assignmentNumber)) { - res.status(400).json({ error: 'Assignment id must be a number' }); - return; + throw new BadRequestException("Assignment id should be a number") } const submissions = await getAssignmentsSubmissions(classid, assignmentNumber, full); - res.json({ - submissions: submissions, - }); + res.json({ submissions }); } diff --git a/backend/src/services/assignments.ts b/backend/src/services/assignments.ts index e86b69b2..fa8e2380 100644 --- a/backend/src/services/assignments.ts +++ b/backend/src/services/assignments.ts @@ -3,15 +3,12 @@ import { mapToAssignment, mapToAssignmentDTO, mapToAssignmentDTOId } from '../in import { mapToSubmissionDTO, mapToSubmissionDTOId } from '../interfaces/submission.js'; import { AssignmentDTO } from '@dwengo-1/common/interfaces/assignment'; import { SubmissionDTO, SubmissionDTOId } from '@dwengo-1/common/interfaces/submission'; -import { getLogger } from '../logging/initalize.js'; +import {fetchClass} from "./classes"; +import {Assignment} from "../entities/assignments/assignment.entity"; +import {NotFoundException} from "../exceptions/not-found-exception"; export async function getAllAssignments(classid: string, full: boolean): Promise { - const classRepository = getClassRepository(); - const cls = await classRepository.findById(classid); - - if (!cls) { - return []; - } + const cls = await fetchClass(classid); const assignmentRepository = getAssignmentRepository(); const assignments = await assignmentRepository.findAllAssignmentsInClass(cls); @@ -23,43 +20,34 @@ export async function getAllAssignments(classid: string, full: boolean): Promise return assignments.map(mapToAssignmentDTOId); } -export async function createAssignment(classid: string, assignmentData: AssignmentDTO): Promise { - const classRepository = getClassRepository(); - const cls = await classRepository.findById(classid); - - if (!cls) { - return null; - } +export async function createAssignment(classid: string, assignmentData: AssignmentDTO): Promise { + const cls = await fetchClass(classid); const assignment = mapToAssignment(assignmentData, cls); const assignmentRepository = getAssignmentRepository(); - try { - const newAssignment = assignmentRepository.create(assignment); - await assignmentRepository.save(newAssignment); + const newAssignment = assignmentRepository.create(assignment); + await assignmentRepository.save(newAssignment, {preventOverwrite: true}); + + return mapToAssignmentDTO(newAssignment); - return mapToAssignmentDTO(newAssignment); - } catch (e) { - getLogger().error(e); - return null; - } } -export async function getAssignment(classid: string, id: number): Promise { - const classRepository = getClassRepository(); - const cls = await classRepository.findById(classid); - - if (!cls) { - return null; - } +export async function fetchAssignment(classid: string, id: number): Promise { + const cls = await fetchClass(classid); const assignmentRepository = getAssignmentRepository(); const assignment = await assignmentRepository.findByClassAndId(cls, id); - if (!assignment) { - return null; + if (!assignment){ + throw new NotFoundException('Assignment with id not found'); } + return assignment; +} + +export async function getAssignment(classid: string, id: number): Promise { + const assignment = await fetchAssignment(classid, id); return mapToAssignmentDTO(assignment); } @@ -68,23 +56,15 @@ export async function getAssignmentsSubmissions( assignmentNumber: number, full: boolean ): Promise { - const classRepository = getClassRepository(); - const cls = await classRepository.findById(classid); - - if (!cls) { - return []; - } - - const assignmentRepository = getAssignmentRepository(); - const assignment = await assignmentRepository.findByClassAndId(cls, assignmentNumber); - - if (!assignment) { - return []; - } + const assignment = await fetchAssignment(classid, assignmentNumber); const groupRepository = getGroupRepository(); const groups = await groupRepository.findAllGroupsForAssignment(assignment); + if (groups.length === 0){ + throw new NotFoundException('No groups for assignment found'); + } + const submissionRepository = getSubmissionRepository(); const submissions = (await Promise.all(groups.map(async (group) => submissionRepository.findAllSubmissionsForGroup(group)))).flat();