feat: kompnavi api
This commit is contained in:
parent
8e7f69f296
commit
7f8cfcba24
|
|
@ -27,6 +27,10 @@ function routeInActionCompetences() {
|
||||||
return route.path.endsWith("/competences");
|
return route.path.endsWith("/competences");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function routeInSelfEvaluationAndFeedback() {
|
||||||
|
return route.path.endsWith("/self-evaluation-and-feedback");
|
||||||
|
}
|
||||||
|
|
||||||
onMounted(async () => {
|
onMounted(async () => {
|
||||||
log.debug("CompetenceParentPage mounted", props.courseSlug);
|
log.debug("CompetenceParentPage mounted", props.courseSlug);
|
||||||
});
|
});
|
||||||
|
|
@ -79,6 +83,20 @@ onMounted(async () => {
|
||||||
</router-link>
|
</router-link>
|
||||||
</li>
|
</li>
|
||||||
|
|
||||||
|
<li
|
||||||
|
class="border-t-2 border-t-transparent lg:ml-12"
|
||||||
|
:class="{
|
||||||
|
'border-b-2 border-b-blue-900': routeInSelfEvaluationAndFeedback(),
|
||||||
|
}"
|
||||||
|
>
|
||||||
|
<router-link
|
||||||
|
:to="`/course/${courseSlug}/competence/self-evaluation-and-feedback`"
|
||||||
|
class="block py-3"
|
||||||
|
>
|
||||||
|
{{ $t("a.Selbst- und Fremdeinschätzungen") }}
|
||||||
|
</router-link>
|
||||||
|
</li>
|
||||||
|
|
||||||
<!-- Add similar logic for other `li` items as you expand the list -->
|
<!-- Add similar logic for other `li` items as you expand the list -->
|
||||||
<li class="ml-6 inline-block lg:ml-12"></li>
|
<li class="ml-6 inline-block lg:ml-12"></li>
|
||||||
</ul>
|
</ul>
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,9 @@
|
||||||
|
<script setup lang="ts"></script>
|
||||||
|
|
||||||
|
<template>
|
||||||
|
<div>
|
||||||
|
<h1>SelfEvaluationsAndFeedback</h1>
|
||||||
|
</div>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<style scoped></style>
|
||||||
|
|
@ -92,7 +92,6 @@ const router = createRouter({
|
||||||
props: true,
|
props: true,
|
||||||
component: () => import("@/pages/competence/CompetenceIndexPage.vue"),
|
component: () => import("@/pages/competence/CompetenceIndexPage.vue"),
|
||||||
},
|
},
|
||||||
|
|
||||||
{
|
{
|
||||||
path: "certificates",
|
path: "certificates",
|
||||||
props: true,
|
props: true,
|
||||||
|
|
@ -110,6 +109,12 @@ const router = createRouter({
|
||||||
props: true,
|
props: true,
|
||||||
component: () => import("@/pages/competence/PerformanceCriteriaPage.vue"),
|
component: () => import("@/pages/competence/PerformanceCriteriaPage.vue"),
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
path: "self-evaluation-and-feedback",
|
||||||
|
props: true,
|
||||||
|
component: () =>
|
||||||
|
import("@/pages/competence/SelfEvaluationAndFeedbackPage.vue"),
|
||||||
|
},
|
||||||
{
|
{
|
||||||
path: "competences",
|
path: "competences",
|
||||||
props: true,
|
props: true,
|
||||||
|
|
|
||||||
|
|
@ -47,6 +47,7 @@ from vbv_lernwelt.learnpath.models import (
|
||||||
LearningContentEdoniqTest,
|
LearningContentEdoniqTest,
|
||||||
LearningPath,
|
LearningPath,
|
||||||
LearningUnit,
|
LearningUnit,
|
||||||
|
LearningUnitPerformanceFeedbackType,
|
||||||
)
|
)
|
||||||
from vbv_lernwelt.learnpath.tests.learning_path_factories import (
|
from vbv_lernwelt.learnpath.tests.learning_path_factories import (
|
||||||
CircleFactory,
|
CircleFactory,
|
||||||
|
|
@ -275,6 +276,7 @@ def create_learning_unit(
|
||||||
circle: Circle,
|
circle: Circle,
|
||||||
course: Course,
|
course: Course,
|
||||||
course_category_title: str = "Course Category",
|
course_category_title: str = "Course Category",
|
||||||
|
feedback_user: LearningUnitPerformanceFeedbackType = LearningUnitPerformanceFeedbackType.NO_FEEDBACK,
|
||||||
) -> LearningUnit:
|
) -> LearningUnit:
|
||||||
cat, _ = CourseCategory.objects.get_or_create(
|
cat, _ = CourseCategory.objects.get_or_create(
|
||||||
course=course,
|
course=course,
|
||||||
|
|
@ -285,6 +287,7 @@ def create_learning_unit(
|
||||||
title="Learning Unit",
|
title="Learning Unit",
|
||||||
parent=circle,
|
parent=circle,
|
||||||
course_category=cat,
|
course_category=cat,
|
||||||
|
feedback_user=feedback_user.value,
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -292,7 +295,7 @@ def create_performance_criteria_page(
|
||||||
course: Course,
|
course: Course,
|
||||||
course_page: CoursePage,
|
course_page: CoursePage,
|
||||||
circle: Circle,
|
circle: Circle,
|
||||||
learning_unit: LearningUnitFactory | None = None,
|
learning_unit: LearningUnitFactory | LearningUnit | None = None,
|
||||||
) -> PerformanceCriteria:
|
) -> PerformanceCriteria:
|
||||||
competence_navi_page = CompetenceNaviPageFactory(
|
competence_navi_page = CompetenceNaviPageFactory(
|
||||||
title="Competence Navi",
|
title="Competence Navi",
|
||||||
|
|
|
||||||
|
|
@ -15,6 +15,7 @@ from vbv_lernwelt.course.creators.test_utils import (
|
||||||
from vbv_lernwelt.course.models import CourseCompletionStatus, CourseSessionUser
|
from vbv_lernwelt.course.models import CourseCompletionStatus, CourseSessionUser
|
||||||
from vbv_lernwelt.course.services import mark_course_completion
|
from vbv_lernwelt.course.services import mark_course_completion
|
||||||
from vbv_lernwelt.learning_mentor.models import LearningMentor
|
from vbv_lernwelt.learning_mentor.models import LearningMentor
|
||||||
|
from vbv_lernwelt.learnpath.models import LearningUnitPerformanceFeedbackType
|
||||||
from vbv_lernwelt.self_evaluation_feedback.models import (
|
from vbv_lernwelt.self_evaluation_feedback.models import (
|
||||||
CourseCompletionFeedback,
|
CourseCompletionFeedback,
|
||||||
SelfEvaluationFeedback,
|
SelfEvaluationFeedback,
|
||||||
|
|
@ -154,7 +155,9 @@ class SelfEvaluationFeedbackAPI(APITestCase):
|
||||||
"""Tests endpoint of feedback REQUESTER"""
|
"""Tests endpoint of feedback REQUESTER"""
|
||||||
|
|
||||||
# GIVEN
|
# GIVEN
|
||||||
learning_unit = create_learning_unit(course=self.course, circle=self.circle)
|
learning_unit = create_learning_unit( # noqa
|
||||||
|
course=self.course, circle=self.circle
|
||||||
|
)
|
||||||
|
|
||||||
performance_criteria_1 = create_performance_criteria_page(
|
performance_criteria_1 = create_performance_criteria_page(
|
||||||
course=self.course,
|
course=self.course,
|
||||||
|
|
@ -204,11 +207,11 @@ class SelfEvaluationFeedbackAPI(APITestCase):
|
||||||
|
|
||||||
feedback = response.data
|
feedback = response.data
|
||||||
self.assertEqual(feedback["learning_unit_id"], learning_unit.id)
|
self.assertEqual(feedback["learning_unit_id"], learning_unit.id)
|
||||||
self.assertEqual(feedback["feedback_submitted"], False)
|
self.assertFalse(feedback["feedback_submitted"])
|
||||||
self.assertEqual(feedback["circle_name"], self.circle.title)
|
self.assertEqual(feedback["circle_name"], self.circle.title) # noqa
|
||||||
|
|
||||||
provider_user = feedback["feedback_provider_user"]
|
provider_user = feedback["feedback_provider_user"]
|
||||||
self.assertEqual(provider_user["id"], str(self.mentor.id)) # noqa
|
self.assertEqual(provider_user["id"], str(self.mentor.id))
|
||||||
self.assertEqual(provider_user["first_name"], self.mentor.first_name)
|
self.assertEqual(provider_user["first_name"], self.mentor.first_name)
|
||||||
self.assertEqual(provider_user["last_name"], self.mentor.last_name)
|
self.assertEqual(provider_user["last_name"], self.mentor.last_name)
|
||||||
self.assertEqual(provider_user["avatar_url"], self.mentor.avatar_url)
|
self.assertEqual(provider_user["avatar_url"], self.mentor.avatar_url)
|
||||||
|
|
@ -243,11 +246,205 @@ class SelfEvaluationFeedbackAPI(APITestCase):
|
||||||
CourseCompletionStatus.UNKNOWN.value,
|
CourseCompletionStatus.UNKNOWN.value,
|
||||||
)
|
)
|
||||||
|
|
||||||
|
def test_feedbacks_with_mixed_completion_statuses(self):
|
||||||
|
"""Case: CourseCompletion AND feedbacks with mixed completion statuses"""
|
||||||
|
|
||||||
|
# GIVEN
|
||||||
|
learning_unit = create_learning_unit(
|
||||||
|
course=self.course,
|
||||||
|
circle=self.circle,
|
||||||
|
feedback_user=LearningUnitPerformanceFeedbackType.MENTOR_FEEDBACK,
|
||||||
|
)
|
||||||
|
|
||||||
|
feedback = create_self_evaluation_feedback(
|
||||||
|
learning_unit=learning_unit,
|
||||||
|
feedback_requester_user=self.member,
|
||||||
|
feedback_provider_user=self.mentor,
|
||||||
|
)
|
||||||
|
|
||||||
|
feedback.feedback_submitted = True
|
||||||
|
feedback.save()
|
||||||
|
|
||||||
|
for status in [
|
||||||
|
CourseCompletionStatus.SUCCESS,
|
||||||
|
CourseCompletionStatus.FAIL,
|
||||||
|
CourseCompletionStatus.UNKNOWN,
|
||||||
|
]:
|
||||||
|
criteria_page = create_performance_criteria_page(
|
||||||
|
course=self.course,
|
||||||
|
course_page=self.course_page,
|
||||||
|
circle=self.circle,
|
||||||
|
learning_unit=learning_unit,
|
||||||
|
)
|
||||||
|
|
||||||
|
# self assessment
|
||||||
|
completion = mark_course_completion(
|
||||||
|
page=criteria_page,
|
||||||
|
user=self.member,
|
||||||
|
course_session=self.course_session,
|
||||||
|
completion_status=status.value,
|
||||||
|
)
|
||||||
|
|
||||||
|
# feedback assessment
|
||||||
|
CourseCompletionFeedback.objects.create(
|
||||||
|
feedback=feedback,
|
||||||
|
course_completion=completion,
|
||||||
|
feedback_assessment=status.value,
|
||||||
|
)
|
||||||
|
|
||||||
|
self.client.force_login(self.member)
|
||||||
|
|
||||||
|
# WHEN
|
||||||
|
response = self.client.get(
|
||||||
|
reverse(
|
||||||
|
"get_self_evaluation_feedbacks_as_requester",
|
||||||
|
args=[self.course_session.id],
|
||||||
|
)
|
||||||
|
)
|
||||||
|
|
||||||
|
# THEN
|
||||||
|
self.assertEqual(response.status_code, 200)
|
||||||
|
|
||||||
|
result = response.data["results"][0]
|
||||||
|
|
||||||
|
self_assessment = result["self_assessment"]
|
||||||
|
self.assertEqual(self_assessment["pass"], 1)
|
||||||
|
self.assertEqual(self_assessment["fail"], 1)
|
||||||
|
self.assertEqual(self_assessment["unknown"], 1)
|
||||||
|
|
||||||
|
feedback_assessment = result["feedback_assessment"]
|
||||||
|
self.assertEqual(feedback_assessment["counts"]["pass"], 1)
|
||||||
|
self.assertEqual(feedback_assessment["counts"]["fail"], 1)
|
||||||
|
self.assertEqual(feedback_assessment["counts"]["unknown"], 1)
|
||||||
|
|
||||||
|
self.assertTrue(feedback_assessment["submitted_by_provider"])
|
||||||
|
self.assertEqual(
|
||||||
|
feedback_assessment["provider_user"]["id"], str(self.mentor.id)
|
||||||
|
)
|
||||||
|
|
||||||
|
def test_no_feedbacks_but_with_completion_status(self):
|
||||||
|
"""Case: CourseCompletion but NO feedback"""
|
||||||
|
|
||||||
|
# GIVEN
|
||||||
|
learning_unit_with_success_feedback = create_learning_unit(
|
||||||
|
course=self.course,
|
||||||
|
circle=self.circle,
|
||||||
|
feedback_user=LearningUnitPerformanceFeedbackType.MENTOR_FEEDBACK,
|
||||||
|
)
|
||||||
|
|
||||||
|
performance_criteria_page = create_performance_criteria_page(
|
||||||
|
course=self.course,
|
||||||
|
course_page=self.course_page,
|
||||||
|
circle=self.circle,
|
||||||
|
learning_unit=learning_unit_with_success_feedback,
|
||||||
|
)
|
||||||
|
|
||||||
|
# IMPORTANT: CourseCompletion but NO feedback!
|
||||||
|
|
||||||
|
mark_course_completion(
|
||||||
|
page=performance_criteria_page,
|
||||||
|
user=self.member,
|
||||||
|
course_session=self.course_session,
|
||||||
|
completion_status=CourseCompletionStatus.SUCCESS.value,
|
||||||
|
)
|
||||||
|
|
||||||
|
self.client.force_login(self.member)
|
||||||
|
|
||||||
|
# WHEN
|
||||||
|
response = self.client.get(
|
||||||
|
reverse(
|
||||||
|
"get_self_evaluation_feedbacks_as_requester",
|
||||||
|
args=[self.course_session.id],
|
||||||
|
)
|
||||||
|
)
|
||||||
|
|
||||||
|
# THEN
|
||||||
|
self.assertEqual(response.status_code, 200)
|
||||||
|
|
||||||
|
result = response.data["results"][0]
|
||||||
|
self.assertEqual(result["self_assessment"]["pass"], 1)
|
||||||
|
self.assertEqual(result["self_assessment"]["fail"], 0)
|
||||||
|
self.assertEqual(result["self_assessment"]["unknown"], 0)
|
||||||
|
|
||||||
|
def test_feedbacks_not_started(self):
|
||||||
|
"""Case: Learning unit with no completion status and no feedback"""
|
||||||
|
|
||||||
|
# GIVEN
|
||||||
|
learning_unit = create_learning_unit( # noqa
|
||||||
|
course=self.course,
|
||||||
|
circle=self.circle,
|
||||||
|
feedback_user=LearningUnitPerformanceFeedbackType.MENTOR_FEEDBACK,
|
||||||
|
)
|
||||||
|
|
||||||
|
create_performance_criteria_page(
|
||||||
|
course=self.course,
|
||||||
|
course_page=self.course_page,
|
||||||
|
circle=self.circle,
|
||||||
|
learning_unit=learning_unit,
|
||||||
|
)
|
||||||
|
|
||||||
|
self.client.force_login(self.member)
|
||||||
|
|
||||||
|
# WHEN
|
||||||
|
response = self.client.get(
|
||||||
|
reverse(
|
||||||
|
"get_self_evaluation_feedbacks_as_requester",
|
||||||
|
args=[self.course_session.id],
|
||||||
|
)
|
||||||
|
)
|
||||||
|
|
||||||
|
# THEN
|
||||||
|
self.assertEqual(response.status_code, 200)
|
||||||
|
|
||||||
|
result = response.data["results"][0]
|
||||||
|
self.assertEqual(result["self_assessment"]["pass"], 0)
|
||||||
|
self.assertEqual(result["self_assessment"]["fail"], 0)
|
||||||
|
self.assertEqual(result["self_assessment"]["unknown"], 1)
|
||||||
|
|
||||||
|
def test_feedbacks_metadata(self):
|
||||||
|
# GIVEN
|
||||||
|
learning_unit = create_learning_unit( # noqa
|
||||||
|
course=self.course,
|
||||||
|
circle=self.circle,
|
||||||
|
feedback_user=LearningUnitPerformanceFeedbackType.MENTOR_FEEDBACK,
|
||||||
|
)
|
||||||
|
|
||||||
|
create_performance_criteria_page(
|
||||||
|
course=self.course,
|
||||||
|
course_page=self.course_page,
|
||||||
|
circle=self.circle,
|
||||||
|
learning_unit=learning_unit,
|
||||||
|
)
|
||||||
|
|
||||||
|
self.client.force_login(self.member)
|
||||||
|
|
||||||
|
# WHEN
|
||||||
|
response = self.client.get(
|
||||||
|
reverse(
|
||||||
|
"get_self_evaluation_feedbacks_as_requester",
|
||||||
|
args=[self.course_session.id],
|
||||||
|
)
|
||||||
|
)
|
||||||
|
|
||||||
|
# THEN
|
||||||
|
self.assertEqual(response.status_code, 200)
|
||||||
|
|
||||||
|
result = response.data["results"][0]
|
||||||
|
self.assertEqual(result["title"], learning_unit.title)
|
||||||
|
self.assertEqual(result["id"], learning_unit.id)
|
||||||
|
|
||||||
|
circles = response.data["circles"]
|
||||||
|
self.assertEqual(len(circles), 1)
|
||||||
|
self.assertEqual(circles[0]["id"], self.circle.id)
|
||||||
|
self.assertEqual(circles[0]["title"], self.circle.title)
|
||||||
|
|
||||||
def test_get_self_evaluation_feedback_as_provider(self):
|
def test_get_self_evaluation_feedback_as_provider(self):
|
||||||
"""Tests endpoint of feedback PROVIDER"""
|
"""Tests endpoint of feedback PROVIDER"""
|
||||||
|
|
||||||
# GIVEN
|
# GIVEN
|
||||||
learning_unit = create_learning_unit(course=self.course, circle=self.circle)
|
learning_unit = create_learning_unit( # noqa
|
||||||
|
course=self.course, circle=self.circle
|
||||||
|
)
|
||||||
|
|
||||||
performance_criteria_1 = create_performance_criteria_page(
|
performance_criteria_1 = create_performance_criteria_page(
|
||||||
course=self.course,
|
course=self.course,
|
||||||
|
|
@ -299,7 +496,7 @@ class SelfEvaluationFeedbackAPI(APITestCase):
|
||||||
self.assertEqual(feedback["learning_unit_id"], learning_unit.id)
|
self.assertEqual(feedback["learning_unit_id"], learning_unit.id)
|
||||||
self.assertEqual(feedback["title"], learning_unit.title)
|
self.assertEqual(feedback["title"], learning_unit.title)
|
||||||
self.assertEqual(feedback["feedback_submitted"], False)
|
self.assertEqual(feedback["feedback_submitted"], False)
|
||||||
self.assertEqual(feedback["circle_name"], self.circle.title)
|
self.assertEqual(feedback["circle_name"], self.circle.title) # noqa
|
||||||
|
|
||||||
provider_user = feedback["feedback_provider_user"]
|
provider_user = feedback["feedback_provider_user"]
|
||||||
self.assertEqual(provider_user["id"], str(self.mentor.id)) # noqa
|
self.assertEqual(provider_user["id"], str(self.mentor.id)) # noqa
|
||||||
|
|
@ -404,7 +601,7 @@ class SelfEvaluationFeedbackAPI(APITestCase):
|
||||||
self.client.force_login(self.mentor)
|
self.client.force_login(self.mentor)
|
||||||
|
|
||||||
# WHEN
|
# WHEN
|
||||||
response = self.client.put(
|
self.client.put(
|
||||||
reverse(
|
reverse(
|
||||||
"release_self_evaluation_feedback", args=[self_evaluation_feedback.id]
|
"release_self_evaluation_feedback", args=[self_evaluation_feedback.id]
|
||||||
),
|
),
|
||||||
|
|
|
||||||
|
|
@ -4,11 +4,18 @@ from vbv_lernwelt.self_evaluation_feedback.views import (
|
||||||
add_provider_self_evaluation_feedback,
|
add_provider_self_evaluation_feedback,
|
||||||
get_self_evaluation_feedback_as_provider,
|
get_self_evaluation_feedback_as_provider,
|
||||||
get_self_evaluation_feedback_as_requester,
|
get_self_evaluation_feedback_as_requester,
|
||||||
|
get_self_evaluation_feedbacks_as_requester,
|
||||||
release_provider_self_evaluation_feedback,
|
release_provider_self_evaluation_feedback,
|
||||||
start_self_evaluation_feedback,
|
start_self_evaluation_feedback,
|
||||||
)
|
)
|
||||||
|
|
||||||
urlpatterns = [
|
urlpatterns = [
|
||||||
|
# /requester/* URLs -> For the user who requests feedback
|
||||||
|
path(
|
||||||
|
"requester/<int:course_session_id>/feedbacks",
|
||||||
|
get_self_evaluation_feedbacks_as_requester,
|
||||||
|
name="get_self_evaluation_feedbacks_as_requester",
|
||||||
|
),
|
||||||
path(
|
path(
|
||||||
"requester/<int:learning_unit_id>/feedback/start",
|
"requester/<int:learning_unit_id>/feedback/start",
|
||||||
start_self_evaluation_feedback,
|
start_self_evaluation_feedback,
|
||||||
|
|
@ -19,6 +26,7 @@ urlpatterns = [
|
||||||
get_self_evaluation_feedback_as_requester,
|
get_self_evaluation_feedback_as_requester,
|
||||||
name="get_self_evaluation_feedback_as_requester",
|
name="get_self_evaluation_feedback_as_requester",
|
||||||
),
|
),
|
||||||
|
# /provider/* URLs -> For the user who is providing feedback
|
||||||
path(
|
path(
|
||||||
"provider/<int:learning_unit_id>/feedback",
|
"provider/<int:learning_unit_id>/feedback",
|
||||||
get_self_evaluation_feedback_as_provider,
|
get_self_evaluation_feedback_as_provider,
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,114 @@
|
||||||
|
from typing import NamedTuple
|
||||||
|
|
||||||
|
from django.db.models import Case, Count, IntegerField, Sum, Value, When
|
||||||
|
from django.db.models.functions import Coalesce
|
||||||
|
|
||||||
|
from vbv_lernwelt.core.admin import User
|
||||||
|
from vbv_lernwelt.course.models import CourseCompletion, CourseCompletionStatus
|
||||||
|
from vbv_lernwelt.learnpath.models import LearningUnit
|
||||||
|
from vbv_lernwelt.self_evaluation_feedback.models import (
|
||||||
|
CourseCompletionFeedback,
|
||||||
|
SelfEvaluationFeedback,
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
|
class AssessmentCounts(NamedTuple):
|
||||||
|
pass_count: int
|
||||||
|
fail_count: int
|
||||||
|
unknown_count: int
|
||||||
|
|
||||||
|
|
||||||
|
def get_self_evaluation_feedback_counts(
|
||||||
|
feedback: SelfEvaluationFeedback,
|
||||||
|
):
|
||||||
|
course_completion_feedback = CourseCompletionFeedback.objects.filter(
|
||||||
|
feedback=feedback
|
||||||
|
).aggregate(
|
||||||
|
pass_count=Coalesce(
|
||||||
|
Sum(
|
||||||
|
Case(
|
||||||
|
When(
|
||||||
|
feedback_assessment=CourseCompletionStatus.SUCCESS.value,
|
||||||
|
then=Value(1),
|
||||||
|
),
|
||||||
|
output_field=IntegerField(),
|
||||||
|
)
|
||||||
|
),
|
||||||
|
Value(0),
|
||||||
|
),
|
||||||
|
fail_count=Coalesce(
|
||||||
|
Sum(
|
||||||
|
Case(
|
||||||
|
When(
|
||||||
|
feedback_assessment=CourseCompletionStatus.FAIL.value,
|
||||||
|
then=Value(1),
|
||||||
|
),
|
||||||
|
output_field=IntegerField(),
|
||||||
|
)
|
||||||
|
),
|
||||||
|
Value(0),
|
||||||
|
),
|
||||||
|
unknown_count=Coalesce(
|
||||||
|
Sum(
|
||||||
|
Case(
|
||||||
|
When(
|
||||||
|
feedback_assessment=CourseCompletionStatus.UNKNOWN.value,
|
||||||
|
then=Value(1),
|
||||||
|
),
|
||||||
|
output_field=IntegerField(),
|
||||||
|
)
|
||||||
|
),
|
||||||
|
Value(0),
|
||||||
|
),
|
||||||
|
)
|
||||||
|
|
||||||
|
return AssessmentCounts(
|
||||||
|
pass_count=course_completion_feedback.get("pass_count", 0),
|
||||||
|
fail_count=course_completion_feedback.get("fail_count", 0),
|
||||||
|
unknown_count=course_completion_feedback.get("unknown_count", 0),
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
|
def get_self_assessment_counts(
|
||||||
|
learning_unit: LearningUnit, user: User
|
||||||
|
) -> AssessmentCounts:
|
||||||
|
performance_criteria = learning_unit.performancecriteria_set.all()
|
||||||
|
|
||||||
|
completion_counts = CourseCompletion.objects.filter(
|
||||||
|
page__in=performance_criteria, user=user
|
||||||
|
).aggregate(
|
||||||
|
pass_count=Count(
|
||||||
|
Case(
|
||||||
|
When(completion_status=CourseCompletionStatus.SUCCESS.value, then=1),
|
||||||
|
output_field=IntegerField(),
|
||||||
|
)
|
||||||
|
),
|
||||||
|
fail_count=Count(
|
||||||
|
Case(
|
||||||
|
When(completion_status=CourseCompletionStatus.FAIL.value, then=1),
|
||||||
|
output_field=IntegerField(),
|
||||||
|
)
|
||||||
|
),
|
||||||
|
unknown_count=Count(
|
||||||
|
Case(
|
||||||
|
When(completion_status=CourseCompletionStatus.UNKNOWN.value, then=1),
|
||||||
|
output_field=IntegerField(),
|
||||||
|
)
|
||||||
|
),
|
||||||
|
)
|
||||||
|
|
||||||
|
pass_count = completion_counts.get("pass_count", 0)
|
||||||
|
fail_count = completion_counts.get("fail_count", 0)
|
||||||
|
unknown_count = completion_counts.get("unknown_count", 0)
|
||||||
|
|
||||||
|
# not yet completed performance criteria are unknown
|
||||||
|
if pass_count + fail_count + unknown_count < performance_criteria.count():
|
||||||
|
unknown_count += performance_criteria.count() - (
|
||||||
|
pass_count + fail_count + unknown_count
|
||||||
|
)
|
||||||
|
|
||||||
|
return AssessmentCounts(
|
||||||
|
pass_count=pass_count,
|
||||||
|
fail_count=fail_count,
|
||||||
|
unknown_count=unknown_count,
|
||||||
|
)
|
||||||
|
|
@ -5,9 +5,14 @@ from rest_framework.permissions import IsAuthenticated
|
||||||
from rest_framework.response import Response
|
from rest_framework.response import Response
|
||||||
|
|
||||||
from vbv_lernwelt.core.models import User
|
from vbv_lernwelt.core.models import User
|
||||||
from vbv_lernwelt.course.models import CourseCompletion
|
from vbv_lernwelt.core.serializers import UserSerializer
|
||||||
|
from vbv_lernwelt.course.models import CourseCompletion, CourseSession
|
||||||
from vbv_lernwelt.learning_mentor.models import LearningMentor
|
from vbv_lernwelt.learning_mentor.models import LearningMentor
|
||||||
from vbv_lernwelt.learnpath.models import LearningUnit
|
from vbv_lernwelt.learnpath.models import (
|
||||||
|
Circle,
|
||||||
|
LearningUnit,
|
||||||
|
LearningUnitPerformanceFeedbackType,
|
||||||
|
)
|
||||||
from vbv_lernwelt.notify.services import NotificationService
|
from vbv_lernwelt.notify.services import NotificationService
|
||||||
from vbv_lernwelt.self_evaluation_feedback.models import (
|
from vbv_lernwelt.self_evaluation_feedback.models import (
|
||||||
CourseCompletionFeedback,
|
CourseCompletionFeedback,
|
||||||
|
|
@ -16,6 +21,10 @@ from vbv_lernwelt.self_evaluation_feedback.models import (
|
||||||
from vbv_lernwelt.self_evaluation_feedback.serializers import (
|
from vbv_lernwelt.self_evaluation_feedback.serializers import (
|
||||||
SelfEvaluationFeedbackSerializer,
|
SelfEvaluationFeedbackSerializer,
|
||||||
)
|
)
|
||||||
|
from vbv_lernwelt.self_evaluation_feedback.utils import (
|
||||||
|
get_self_assessment_counts,
|
||||||
|
get_self_evaluation_feedback_counts,
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
@api_view(["POST"])
|
@api_view(["POST"])
|
||||||
|
|
@ -80,6 +89,66 @@ def get_self_evaluation_feedback_as_provider(request, learning_unit_id):
|
||||||
return Response(SelfEvaluationFeedbackSerializer(feedback).data)
|
return Response(SelfEvaluationFeedbackSerializer(feedback).data)
|
||||||
|
|
||||||
|
|
||||||
|
@api_view(["GET"])
|
||||||
|
@permission_classes([IsAuthenticated])
|
||||||
|
def get_self_evaluation_feedbacks_as_requester(request, course_session_id: int):
|
||||||
|
course_session = get_object_or_404(CourseSession, id=course_session_id)
|
||||||
|
|
||||||
|
results = []
|
||||||
|
circle_ids = set()
|
||||||
|
|
||||||
|
for learning_unit in LearningUnit.objects.filter(
|
||||||
|
feedback_user=LearningUnitPerformanceFeedbackType.MENTOR_FEEDBACK.value,
|
||||||
|
course_category__course=course_session.course,
|
||||||
|
):
|
||||||
|
circle = learning_unit.get_parent().specific
|
||||||
|
circle_ids.add(circle.id)
|
||||||
|
|
||||||
|
feedback_assessment = None
|
||||||
|
|
||||||
|
feedback = SelfEvaluationFeedback.objects.filter(
|
||||||
|
learning_unit=learning_unit,
|
||||||
|
feedback_requester_user=request.user,
|
||||||
|
).first()
|
||||||
|
|
||||||
|
if feedback:
|
||||||
|
feedback_counts = get_self_evaluation_feedback_counts(feedback)
|
||||||
|
|
||||||
|
feedback_assessment = {
|
||||||
|
"submitted_by_provider": feedback.feedback_submitted,
|
||||||
|
"provider_user": UserSerializer(feedback.feedback_provider_user).data,
|
||||||
|
"counts": {
|
||||||
|
"pass": feedback_counts.pass_count,
|
||||||
|
"fail": feedback_counts.fail_count,
|
||||||
|
"unknown": feedback_counts.unknown_count,
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
self_assessment_counts = get_self_assessment_counts(learning_unit, request.user)
|
||||||
|
|
||||||
|
results.append(
|
||||||
|
{
|
||||||
|
"id": learning_unit.id,
|
||||||
|
"title": learning_unit.title,
|
||||||
|
"feedback_assessment": feedback_assessment,
|
||||||
|
"self_assessment": {
|
||||||
|
"pass": self_assessment_counts.pass_count,
|
||||||
|
"fail": self_assessment_counts.fail_count,
|
||||||
|
"unknown": self_assessment_counts.unknown_count,
|
||||||
|
},
|
||||||
|
}
|
||||||
|
)
|
||||||
|
|
||||||
|
return Response(
|
||||||
|
{
|
||||||
|
"results": results,
|
||||||
|
"circles": list(
|
||||||
|
Circle.objects.filter(id__in=circle_ids).values("id", "title")
|
||||||
|
),
|
||||||
|
}
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
@api_view(["GET"])
|
@api_view(["GET"])
|
||||||
@permission_classes([IsAuthenticated])
|
@permission_classes([IsAuthenticated])
|
||||||
def get_self_evaluation_feedback_as_requester(request, learning_unit_id):
|
def get_self_evaluation_feedback_as_requester(request, learning_unit_id):
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue