From fb0230027421cf29b5f3726f2d18c8d8cdd2a4ca Mon Sep 17 00:00:00 2001 From: Timo De Meyst Date: Mon, 14 Apr 2025 10:59:59 +0200 Subject: [PATCH 01/49] feat: assignment label bij leerpaden die opdrachten zijn --- .../views/learning-paths/LearningPathPage.vue | 18 ++++++++++++++++++ 1 file changed, 18 insertions(+) diff --git a/frontend/src/views/learning-paths/LearningPathPage.vue b/frontend/src/views/learning-paths/LearningPathPage.vue index 2a86d08d..19c8be04 100644 --- a/frontend/src/views/learning-paths/LearningPathPage.vue +++ b/frontend/src/views/learning-paths/LearningPathPage.vue @@ -168,6 +168,10 @@ + +
+ ASSIGNMENT +
From d0c6e13944b4d5dc27648cdd7099e5c051656e15 Mon Sep 17 00:00:00 2001 From: laurejablonski Date: Mon, 21 Apr 2025 16:47:54 +0200 Subject: [PATCH 02/49] fix: onnodige router verwijderd --- backend/src/routes/assignments.ts | 6 ------ 1 file changed, 6 deletions(-) diff --git a/backend/src/routes/assignments.ts b/backend/src/routes/assignments.ts index 083ee586..5b9ed7c6 100644 --- a/backend/src/routes/assignments.ts +++ b/backend/src/routes/assignments.ts @@ -23,12 +23,6 @@ router.delete('/:id', deleteAssignmentHandler); router.get('/:id/submissions', getAssignmentsSubmissionsHandler); -router.get('/:id/questions', (_req, res) => { - res.json({ - questions: ['0'], - }); -}); - router.use('/:assignmentid/groups', groupRouter); export default router; From ad63cde3b40d03a874d295a6e277963f9d9f3c8c Mon Sep 17 00:00:00 2001 From: Timo De Meyst Date: Mon, 21 Apr 2025 21:51:54 +0200 Subject: [PATCH 03/49] feat: checken of leerpaden assignments zijn --- .../views/learning-paths/LearningPathPage.vue | 42 ++++++++++++++++++- 1 file changed, 41 insertions(+), 1 deletion(-) diff --git a/frontend/src/views/learning-paths/LearningPathPage.vue b/frontend/src/views/learning-paths/LearningPathPage.vue index 19c8be04..cd42a8d8 100644 --- a/frontend/src/views/learning-paths/LearningPathPage.vue +++ b/frontend/src/views/learning-paths/LearningPathPage.vue @@ -12,6 +12,9 @@ import UsingQueryResult from "@/components/UsingQueryResult.vue"; import authService from "@/services/auth/auth-service.ts"; import { LearningPathNode } from "@/data-objects/learning-paths/learning-path-node.ts"; +import { useStudentAssignmentsQuery } from "@/queries/students"; +import type { AssignmentDTO } from "@dwengo-1/common/interfaces/assignment"; +import { watch } from "vue"; const route = useRoute(); const { t } = useI18n(); @@ -98,6 +101,43 @@ } return "notCompleted"; } + + //TODO: berekenen of het een assignment is voor de student werkt nog niet zoals het hoort... + + const studentAssignmentsQuery = useStudentAssignmentsQuery(authService.authState.user?.profile?.preferred_username); + + watch( + () => authService.authState.user?.profile?.preferred_username, + (newUsername) => { + if (newUsername) { + studentAssignmentsQuery.refetch(); + } + } + ); + + const isAssignmentForStudent = computed(() => { + // Check if the user is a student + const isStudent = authService.authState.activeRole === "student"; + + if (isStudent && studentAssignmentsQuery.isSuccess) { + // Use the query to fetch assignments for the current student + console.log("Query Result:", studentAssignmentsQuery.data?.value); + + // Check if the query is successful and contains the current learning path + const isAssignment = (studentAssignmentsQuery.data?.value?.assignments as AssignmentDTO[]).some( + (assignment: AssignmentDTO) => { + console.log(assignment.learningPath) + return assignment.learningPath === props.hruid + } + ); + + // Return true only if the user is a student and the learning path is an assignment + return isAssignment; + } + + return false; + }); + From 8751eec006838b6fb32b3f08679ac44e70803392 Mon Sep 17 00:00:00 2001 From: Timo De Meyst Date: Tue, 22 Apr 2025 09:05:30 +0200 Subject: [PATCH 11/49] feat: leerpad vraag layout --- .../views/learning-paths/LearningPathPage.vue | 75 ++++++++++++++++++- 1 file changed, 74 insertions(+), 1 deletion(-) diff --git a/frontend/src/views/learning-paths/LearningPathPage.vue b/frontend/src/views/learning-paths/LearningPathPage.vue index cd42a8d8..38c9e409 100644 --- a/frontend/src/views/learning-paths/LearningPathPage.vue +++ b/frontend/src/views/learning-paths/LearningPathPage.vue @@ -138,6 +138,11 @@ import { watch } from "vue"; return false; }); + function submitQuestion() { + // Replace with actual submission logic + alert(`Submitted`); + } + -
- -
- ASSIGNMENT + +
+ ASSIGNMENT +
+
@@ -277,7 +278,7 @@ v-if="currentNode" >
-
+
Date: Wed, 23 Apr 2025 22:27:12 +0200 Subject: [PATCH 18/49] i18n: assignment indicator beschikbaar in verschillende talen --- frontend/src/i18n/locale/de.json | 3 ++- frontend/src/i18n/locale/en.json | 3 ++- frontend/src/i18n/locale/fr.json | 3 ++- frontend/src/i18n/locale/nl.json | 3 ++- frontend/src/views/learning-paths/LearningPathPage.vue | 2 +- 5 files changed, 9 insertions(+), 5 deletions(-) diff --git a/frontend/src/i18n/locale/de.json b/frontend/src/i18n/locale/de.json index f79af679..b0bf13fe 100644 --- a/frontend/src/i18n/locale/de.json +++ b/frontend/src/i18n/locale/de.json @@ -100,5 +100,6 @@ "accepted": "akzeptiert", "enterUsername": "Geben Sie den Benutzernamen der Lehrkraft ein, die Sie einladen möchten", "username": "Nutzername", - "invite": "einladen" + "invite": "einladen", + "assignmentIndicator": "AUFGABE" } diff --git a/frontend/src/i18n/locale/en.json b/frontend/src/i18n/locale/en.json index 5bcc44c0..259195a6 100644 --- a/frontend/src/i18n/locale/en.json +++ b/frontend/src/i18n/locale/en.json @@ -100,5 +100,6 @@ "rejected": "rejected", "enterUsername": "enter the username of the teacher you would like to invite", "username": "username", - "invite": "invite" + "invite": "invite", + "assignmentIndicator": "ASSIGNMENT" } diff --git a/frontend/src/i18n/locale/fr.json b/frontend/src/i18n/locale/fr.json index c5ecc6b7..aac60a58 100644 --- a/frontend/src/i18n/locale/fr.json +++ b/frontend/src/i18n/locale/fr.json @@ -100,5 +100,6 @@ "rejected": "rejetée", "enterUsername": "entrez le nom d'utilisateur de l'enseignant que vous souhaitez inviter", "username": "Nom d'utilisateur", - "invite": "inviter" + "invite": "inviter", + "assignmentIndicator": "DEVOIR" } diff --git a/frontend/src/i18n/locale/nl.json b/frontend/src/i18n/locale/nl.json index 62f027ac..bfb8d61b 100644 --- a/frontend/src/i18n/locale/nl.json +++ b/frontend/src/i18n/locale/nl.json @@ -100,5 +100,6 @@ "rejected": "geweigerd", "enterUsername": "vul de gebruikersnaam van de leerkracht die je wilt uitnodigen in", "username": "gebruikersnaam", - "invite": "uitnodigen" + "invite": "uitnodigen", + "assignmentIndicator": "OPDRACHT" } diff --git a/frontend/src/views/learning-paths/LearningPathPage.vue b/frontend/src/views/learning-paths/LearningPathPage.vue index 0cc24c74..d311f36f 100644 --- a/frontend/src/views/learning-paths/LearningPathPage.vue +++ b/frontend/src/views/learning-paths/LearningPathPage.vue @@ -253,7 +253,7 @@
- ASSIGNMENT + {{ t("assignmentIndicator") }}
From 95715728e4ec4bde2c212026c96d867f8c928387 Mon Sep 17 00:00:00 2001 From: Timo De Meyst Date: Thu, 24 Apr 2025 01:07:29 +0200 Subject: [PATCH 19/49] feat: submit vraag (POST response zegt dat hier nog een fout zit) --- .../views/learning-paths/LearningPathPage.vue | 43 ++++++++++++++++--- 1 file changed, 37 insertions(+), 6 deletions(-) diff --git a/frontend/src/views/learning-paths/LearningPathPage.vue b/frontend/src/views/learning-paths/LearningPathPage.vue index d311f36f..5de19524 100644 --- a/frontend/src/views/learning-paths/LearningPathPage.vue +++ b/frontend/src/views/learning-paths/LearningPathPage.vue @@ -13,13 +13,14 @@ import authService from "@/services/auth/auth-service.ts"; import { LearningPathNode } from "@/data-objects/learning-paths/learning-path-node.ts"; import LearningPathGroupSelector from "@/views/learning-paths/LearningPathGroupSelector.vue"; - import { useQuestionsQuery } from "@/queries/questions"; + import { useCreateQuestionMutation, useQuestionsQuery } from "@/queries/questions"; import type { QuestionsResponse } from "@/controllers/questions"; import type { LearningObjectIdentifierDTO } from "@dwengo-1/common/interfaces/learning-content"; import QandA from "@/components/QandA.vue"; - import type { QuestionDTO } from "@dwengo-1/common/interfaces/question"; - import {useStudentAssignmentsQuery} from "@/queries/students" + import type { QuestionData, QuestionDTO } from "@dwengo-1/common/interfaces/question"; + import {useStudentAssignmentsQuery, useStudentGroupsQuery} from "@/queries/students" import type { AssignmentDTO } from "@dwengo-1/common/interfaces/assignment"; +import type { GroupDTO } from "@dwengo-1/common/interfaces/group"; const router = useRouter(); const route = useRoute(); @@ -153,10 +154,39 @@ assignment.language === props.language ); }); - + + const loID:LearningObjectIdentifierDTO = { + hruid: props.learningObjectHruid as string, + language: props.language + } + const createQuestionMutation = useCreateQuestionMutation(loID) + const groupsQueryResult = useStudentGroupsQuery(authService.authState.user?.profile.preferred_username) + + const questionInput = ref(""); + function submitQuestion() { - // Replace with actual submission logic - alert(`Submitted`); + const assignments = studentAssignmentsQueryResult.data.value?.assignments as AssignmentDTO[] + const assignment = assignments.find( + (assignment) => + assignment.learningPath === props.hruid && + assignment.language === props.language + ) + const groups = groupsQueryResult.data.value?.groups as GroupDTO[] + const group = groups?.find(group => group.assignment === assignment?.id) as GroupDTO + const questionData:QuestionData = { + author: authService.authState.user?.profile.preferred_username, + content: questionInput.value, + inGroup: group //TODO: POST response zegt dat dit null is??? + } + createQuestionMutation.mutate(questionData, { + onSuccess: () => { + questionInput.value = "question:..."; // Clear the input field after submission + }, + onError: (e) => { + console.error(e) + questionInput.value = ""; // Clear the input field after submission + }, + }) } @@ -284,6 +314,7 @@ type="text" placeholder="question : ..." class="question-input" + v-model="questionInput" />
From 5c6e0b8554e0c8370885604ee87974494c990985 Mon Sep 17 00:00:00 2001 From: Gabriellvl Date: Thu, 24 Apr 2025 15:18:00 +0200 Subject: [PATCH 20/49] fix: assignment opvragen met andere types --- backend/src/services/questions.ts | 15 +++++++++++++-- 1 file changed, 13 insertions(+), 2 deletions(-) diff --git a/backend/src/services/questions.ts b/backend/src/services/questions.ts index a16c277b..a84f59a5 100644 --- a/backend/src/services/questions.ts +++ b/backend/src/services/questions.ts @@ -12,6 +12,8 @@ import { AssignmentDTO } from '@dwengo-1/common/interfaces/assignment'; import { fetchStudent } from './students.js'; import { NotFoundException } from '../exceptions/not-found-exception.js'; import { FALLBACK_VERSION_NUM } from '../config.js'; +import {fetchClass} from "./classes"; +import {fetchAssignment} from "./assignments"; export async function getQuestionsAboutLearningObjectInAssignment( loId: LearningObjectIdentifier, @@ -86,8 +88,17 @@ export async function createQuestion(loId: LearningObjectIdentifier, questionDat const author = await fetchStudent(questionData.author!); const content = questionData.content; - const clazz = await getClassRepository().findById((questionData.inGroup.assignment as AssignmentDTO).within); - const assignment = mapToAssignment(questionData.inGroup.assignment as AssignmentDTO, clazz!); + let assignment; + + if (questionData.inGroup.assignment instanceof Number && questionData.inGroup.class instanceof String) { + assignment = await fetchAssignment(questionData.inGroup.class as string, + questionData.inGroup.assignment as number); + } else { + // TODO check if necessary and no conflicts to delete this if + const clazz = await getClassRepository().findById((questionData.inGroup.assignment as AssignmentDTO).within); + assignment = mapToAssignment(questionData.inGroup.assignment as AssignmentDTO, clazz!); + } + const inGroup = await getGroupRepository().findByAssignmentAndGroupNumber(assignment, questionData.inGroup.groupNumber); const question = await questionRepository.createQuestion({ From 2b21cf4c53016f72ff1aded75a78a46c0022ba6c Mon Sep 17 00:00:00 2001 From: Timo De Meyst Date: Thu, 24 Apr 2025 15:42:09 +0200 Subject: [PATCH 21/49] feat: verplicht de gebruiker om een vraag te typen voordat hij submit --- .../views/learning-paths/LearningPathPage.vue | 24 ++++++++++++------- 1 file changed, 15 insertions(+), 9 deletions(-) diff --git a/frontend/src/views/learning-paths/LearningPathPage.vue b/frontend/src/views/learning-paths/LearningPathPage.vue index 5de19524..e329b4f9 100644 --- a/frontend/src/views/learning-paths/LearningPathPage.vue +++ b/frontend/src/views/learning-paths/LearningPathPage.vue @@ -178,15 +178,21 @@ import type { GroupDTO } from "@dwengo-1/common/interfaces/group"; content: questionInput.value, inGroup: group //TODO: POST response zegt dat dit null is??? } - createQuestionMutation.mutate(questionData, { - onSuccess: () => { - questionInput.value = "question:..."; // Clear the input field after submission - }, - onError: (e) => { - console.error(e) - questionInput.value = ""; // Clear the input field after submission - }, - }) + console.log(questionData) + if (questionInput.value != "") { + createQuestionMutation.mutate(questionData, { + onSuccess: () => { + questionInput.value = "question:..."; // Clear the input field after submission + }, + onError: (e) => { + console.error(e) + questionInput.value = ""; // Clear the input field after submission + }, + }) + } else { + alert("Please type a question before submitting.") + } + } From d37d3b6eac93c9461d80a167f020666abe43b371 Mon Sep 17 00:00:00 2001 From: Timo De Meyst Date: Thu, 24 Apr 2025 16:17:56 +0200 Subject: [PATCH 22/49] fix: branch werd niet genomen door instanceof ipv typeof --- backend/src/services/questions.ts | 11 ++++++++--- 1 file changed, 8 insertions(+), 3 deletions(-) diff --git a/backend/src/services/questions.ts b/backend/src/services/questions.ts index a84f59a5..766d28fa 100644 --- a/backend/src/services/questions.ts +++ b/backend/src/services/questions.ts @@ -90,7 +90,7 @@ export async function createQuestion(loId: LearningObjectIdentifier, questionDat let assignment; - if (questionData.inGroup.assignment instanceof Number && questionData.inGroup.class instanceof String) { + if ((typeof questionData.inGroup.assignment === "number") && (typeof questionData.inGroup.class === "string")) { assignment = await fetchAssignment(questionData.inGroup.class as string, questionData.inGroup.assignment as number); } else { @@ -100,14 +100,19 @@ export async function createQuestion(loId: LearningObjectIdentifier, questionDat } const inGroup = await getGroupRepository().findByAssignmentAndGroupNumber(assignment, questionData.inGroup.groupNumber); - + const question = await questionRepository.createQuestion({ loId, author, inGroup: inGroup!, content, }); - + console.log() + console.log(loId) + console.log(author) + console.log(inGroup) + console.log(content) + console.log(question) return mapToQuestionDTO(question); } From c344e5e9242d48fe49fc480525438f465b706b8b Mon Sep 17 00:00:00 2001 From: Timo De Meyst Date: Thu, 24 Apr 2025 16:18:04 +0200 Subject: [PATCH 23/49] fix: missing await --- backend/src/data/questions/question-repository.ts | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/backend/src/data/questions/question-repository.ts b/backend/src/data/questions/question-repository.ts index 362ec4c9..941bca79 100644 --- a/backend/src/data/questions/question-repository.ts +++ b/backend/src/data/questions/question-repository.ts @@ -24,7 +24,8 @@ export class QuestionRepository extends DwengoEntityRepository { questionEntity.author = question.author; questionEntity.inGroup = question.inGroup; questionEntity.content = question.content; - return this.insert(questionEntity); + await this.insert(questionEntity); + return questionEntity; } public async findAllQuestionsAboutLearningObject(loId: LearningObjectIdentifier): Promise { return this.findAll({ From 9bc0c59249852c1384ec5507a14bef306872bd5d Mon Sep 17 00:00:00 2001 From: Timo De Meyst Date: Thu, 24 Apr 2025 16:18:26 +0200 Subject: [PATCH 24/49] debug: cleanup logging --- backend/src/services/questions.ts | 7 +------ 1 file changed, 1 insertion(+), 6 deletions(-) diff --git a/backend/src/services/questions.ts b/backend/src/services/questions.ts index 766d28fa..0841b574 100644 --- a/backend/src/services/questions.ts +++ b/backend/src/services/questions.ts @@ -107,12 +107,7 @@ export async function createQuestion(loId: LearningObjectIdentifier, questionDat inGroup: inGroup!, content, }); - console.log() - console.log(loId) - console.log(author) - console.log(inGroup) - console.log(content) - console.log(question) + return mapToQuestionDTO(question); } From c1eeee4e3942fddc5247e294fe6ce567d1a204b7 Mon Sep 17 00:00:00 2001 From: Timo De Meyst Date: Thu, 24 Apr 2025 16:18:53 +0200 Subject: [PATCH 25/49] chore: questionInput wordt enkel leeggemaakt als vraag verstuurd is --- frontend/src/views/learning-paths/LearningPathPage.vue | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/frontend/src/views/learning-paths/LearningPathPage.vue b/frontend/src/views/learning-paths/LearningPathPage.vue index e329b4f9..0e050477 100644 --- a/frontend/src/views/learning-paths/LearningPathPage.vue +++ b/frontend/src/views/learning-paths/LearningPathPage.vue @@ -182,11 +182,10 @@ import type { GroupDTO } from "@dwengo-1/common/interfaces/group"; if (questionInput.value != "") { createQuestionMutation.mutate(questionData, { onSuccess: () => { - questionInput.value = "question:..."; // Clear the input field after submission + questionInput.value = ""; // Clear the input field after submission }, onError: (e) => { console.error(e) - questionInput.value = ""; // Clear the input field after submission }, }) } else { From f5e75cd86810fe0912ccef6d7030cdc511521e4e Mon Sep 17 00:00:00 2001 From: Timo De Meyst Date: Thu, 24 Apr 2025 16:38:36 +0200 Subject: [PATCH 26/49] todo: i18n --- frontend/src/views/learning-paths/LearningPathPage.vue | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frontend/src/views/learning-paths/LearningPathPage.vue b/frontend/src/views/learning-paths/LearningPathPage.vue index 0e050477..8d59acb4 100644 --- a/frontend/src/views/learning-paths/LearningPathPage.vue +++ b/frontend/src/views/learning-paths/LearningPathPage.vue @@ -189,7 +189,7 @@ import type { GroupDTO } from "@dwengo-1/common/interfaces/group"; }, }) } else { - alert("Please type a question before submitting.") + alert("Please type a question before submitting.") // TODO: i18n } } From cab39dc87744dd3048cd5120e954f9527821af56 Mon Sep 17 00:00:00 2001 From: Timo De Meyst Date: Thu, 24 Apr 2025 16:40:04 +0200 Subject: [PATCH 27/49] fix: missing await --- backend/src/data/questions/answer-repository.ts | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/backend/src/data/questions/answer-repository.ts b/backend/src/data/questions/answer-repository.ts index 54f67a01..ba5cf796 100644 --- a/backend/src/data/questions/answer-repository.ts +++ b/backend/src/data/questions/answer-repository.ts @@ -12,7 +12,8 @@ export class AnswerRepository extends DwengoEntityRepository { content: answer.content, timestamp: new Date(), }); - return this.insert(answerEntity); + await this.insert(answerEntity); + return answerEntity; } public async findAllAnswersToQuestion(question: Question): Promise { return this.findAll({ From 7d881e6c356fdf261e41246db4d29e05a4b4b325 Mon Sep 17 00:00:00 2001 From: Timo De Meyst Date: Thu, 24 Apr 2025 16:51:08 +0200 Subject: [PATCH 28/49] feat: answer input box toegevoegd --- frontend/src/components/SingleQuestion.vue | 60 +++++++++++++++++++++- 1 file changed, 58 insertions(+), 2 deletions(-) diff --git a/frontend/src/components/SingleQuestion.vue b/frontend/src/components/SingleQuestion.vue index f0607b8b..69b543e1 100644 --- a/frontend/src/components/SingleQuestion.vue +++ b/frontend/src/components/SingleQuestion.vue @@ -29,6 +29,12 @@ }) as QuestionId, ), ); + + const answer = ref('') + + function submitAnswer() { + console.log('Submitted answer:', answer.value) + } - + From ff702de3795030396a94442bef94af170b69fd17 Mon Sep 17 00:00:00 2001 From: Timo De Meyst Date: Thu, 24 Apr 2025 17:05:00 +0200 Subject: [PATCH 29/49] feat: antwoorden kunnen gepost worden --- frontend/src/components/SingleQuestion.vue | 28 ++++++++++++++++++---- 1 file changed, 23 insertions(+), 5 deletions(-) diff --git a/frontend/src/components/SingleQuestion.vue b/frontend/src/components/SingleQuestion.vue index 69b543e1..38960ea3 100644 --- a/frontend/src/components/SingleQuestion.vue +++ b/frontend/src/components/SingleQuestion.vue @@ -1,10 +1,11 @@ + - From 103742db3190d3a5e2ec63248f47ea76d28232cb Mon Sep 17 00:00:00 2001 From: Timo De Meyst Date: Thu, 24 Apr 2025 19:36:48 +0200 Subject: [PATCH 35/49] feat: poging tot precomputen van check of leerobjecten vragen hebben --- .../views/learning-paths/LearningPathPage.vue | 29 +++++++++++++++++-- 1 file changed, 26 insertions(+), 3 deletions(-) diff --git a/frontend/src/views/learning-paths/LearningPathPage.vue b/frontend/src/views/learning-paths/LearningPathPage.vue index 94ac74fd..d5308b12 100644 --- a/frontend/src/views/learning-paths/LearningPathPage.vue +++ b/frontend/src/views/learning-paths/LearningPathPage.vue @@ -20,7 +20,7 @@ import type { QuestionData, QuestionDTO } from "@dwengo-1/common/interfaces/question"; import {useStudentAssignmentsQuery, useStudentGroupsQuery} from "@/queries/students" import type { AssignmentDTO } from "@dwengo-1/common/interfaces/assignment"; - import type { GroupDTO } from "@dwengo-1/common/interfaces/group"; +import type { GroupDTO } from "@dwengo-1/common/interfaces/group"; const router = useRouter(); const route = useRoute(); @@ -192,8 +192,31 @@ } else { alert("Please type a question before submitting.") // TODO: i18n } - } + + const learningObjectHasQuestions = computed(() => { + const result = new Map(); + const learningObjects = learningObjectListQueryResult.data?.value ?? []; + + learningObjects.forEach((learningObject) => { + const nodeLoId: LearningObjectIdentifierDTO = { + hruid: learningObject.key, + language: learningObject.language, + version: learningObject.version + }; + + // Check if the learning object has questions + const questions = useQuestionsQuery(nodeLoId).data.value?.questions as QuestionDTO[] || []; + result.set(learningObject.key, questions.length > 0); + }); + + return result; + }); + +// Helper function to check if a learning object has questions +function hasQuestions(learningObjectKey: string): boolean { + return learningObjectHasQuestions.value.get(learningObjectKey) ?? false; +} @@ -273,7 +296,7 @@ > From 3f26353d797a4bf45894a0f0daeaf0f83080b686 Mon Sep 17 00:00:00 2001 From: laurejablonski Date: Thu, 24 Apr 2025 20:43:12 +0200 Subject: [PATCH 36/49] feat: melding bij leerobjecten met vragen --- .../src/components/QuestionNotification.vue | 24 +++++++++++++++ .../views/learning-paths/LearningPathPage.vue | 30 ++----------------- 2 files changed, 26 insertions(+), 28 deletions(-) create mode 100644 frontend/src/components/QuestionNotification.vue diff --git a/frontend/src/components/QuestionNotification.vue b/frontend/src/components/QuestionNotification.vue new file mode 100644 index 00000000..75540754 --- /dev/null +++ b/frontend/src/components/QuestionNotification.vue @@ -0,0 +1,24 @@ + + + diff --git a/frontend/src/views/learning-paths/LearningPathPage.vue b/frontend/src/views/learning-paths/LearningPathPage.vue index d5308b12..94d8e8a7 100644 --- a/frontend/src/views/learning-paths/LearningPathPage.vue +++ b/frontend/src/views/learning-paths/LearningPathPage.vue @@ -21,6 +21,7 @@ import {useStudentAssignmentsQuery, useStudentGroupsQuery} from "@/queries/students" import type { AssignmentDTO } from "@dwengo-1/common/interfaces/assignment"; import type { GroupDTO } from "@dwengo-1/common/interfaces/group"; +import QuestionNotification from "@/components/QuestionNotification.vue"; const router = useRouter(); const route = useRoute(); @@ -193,30 +194,6 @@ import type { GroupDTO } from "@dwengo-1/common/interfaces/group"; alert("Please type a question before submitting.") // TODO: i18n } } - - const learningObjectHasQuestions = computed(() => { - const result = new Map(); - const learningObjects = learningObjectListQueryResult.data?.value ?? []; - - learningObjects.forEach((learningObject) => { - const nodeLoId: LearningObjectIdentifierDTO = { - hruid: learningObject.key, - language: learningObject.language, - version: learningObject.version - }; - - // Check if the learning object has questions - const questions = useQuestionsQuery(nodeLoId).data.value?.questions as QuestionDTO[] || []; - result.set(learningObject.key, questions.length > 0); - }); - - return result; - }); - -// Helper function to check if a learning object has questions -function hasQuestions(learningObjectKey: string): boolean { - return learningObjectHasQuestions.value.get(learningObjectKey) ?? false; -} @@ -295,10 +272,7 @@ function hasQuestions(learningObjectKey: string): boolean { :icon="ICONS[getNavItemState(node)]" > - + From 0a37d96c6946aebdc88668fba15baf58553bd437 Mon Sep 17 00:00:00 2001 From: Timo De Meyst Date: Thu, 24 Apr 2025 20:58:06 +0200 Subject: [PATCH 37/49] style: vraag indicator en estimated time staan naast elkaar ipv onder --- frontend/src/components/QuestionNotification.vue | 1 - frontend/src/views/learning-paths/LearningPathPage.vue | 6 +++++- 2 files changed, 5 insertions(+), 2 deletions(-) diff --git a/frontend/src/components/QuestionNotification.vue b/frontend/src/components/QuestionNotification.vue index 75540754..21801fea 100644 --- a/frontend/src/components/QuestionNotification.vue +++ b/frontend/src/components/QuestionNotification.vue @@ -19,6 +19,5 @@ const hasQuestions = computed(() => { diff --git a/frontend/src/views/learning-paths/LearningPathPage.vue b/frontend/src/views/learning-paths/LearningPathPage.vue index 94d8e8a7..5e157808 100644 --- a/frontend/src/views/learning-paths/LearningPathPage.vue +++ b/frontend/src/views/learning-paths/LearningPathPage.vue @@ -272,7 +272,11 @@ import QuestionNotification from "@/components/QuestionNotification.vue"; :icon="ICONS[getNavItemState(node)]" > - + + From 085e72b0ebb850defb320f991a9aecc87d1aa10a Mon Sep 17 00:00:00 2001 From: Timo De Meyst Date: Thu, 24 Apr 2025 21:02:13 +0200 Subject: [PATCH 38/49] style: estimated time toont altijd 2 cijfers --- frontend/src/views/learning-paths/LearningPathPage.vue | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frontend/src/views/learning-paths/LearningPathPage.vue b/frontend/src/views/learning-paths/LearningPathPage.vue index 5e157808..0da7c85c 100644 --- a/frontend/src/views/learning-paths/LearningPathPage.vue +++ b/frontend/src/views/learning-paths/LearningPathPage.vue @@ -274,7 +274,7 @@ import QuestionNotification from "@/components/QuestionNotification.vue"; From 4be7aa9b215170ec099c9588d7cb9e6a68fa3054 Mon Sep 17 00:00:00 2001 From: Gabriellvl Date: Thu, 24 Apr 2025 21:13:06 +0200 Subject: [PATCH 39/49] fix: commas in json --- frontend/src/i18n/locale/de.json | 2 +- frontend/src/i18n/locale/en.json | 2 +- frontend/src/i18n/locale/fr.json | 2 +- frontend/src/i18n/locale/nl.json | 2 +- 4 files changed, 4 insertions(+), 4 deletions(-) diff --git a/frontend/src/i18n/locale/de.json b/frontend/src/i18n/locale/de.json index 98627f47..fbdc652a 100644 --- a/frontend/src/i18n/locale/de.json +++ b/frontend/src/i18n/locale/de.json @@ -119,7 +119,7 @@ "enterUsername": "Geben Sie den Benutzernamen der Lehrkraft ein, die Sie einladen möchten", "username": "Nutzername", "invite": "einladen", - "assignmentIndicator": "AUFGABE" + "assignmentIndicator": "AUFGABE", "searchAllLearningPathsTitle": "Alle Lernpfade durchsuchen", "searchAllLearningPathsDescription": "Nicht gefunden, was Sie gesucht haben? Klicken Sie hier, um unsere gesamte Lernpfad-Datenbank zu durchsuchen." } diff --git a/frontend/src/i18n/locale/en.json b/frontend/src/i18n/locale/en.json index 710351c1..e4042d09 100644 --- a/frontend/src/i18n/locale/en.json +++ b/frontend/src/i18n/locale/en.json @@ -119,7 +119,7 @@ "enterUsername": "enter the username of the teacher you would like to invite", "username": "username", "invite": "invite", - "assignmentIndicator": "ASSIGNMENT" + "assignmentIndicator": "ASSIGNMENT", "searchAllLearningPathsTitle": "Search all learning paths", "searchAllLearningPathsDescription": "You didn't find what you were looking for? Click here to search our whole database of available learning paths." } diff --git a/frontend/src/i18n/locale/fr.json b/frontend/src/i18n/locale/fr.json index 4e64a347..b331a168 100644 --- a/frontend/src/i18n/locale/fr.json +++ b/frontend/src/i18n/locale/fr.json @@ -119,7 +119,7 @@ "enterUsername": "entrez le nom d'utilisateur de l'enseignant que vous souhaitez inviter", "username": "Nom d'utilisateur", "invite": "inviter", - "assignmentIndicator": "DEVOIR" + "assignmentIndicator": "DEVOIR", "searchAllLearningPathsTitle": "Rechercher tous les parcours d'apprentissage", "searchAllLearningPathsDescription": "Vous n'avez pas trouvé ce que vous cherchiez ? Cliquez ici pour rechercher dans toute notre base de données de parcours d'apprentissage disponibles." } diff --git a/frontend/src/i18n/locale/nl.json b/frontend/src/i18n/locale/nl.json index 57facc49..5aa17930 100644 --- a/frontend/src/i18n/locale/nl.json +++ b/frontend/src/i18n/locale/nl.json @@ -119,7 +119,7 @@ "enterUsername": "vul de gebruikersnaam van de leerkracht die je wilt uitnodigen in", "username": "gebruikersnaam", "invite": "uitnodigen", - "assignmentIndicator": "OPDRACHT" + "assignmentIndicator": "OPDRACHT", "searchAllLearningPathsTitle": "Alle leerpaden doorzoeken", "searchAllLearningPathsDescription": "Niet gevonden waar je naar op zoek was? Klik hier om onze volledige databank van beschikbare leerpaden te doorzoeken." } From efb2ba68a92b94a0545d8b26fc1a206a9f64b9ec Mon Sep 17 00:00:00 2001 From: Tibo De Peuter Date: Thu, 24 Apr 2025 21:20:54 +0200 Subject: [PATCH 40/49] fix: .js toevoegen aan imports --- backend/src/services/questions.ts | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/backend/src/services/questions.ts b/backend/src/services/questions.ts index 0841b574..f59f5166 100644 --- a/backend/src/services/questions.ts +++ b/backend/src/services/questions.ts @@ -12,8 +12,7 @@ import { AssignmentDTO } from '@dwengo-1/common/interfaces/assignment'; import { fetchStudent } from './students.js'; import { NotFoundException } from '../exceptions/not-found-exception.js'; import { FALLBACK_VERSION_NUM } from '../config.js'; -import {fetchClass} from "./classes"; -import {fetchAssignment} from "./assignments"; +import { fetchAssignment } from './assignments.js'; export async function getQuestionsAboutLearningObjectInAssignment( loId: LearningObjectIdentifier, From 0e44de0e7c6a8be2ab7fc4b6d962adb1c365f61d Mon Sep 17 00:00:00 2001 From: Timo De Meyst Date: Thu, 24 Apr 2025 21:22:06 +0200 Subject: [PATCH 41/49] chore: package-lock die zeker en vast klopt! --- package-lock.json | 354 ++-------------------------------------------- 1 file changed, 9 insertions(+), 345 deletions(-) diff --git a/package-lock.json b/package-lock.json index a3f35b8b..d90cc651 100644 --- a/package-lock.json +++ b/package-lock.json @@ -2358,7 +2358,7 @@ "resolved": "https://registry.npmjs.org/@rollup/rollup-darwin-x64/-/rollup-darwin-x64-4.40.0.tgz", "integrity": "sha512-CoLEGJ+2eheqD9KBSxmma6ld01czS52Iw0e2qMZNpPDlf7Z9mj8xmMemxEucinev4LgHalDPczMyxzbq+Q+EtA==", "cpu": [ - "arm" + "x64" ], "license": "MIT", "optional": true, @@ -2526,12 +2526,8 @@ "version": "4.40.0", "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-x64-musl/-/rollup-linux-x64-musl-4.40.0.tgz", "integrity": "sha512-HZvjpiUmSNx5zFgwtQAV1GaGazT2RWvqeDi0hV+AtC8unqqDSsaFjPxfsO6qPtKRRg25SisACWnJ37Yio8ttaw==", - "node_modules/@rollup/rollup-android-arm64": { - "version": "4.40.0", - "resolved": "https://registry.npmjs.org/@rollup/rollup-android-arm64/-/rollup-android-arm64-4.40.0.tgz", - "integrity": "sha512-PPA6aEEsTPRz+/4xxAmaoWDqh67N7wFbgFUJGMnanCFs0TV99M0M8QhhaSCks+n6EbQoFvLQgYOGXxlMGQe/6w==", "cpu": [ - "arm64" + "x64" ], "license": "MIT", "optional": true, @@ -2578,276 +2574,6 @@ "win32" ] }, - "node_modules/@rollup/rollup-darwin-arm64": { - "version": "4.40.0", - "resolved": "https://registry.npmjs.org/@rollup/rollup-darwin-arm64/-/rollup-darwin-arm64-4.40.0.tgz", - "integrity": "sha512-GwYOcOakYHdfnjjKwqpTGgn5a6cUX7+Ra2HeNj/GdXvO2VJOOXCiYYlRFU4CubFM67EhbmzLOmACKEfvp3J1kQ==", - "cpu": [ - "arm64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "darwin" - ], - "peer": true - }, - "node_modules/@rollup/rollup-darwin-x64": { - "version": "4.40.0", - "resolved": "https://registry.npmjs.org/@rollup/rollup-darwin-x64/-/rollup-darwin-x64-4.40.0.tgz", - "integrity": "sha512-CoLEGJ+2eheqD9KBSxmma6ld01czS52Iw0e2qMZNpPDlf7Z9mj8xmMemxEucinev4LgHalDPczMyxzbq+Q+EtA==", - "cpu": [ - "x64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "darwin" - ], - "peer": true - }, - "node_modules/@rollup/rollup-freebsd-arm64": { - "version": "4.40.0", - "resolved": "https://registry.npmjs.org/@rollup/rollup-freebsd-arm64/-/rollup-freebsd-arm64-4.40.0.tgz", - "integrity": "sha512-r7yGiS4HN/kibvESzmrOB/PxKMhPTlz+FcGvoUIKYoTyGd5toHp48g1uZy1o1xQvybwwpqpe010JrcGG2s5nkg==", - "cpu": [ - "arm64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "freebsd" - ], - "peer": true - }, - "node_modules/@rollup/rollup-freebsd-x64": { - "version": "4.40.0", - "resolved": "https://registry.npmjs.org/@rollup/rollup-freebsd-x64/-/rollup-freebsd-x64-4.40.0.tgz", - "integrity": "sha512-mVDxzlf0oLzV3oZOr0SMJ0lSDd3xC4CmnWJ8Val8isp9jRGl5Dq//LLDSPFrasS7pSm6m5xAcKaw3sHXhBjoRw==", - "cpu": [ - "x64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "freebsd" - ], - "peer": true - }, - "node_modules/@rollup/rollup-linux-arm-gnueabihf": { - "version": "4.40.0", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm-gnueabihf/-/rollup-linux-arm-gnueabihf-4.40.0.tgz", - "integrity": "sha512-y/qUMOpJxBMy8xCXD++jeu8t7kzjlOCkoxxajL58G62PJGBZVl/Gwpm7JK9+YvlB701rcQTzjUZ1JgUoPTnoQA==", - "cpu": [ - "arm" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "linux" - ], - "peer": true - }, - "node_modules/@rollup/rollup-linux-arm-musleabihf": { - "version": "4.40.0", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm-musleabihf/-/rollup-linux-arm-musleabihf-4.40.0.tgz", - "integrity": "sha512-GoCsPibtVdJFPv/BOIvBKO/XmwZLwaNWdyD8TKlXuqp0veo2sHE+A/vpMQ5iSArRUz/uaoj4h5S6Pn0+PdhRjg==", - "cpu": [ - "arm" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "linux" - ], - "peer": true - }, - "node_modules/@rollup/rollup-linux-arm64-gnu": { - "version": "4.40.0", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm64-gnu/-/rollup-linux-arm64-gnu-4.40.0.tgz", - "integrity": "sha512-L5ZLphTjjAD9leJzSLI7rr8fNqJMlGDKlazW2tX4IUF9P7R5TMQPElpH82Q7eNIDQnQlAyiNVfRPfP2vM5Avvg==", - "cpu": [ - "arm64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "linux" - ], - "peer": true - }, - "node_modules/@rollup/rollup-linux-arm64-musl": { - "version": "4.40.0", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm64-musl/-/rollup-linux-arm64-musl-4.40.0.tgz", - "integrity": "sha512-ATZvCRGCDtv1Y4gpDIXsS+wfFeFuLwVxyUBSLawjgXK2tRE6fnsQEkE4csQQYWlBlsFztRzCnBvWVfcae/1qxQ==", - "cpu": [ - "arm64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "linux" - ], - "peer": true - }, - "node_modules/@rollup/rollup-linux-loongarch64-gnu": { - "version": "4.40.0", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-loongarch64-gnu/-/rollup-linux-loongarch64-gnu-4.40.0.tgz", - "integrity": "sha512-wG9e2XtIhd++QugU5MD9i7OnpaVb08ji3P1y/hNbxrQ3sYEelKJOq1UJ5dXczeo6Hj2rfDEL5GdtkMSVLa/AOg==", - "cpu": [ - "loong64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "linux" - ], - "peer": true - }, - "node_modules/@rollup/rollup-linux-powerpc64le-gnu": { - "version": "4.40.0", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-powerpc64le-gnu/-/rollup-linux-powerpc64le-gnu-4.40.0.tgz", - "integrity": "sha512-vgXfWmj0f3jAUvC7TZSU/m/cOE558ILWDzS7jBhiCAFpY2WEBn5jqgbqvmzlMjtp8KlLcBlXVD2mkTSEQE6Ixw==", - "cpu": [ - "ppc64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "linux" - ], - "peer": true - }, - "node_modules/@rollup/rollup-linux-riscv64-gnu": { - "version": "4.40.0", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-riscv64-gnu/-/rollup-linux-riscv64-gnu-4.40.0.tgz", - "integrity": "sha512-uJkYTugqtPZBS3Z136arevt/FsKTF/J9dEMTX/cwR7lsAW4bShzI2R0pJVw+hcBTWF4dxVckYh72Hk3/hWNKvA==", - "cpu": [ - "riscv64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "linux" - ], - "peer": true - }, - "node_modules/@rollup/rollup-linux-riscv64-musl": { - "version": "4.40.0", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-riscv64-musl/-/rollup-linux-riscv64-musl-4.40.0.tgz", - "integrity": "sha512-rKmSj6EXQRnhSkE22+WvrqOqRtk733x3p5sWpZilhmjnkHkpeCgWsFFo0dGnUGeA+OZjRl3+VYq+HyCOEuwcxQ==", - "cpu": [ - "riscv64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "linux" - ], - "peer": true - }, - "node_modules/@rollup/rollup-linux-s390x-gnu": { - "version": "4.40.0", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-s390x-gnu/-/rollup-linux-s390x-gnu-4.40.0.tgz", - "integrity": "sha512-SpnYlAfKPOoVsQqmTFJ0usx0z84bzGOS9anAC0AZ3rdSo3snecihbhFTlJZ8XMwzqAcodjFU4+/SM311dqE5Sw==", - "cpu": [ - "s390x" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "linux" - ], - "peer": true - }, - "node_modules/@rollup/rollup-linux-x64-gnu": { - "version": "4.40.0", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-x64-gnu/-/rollup-linux-x64-gnu-4.40.0.tgz", - "integrity": "sha512-RcDGMtqF9EFN8i2RYN2W+64CdHruJ5rPqrlYw+cgM3uOVPSsnAQps7cpjXe9be/yDp8UC7VLoCoKC8J3Kn2FkQ==", - "cpu": [ - "x64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "linux" - ], - "peer": true - }, - "node_modules/@rollup/rollup-linux-x64-musl": { - "version": "4.40.0", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-x64-musl/-/rollup-linux-x64-musl-4.40.0.tgz", - "integrity": "sha512-HZvjpiUmSNx5zFgwtQAV1GaGazT2RWvqeDi0hV+AtC8unqqDSsaFjPxfsO6qPtKRRg25SisACWnJ37Yio8ttaw==", - "cpu": [ - "x64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "linux" - ], - "peer": true - }, - "node_modules/@rollup/rollup-win32-arm64-msvc": { - "version": "4.40.0", - "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-arm64-msvc/-/rollup-win32-arm64-msvc-4.40.0.tgz", - "integrity": "sha512-UtZQQI5k/b8d7d3i9AZmA/t+Q4tk3hOC0tMOMSq2GlMYOfxbesxG4mJSeDp0EHs30N9bsfwUvs3zF4v/RzOeTQ==", - "cpu": [ - "arm64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "win32" - ], - "peer": true - }, - "node_modules/@rollup/rollup-win32-ia32-msvc": { - "version": "4.40.0", - "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-ia32-msvc/-/rollup-win32-ia32-msvc-4.40.0.tgz", - "integrity": "sha512-+m03kvI2f5syIqHXCZLPVYplP8pQch9JHyXKZ3AGMKlg8dCyr2PKHjwRLiW53LTrN/Nc3EqHOKxUxzoSPdKddA==", - "cpu": [ - "ia32" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "win32" - ], - "peer": true - }, - "node_modules/@rollup/rollup-win32-x64-msvc": { - "version": "4.40.0", - "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-x64-msvc/-/rollup-win32-x64-msvc-4.40.0.tgz", - "integrity": "sha512-lpPE1cLfP5oPzVjKMx10pgBmKELQnFJXHgvtHCtuJWOv8MxqdEIMNtgHgBFf7Ea2/7EuVwa9fodWUfXAlXZLZQ==", - "cpu": [ - "x64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "win32" - ], - "peer": true - }, "node_modules/@scarf/scarf": { "version": "1.4.0", "resolved": "https://registry.npmjs.org/@scarf/scarf/-/scarf-1.4.0.tgz", @@ -6661,9 +6387,9 @@ "license": "MIT" }, "node_modules/electron-to-chromium": { - "version": "1.5.141", - "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.5.141.tgz", - "integrity": "sha512-qS+qH9oqVYc1ooubTiB9l904WVyM6qNYxtOEEGReoZXw3xlqeYdFr5GclNzbkAufWgwWLEPoDi3d9MoRwwIjGw==", + "version": "1.5.142", + "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.5.142.tgz", + "integrity": "sha512-Ah2HgkTu/9RhTDNThBtzu2Wirdy4DC9b0sMT1pUhbkZQ5U/iwmE+PHZX1MpjD5IkJCc2wSghgGG/B04szAx07w==", "dev": true, "license": "ISC" }, @@ -8085,9 +7811,9 @@ "license": "ISC" }, "node_modules/fsevents": { - "version": "2.3.3", - "resolved": "https://registry.npmjs.org/fsevents/-/fsevents-2.3.3.tgz", - "integrity": "sha512-5xoDfX+fL7faATnagmWPpbFtwh/R77WmMMqqHGS65C3vvB0YHrgF+B1YmZ3441tMj5n63k0212XNoJwzlhffQw==", + "version": "2.3.2", + "resolved": "https://registry.npmjs.org/fsevents/-/fsevents-2.3.2.tgz", + "integrity": "sha512-xiqMQR4xAeHTuB9uWm+fFRcIOgKBMiOBP+eXiyT7jsgVCq1bkVygt00oASowB7EdtpOHaaPgKt812P9ab+DDKA==", "hasInstallScript": true, "license": "MIT", "optional": true, @@ -13852,7 +13578,6 @@ "version": "4.40.0", "resolved": "https://registry.npmjs.org/rollup/-/rollup-4.40.0.tgz", "integrity": "sha512-Noe455xmA96nnqH5piFtLobsGbCij7Tu+tb3c1vYjNbTkfzGqXqQXG3wJaYXkRZuQ0vEYN4bhwg7QnIrqB5B+w==", - "dev": true, "license": "MIT", "dependencies": { "@types/estree": "1.0.7" @@ -14541,39 +14266,6 @@ "node": ">=0.10.0" } }, - "node_modules/playwright/node_modules/fsevents": { - "version": "2.3.2", - "resolved": "https://registry.npmjs.org/fsevents/-/fsevents-2.3.2.tgz", - "integrity": "sha512-xiqMQR4xAeHTuB9uWm+fFRcIOgKBMiOBP+eXiyT7jsgVCq1bkVygt00oASowB7EdtpOHaaPgKt812P9ab+DDKA==", - "dev": true, - "hasInstallScript": true, - "license": "MIT", - "optional": true, - "os": [ - "darwin" - ], - "engines": { - "node": "^8.16.0 || ^10.6.0 || >=11.0.0" - } - }, - "node_modules/postcss": { - "version": "8.5.3", - "resolved": "https://registry.npmjs.org/postcss/-/postcss-8.5.3.tgz", - "integrity": "sha512-dle9A3yYxlBSrt8Fu+IpjGT8SY8hN0mlaA6GY8t0P5PjIOZemULz/E2Bnm/2dcUOena75OTNkHI76uZBNUUq3A==", - "funding": [ - { - "type": "opencollective", - "url": "https://opencollective.com/postcss/" - }, - { - "type": "tidelift", - "url": "https://tidelift.com/funding/github/npm/postcss" - }, - { - "type": "github", - "url": "https://github.com/sponsors/ai" - } - ], "node_modules/snapdragon/node_modules/debug": { "version": "2.6.9", "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", @@ -15120,10 +14812,6 @@ "node": ">=8" } }, - "node_modules/rollup": { - "version": "4.40.0", - "resolved": "https://registry.npmjs.org/rollup/-/rollup-4.40.0.tgz", - "integrity": "sha512-Noe455xmA96nnqH5piFtLobsGbCij7Tu+tb3c1vYjNbTkfzGqXqQXG3wJaYXkRZuQ0vEYN4bhwg7QnIrqB5B+w==", "node_modules/strip-bom": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/strip-bom/-/strip-bom-3.0.0.tgz", @@ -15131,31 +14819,7 @@ "dev": true, "license": "MIT", "engines": { - "node": ">=18.0.0", - "npm": ">=8.0.0" - }, - "optionalDependencies": { - "@rollup/rollup-android-arm-eabi": "4.40.0", - "@rollup/rollup-android-arm64": "4.40.0", - "@rollup/rollup-darwin-arm64": "4.40.0", - "@rollup/rollup-darwin-x64": "4.40.0", - "@rollup/rollup-freebsd-arm64": "4.40.0", - "@rollup/rollup-freebsd-x64": "4.40.0", - "@rollup/rollup-linux-arm-gnueabihf": "4.40.0", - "@rollup/rollup-linux-arm-musleabihf": "4.40.0", - "@rollup/rollup-linux-arm64-gnu": "4.40.0", - "@rollup/rollup-linux-arm64-musl": "4.40.0", - "@rollup/rollup-linux-loongarch64-gnu": "4.40.0", - "@rollup/rollup-linux-powerpc64le-gnu": "4.40.0", - "@rollup/rollup-linux-riscv64-gnu": "4.40.0", - "@rollup/rollup-linux-riscv64-musl": "4.40.0", - "@rollup/rollup-linux-s390x-gnu": "4.40.0", - "@rollup/rollup-linux-x64-gnu": "4.40.0", - "@rollup/rollup-linux-x64-musl": "4.40.0", - "@rollup/rollup-win32-arm64-msvc": "4.40.0", - "@rollup/rollup-win32-ia32-msvc": "4.40.0", - "@rollup/rollup-win32-x64-msvc": "4.40.0", - "fsevents": "~2.3.2" + "node": ">=4" } }, "node_modules/strip-eof": { From a0192ddbdf1df5c9be9119058db89753db133827 Mon Sep 17 00:00:00 2001 From: Timo De Meyst Date: Thu, 24 Apr 2025 21:24:53 +0200 Subject: [PATCH 42/49] feat: vragen kunnen niet gesteld worden als leerobject geen assignment is --- frontend/src/views/learning-paths/LearningPathPage.vue | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frontend/src/views/learning-paths/LearningPathPage.vue b/frontend/src/views/learning-paths/LearningPathPage.vue index 0da7c85c..8f97379a 100644 --- a/frontend/src/views/learning-paths/LearningPathPage.vue +++ b/frontend/src/views/learning-paths/LearningPathPage.vue @@ -318,7 +318,7 @@ import QuestionNotification from "@/components/QuestionNotification.vue"; v-if="currentNode" >
-
+
Date: Thu, 24 Apr 2025 19:28:10 +0000 Subject: [PATCH 43/49] style: fix linting issues met ESLint --- backend/src/services/questions.ts | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/backend/src/services/questions.ts b/backend/src/services/questions.ts index f59f5166..d80fffac 100644 --- a/backend/src/services/questions.ts +++ b/backend/src/services/questions.ts @@ -90,8 +90,8 @@ export async function createQuestion(loId: LearningObjectIdentifier, questionDat let assignment; if ((typeof questionData.inGroup.assignment === "number") && (typeof questionData.inGroup.class === "string")) { - assignment = await fetchAssignment(questionData.inGroup.class as string, - questionData.inGroup.assignment as number); + assignment = await fetchAssignment(questionData.inGroup.class, + questionData.inGroup.assignment); } else { // TODO check if necessary and no conflicts to delete this if const clazz = await getClassRepository().findById((questionData.inGroup.assignment as AssignmentDTO).within); From 18e17e0133b2cfd003257b25328a91f030beadd3 Mon Sep 17 00:00:00 2001 From: Lint Action Date: Thu, 24 Apr 2025 19:28:16 +0000 Subject: [PATCH 44/49] style: fix linting issues met Prettier --- .../src/data/questions/answer-repository.ts | 2 +- backend/src/services/questions.ts | 9 +- .../test_assets/questions/answers.testdata.ts | 4 +- .../questions/questions.testdata.ts | 6 +- frontend/src/components/QandA.vue | 4 +- .../src/components/QuestionNotification.vue | 38 +++-- frontend/src/components/SingleQuestion.vue | 125 ++++++++------- frontend/src/controllers/answers.ts | 6 +- .../views/learning-paths/LearningPathPage.vue | 150 ++++++++++-------- 9 files changed, 184 insertions(+), 160 deletions(-) diff --git a/backend/src/data/questions/answer-repository.ts b/backend/src/data/questions/answer-repository.ts index ae59a56c..4ef30bbe 100644 --- a/backend/src/data/questions/answer-repository.ts +++ b/backend/src/data/questions/answer-repository.ts @@ -15,7 +15,7 @@ export class AnswerRepository extends DwengoEntityRepository { await this.insert(answerEntity); answerEntity.toQuestion = answer.toQuestion; answerEntity.author = answer.author; - answerEntity.content = answer.content; + answerEntity.content = answer.content; return answerEntity; } public async findAllAnswersToQuestion(question: Question): Promise { diff --git a/backend/src/services/questions.ts b/backend/src/services/questions.ts index d80fffac..09643cd2 100644 --- a/backend/src/services/questions.ts +++ b/backend/src/services/questions.ts @@ -89,9 +89,8 @@ export async function createQuestion(loId: LearningObjectIdentifier, questionDat let assignment; - if ((typeof questionData.inGroup.assignment === "number") && (typeof questionData.inGroup.class === "string")) { - assignment = await fetchAssignment(questionData.inGroup.class, - questionData.inGroup.assignment); + if (typeof questionData.inGroup.assignment === 'number' && typeof questionData.inGroup.class === 'string') { + assignment = await fetchAssignment(questionData.inGroup.class, questionData.inGroup.assignment); } else { // TODO check if necessary and no conflicts to delete this if const clazz = await getClassRepository().findById((questionData.inGroup.assignment as AssignmentDTO).within); @@ -99,14 +98,14 @@ export async function createQuestion(loId: LearningObjectIdentifier, questionDat } const inGroup = await getGroupRepository().findByAssignmentAndGroupNumber(assignment, questionData.inGroup.groupNumber); - + const question = await questionRepository.createQuestion({ loId, author, inGroup: inGroup!, content, }); - + return mapToQuestionDTO(question); } diff --git a/backend/tests/test_assets/questions/answers.testdata.ts b/backend/tests/test_assets/questions/answers.testdata.ts index 44724604..443f523d 100644 --- a/backend/tests/test_assets/questions/answers.testdata.ts +++ b/backend/tests/test_assets/questions/answers.testdata.ts @@ -36,7 +36,7 @@ export function makeTestAnswers(em: EntityManager, teachers: Teacher[], question toQuestion: getQuestion07(), sequenceNumber: 1, timestamp: new Date(), - content: "this is a test answer" + content: 'this is a test answer', }); const answer05 = em.create(Answer, { @@ -44,7 +44,7 @@ export function makeTestAnswers(em: EntityManager, teachers: Teacher[], question toQuestion: getQuestion07(), sequenceNumber: 2, timestamp: new Date(), - content: "this is a test answer" + content: 'this is a test answer', }); return [answer01, answer02, answer03, answer04, answer05]; diff --git a/backend/tests/test_assets/questions/questions.testdata.ts b/backend/tests/test_assets/questions/questions.testdata.ts index 5e50d7d7..9e8d6df3 100644 --- a/backend/tests/test_assets/questions/questions.testdata.ts +++ b/backend/tests/test_assets/questions/questions.testdata.ts @@ -73,7 +73,7 @@ export function makeTestQuestions(em: EntityManager, students: Student[], groups timestamp: new Date(), content: 'question', }); - + question07 = em.create(Question, { learningObjectLanguage: Language.English, learningObjectVersion: 1, @@ -93,7 +93,7 @@ export function makeTestQuestions(em: EntityManager, students: Student[], groups author: getTestleerling1(), inGroup: getGroup1ConditionalLearningPath(), timestamp: new Date(), - content: 'this is a second test question' + content: 'this is a second test question', }); return [question01, question02, question03, question04, question05, question06, question07, question08]; @@ -108,4 +108,4 @@ export function getQuestion07(): Question { export function getQuestion08(): Question { return question08; -} \ No newline at end of file +} diff --git a/frontend/src/components/QandA.vue b/frontend/src/components/QandA.vue index 3d7bae39..f9b15362 100644 --- a/frontend/src/components/QandA.vue +++ b/frontend/src/components/QandA.vue @@ -9,13 +9,11 @@ diff --git a/frontend/src/components/QuestionNotification.vue b/frontend/src/components/QuestionNotification.vue index 21801fea..30d73e00 100644 --- a/frontend/src/components/QuestionNotification.vue +++ b/frontend/src/components/QuestionNotification.vue @@ -1,23 +1,31 @@ diff --git a/frontend/src/components/SingleQuestion.vue b/frontend/src/components/SingleQuestion.vue index 13553290..fdf48bd3 100644 --- a/frontend/src/components/SingleQuestion.vue +++ b/frontend/src/components/SingleQuestion.vue @@ -5,7 +5,7 @@ import UsingQueryResult from "./UsingQueryResult.vue"; import type { AnswersResponse } from "@/controllers/answers"; import type { AnswerData, AnswerDTO } from "@dwengo-1/common/interfaces/answer"; -import authService from "@/services/auth/auth-service"; + import authService from "@/services/auth/auth-service"; const props = defineProps<{ question: QuestionDTO; @@ -30,31 +30,30 @@ import authService from "@/services/auth/auth-service"; }) as QuestionId, ), ); - - const questionId : QuestionId = { + + const questionId: QuestionId = { learningObjectIdentifier: props.question.learningObjectIdentifier, - sequenceNumber: props.question.sequenceNumber as number + sequenceNumber: props.question.sequenceNumber as number, }; const createAnswerMutation = useCreateAnswerMutation(questionId); - const answer = ref(''); + const answer = ref(""); function submitAnswer() { const answerData: AnswerData = { author: authService.authState.user?.profile.preferred_username as string, - content: answer.value + content: answer.value, }; if (answer.value != "") { createAnswerMutation.mutate(answerData, { onSuccess: () => { answer.value = ""; answersQuery.refetch(); - } + }, }); } else { - alert("Please type an answer before submitting") //TODO: i18n + alert("Please type an answer before submitting"); //TODO: i18n } - } diff --git a/frontend/src/controllers/answers.ts b/frontend/src/controllers/answers.ts index 3a378a96..57407b19 100644 --- a/frontend/src/controllers/answers.ts +++ b/frontend/src/controllers/answers.ts @@ -12,13 +12,13 @@ export interface AnswerResponse { } export class AnswerController extends BaseController { - loId: LearningObjectIdentifierDTO; sequenceNumber: number; - constructor(questionId: QuestionId) { - super(`learningObject/${questionId.learningObjectIdentifier.hruid}/:${questionId.learningObjectIdentifier.version}/questions/${questionId.sequenceNumber}/answers`); + super( + `learningObject/${questionId.learningObjectIdentifier.hruid}/:${questionId.learningObjectIdentifier.version}/questions/${questionId.sequenceNumber}/answers`, + ); this.loId = questionId.learningObjectIdentifier; this.sequenceNumber = questionId.sequenceNumber; } diff --git a/frontend/src/views/learning-paths/LearningPathPage.vue b/frontend/src/views/learning-paths/LearningPathPage.vue index 8f97379a..e0199cfe 100644 --- a/frontend/src/views/learning-paths/LearningPathPage.vue +++ b/frontend/src/views/learning-paths/LearningPathPage.vue @@ -18,10 +18,10 @@ import type { LearningObjectIdentifierDTO } from "@dwengo-1/common/interfaces/learning-content"; import QandA from "@/components/QandA.vue"; import type { QuestionData, QuestionDTO } from "@dwengo-1/common/interfaces/question"; - import {useStudentAssignmentsQuery, useStudentGroupsQuery} from "@/queries/students" + import { useStudentAssignmentsQuery, useStudentGroupsQuery } from "@/queries/students"; import type { AssignmentDTO } from "@dwengo-1/common/interfaces/assignment"; -import type { GroupDTO } from "@dwengo-1/common/interfaces/group"; -import QuestionNotification from "@/components/QuestionNotification.vue"; + import type { GroupDTO } from "@dwengo-1/common/interfaces/group"; + import QuestionNotification from "@/components/QuestionNotification.vue"; const router = useRouter(); const route = useRoute(); @@ -146,40 +146,38 @@ import QuestionNotification from "@/components/QuestionNotification.vue"; }); } - const studentAssignmentsQueryResult = useStudentAssignmentsQuery(authService.authState.user?.profile.preferred_username); + const studentAssignmentsQueryResult = useStudentAssignmentsQuery( + authService.authState.user?.profile.preferred_username, + ); const pathIsAssignment = computed(() => { - const assignments = studentAssignmentsQueryResult.data.value?.assignments as AssignmentDTO[] || []; + const assignments = (studentAssignmentsQueryResult.data.value?.assignments as AssignmentDTO[]) || []; return assignments.some( - (assignment) => - assignment.learningPath === props.hruid && - assignment.language === props.language + (assignment) => assignment.learningPath === props.hruid && assignment.language === props.language, ); }); - const loID:LearningObjectIdentifierDTO = { - hruid: props.learningObjectHruid as string, - language: props.language - } - const createQuestionMutation = useCreateQuestionMutation(loID) - const groupsQueryResult = useStudentGroupsQuery(authService.authState.user?.profile.preferred_username) + const loID: LearningObjectIdentifierDTO = { + hruid: props.learningObjectHruid as string, + language: props.language, + }; + const createQuestionMutation = useCreateQuestionMutation(loID); + const groupsQueryResult = useStudentGroupsQuery(authService.authState.user?.profile.preferred_username); const questionInput = ref(""); function submitQuestion() { - const assignments = studentAssignmentsQueryResult.data.value?.assignments as AssignmentDTO[] + const assignments = studentAssignmentsQueryResult.data.value?.assignments as AssignmentDTO[]; const assignment = assignments.find( - (assignment) => - assignment.learningPath === props.hruid && - assignment.language === props.language - ) - const groups = groupsQueryResult.data.value?.groups as GroupDTO[] - const group = groups?.find(group => group.assignment === assignment?.id) as GroupDTO - const questionData:QuestionData = { + (assignment) => assignment.learningPath === props.hruid && assignment.language === props.language, + ); + const groups = groupsQueryResult.data.value?.groups as GroupDTO[]; + const group = groups?.find((group) => group.assignment === assignment?.id) as GroupDTO; + const questionData: QuestionData = { author: authService.authState.user?.profile.preferred_username, content: questionInput.value, - inGroup: group //TODO: POST response zegt dat dit null is??? - } - console.log(questionData) + inGroup: group, //TODO: POST response zegt dat dit null is??? + }; + console.log(questionData); if (questionInput.value != "") { createQuestionMutation.mutate(questionData, { onSuccess: () => { @@ -187,14 +185,13 @@ import QuestionNotification from "@/components/QuestionNotification.vue"; getQuestionsQuery.refetch(); // Reload the questions }, onError: (e) => { - console.error(e) + console.error(e); }, - }) + }); } else { - alert("Please type a question before submitting.") // TODO: i18n + alert("Please type a question before submitting."); // TODO: i18n } } - + - @@ -292,7 +295,10 @@ import QuestionNotification from "@/components/QuestionNotification.vue"; -
+
{{ t("assignmentIndicator") }}
@@ -318,17 +324,25 @@ import QuestionNotification from "@/components/QuestionNotification.vue"; v-if="currentNode" >
-
+
- - + +
-
+