Search in sources :

Example 46 with Exam

use of de.tum.in.www1.artemis.domain.exam.Exam in project ArTEMiS by ls1intum.

the class ExamIntegrationTest method testRemovingAllStudentsAndParticipations.

@Test
@WithMockUser(username = "admin", roles = "ADMIN")
public void testRemovingAllStudentsAndParticipations() throws Exception {
    Exam exam = database.setupExamWithExerciseGroupsExercisesRegisteredStudents(course1);
    // Generate student exams
    List<StudentExam> studentExams = request.postListWithResponseBody("/api/courses/" + course1.getId() + "/exams/" + exam.getId() + "/generate-student-exams", Optional.empty(), StudentExam.class, HttpStatus.OK);
    assertThat(studentExams).hasSize(4);
    assertThat(exam.getRegisteredUsers()).hasSize(4);
    // /courses/{courseId}/exams/{examId}/student-exams/start-exercises
    Integer numberOfGeneratedParticipations = request.postWithResponseBody("/api/courses/" + course1.getId() + "/exams/" + exam.getId() + "/student-exams/start-exercises", Optional.empty(), Integer.class, HttpStatus.OK);
    assertThat(numberOfGeneratedParticipations).isEqualTo(16);
    // Fetch student exams
    List<StudentExam> studentExamsDB = request.getList("/api/courses/" + course1.getId() + "/exams/" + exam.getId() + "/student-exams", HttpStatus.OK, StudentExam.class);
    assertThat(studentExamsDB).hasSize(4);
    List<StudentParticipation> participationList = new ArrayList<>();
    Exercise[] exercises = examRepository.findAllExercisesByExamId(exam.getId()).toArray(new Exercise[0]);
    for (Exercise value : exercises) {
        participationList.addAll(studentParticipationRepository.findByExerciseId(value.getId()));
    }
    assertThat(participationList).hasSize(16);
    // TODO there should be some participation but no submissions unfortunately
    // remove all students
    var paramsParticipations = new LinkedMultiValueMap<String, String>();
    paramsParticipations.add("withParticipationsAndSubmission", "true");
    request.delete("/api/courses/" + course1.getId() + "/exams/" + exam.getId() + "/students", HttpStatus.OK, paramsParticipations);
    // Get the exam with all registered users
    var params = new LinkedMultiValueMap<String, String>();
    params.add("withStudents", "true");
    Exam storedExam = request.get("/api/courses/" + course1.getId() + "/exams/" + exam.getId(), HttpStatus.OK, Exam.class, params);
    assertThat(storedExam.getRegisteredUsers()).isEmpty();
    // Fetch student exams
    studentExamsDB = request.getList("/api/courses/" + course1.getId() + "/exams/" + exam.getId() + "/student-exams", HttpStatus.OK, StudentExam.class);
    assertThat(studentExamsDB).isEmpty();
    // Fetch participations
    exercises = examRepository.findAllExercisesByExamId(exam.getId()).toArray(new Exercise[0]);
    participationList = new ArrayList<>();
    for (Exercise exercise : exercises) {
        participationList.addAll(studentParticipationRepository.findByExerciseId(exercise.getId()));
    }
    assertThat(participationList).isEmpty();
}
Also used : QuizExercise(de.tum.in.www1.artemis.domain.quiz.QuizExercise) ModelingExercise(de.tum.in.www1.artemis.domain.modeling.ModelingExercise) LinkedMultiValueMap(org.springframework.util.LinkedMultiValueMap) StudentExam(de.tum.in.www1.artemis.domain.exam.StudentExam) StudentExam(de.tum.in.www1.artemis.domain.exam.StudentExam) Exam(de.tum.in.www1.artemis.domain.exam.Exam) StudentParticipation(de.tum.in.www1.artemis.domain.participation.StudentParticipation) WithMockUser(org.springframework.security.test.context.support.WithMockUser) Test(org.junit.jupiter.api.Test)

Example 47 with Exam

use of de.tum.in.www1.artemis.domain.exam.Exam in project ArTEMiS by ls1intum.

the class ExamIntegrationTest method testCreateExam_checkCourseAccess_InstructorNotInCourse_forbidden.

@Test
@WithMockUser(username = "instructor6", roles = "INSTRUCTOR")
public void testCreateExam_checkCourseAccess_InstructorNotInCourse_forbidden() throws Exception {
    Exam exam = ModelFactory.generateExam(course1);
    request.post("/api/courses/" + course1.getId() + "/exams", exam, HttpStatus.FORBIDDEN);
}
Also used : StudentExam(de.tum.in.www1.artemis.domain.exam.StudentExam) Exam(de.tum.in.www1.artemis.domain.exam.Exam) WithMockUser(org.springframework.security.test.context.support.WithMockUser) Test(org.junit.jupiter.api.Test)

Example 48 with Exam

use of de.tum.in.www1.artemis.domain.exam.Exam in project ArTEMiS by ls1intum.

the class ExamIntegrationTest method testStartExercisesWithModelingExercise.

@Test
@WithMockUser(username = "instructor1", roles = "INSTRUCTOR")
public void testStartExercisesWithModelingExercise() throws Exception {
    // TODO IMPORTANT test more complex exam configurations (mixed exercise type, more variants and more registered students)
    // registering users
    var student1 = database.getUserByLogin("student1");
    var student2 = database.getUserByLogin("student2");
    var registeredUsers = Set.of(student1, student2);
    exam2.setRegisteredUsers(registeredUsers);
    // setting dates
    exam2.setStartDate(now().plusHours(2));
    exam2.setEndDate(now().plusHours(3));
    exam2.setVisibleDate(now().plusHours(1));
    // creating exercise
    ModelingExercise modelingExercise = ModelFactory.generateModelingExerciseForExam(DiagramType.ClassDiagram, exam2.getExerciseGroups().get(0));
    exam2.getExerciseGroups().get(0).addExercise(modelingExercise);
    exerciseGroupRepository.save(exam2.getExerciseGroups().get(0));
    modelingExercise = exerciseRepo.save(modelingExercise);
    List<StudentExam> createdStudentExams = new ArrayList<>();
    // creating student exams
    for (User user : registeredUsers) {
        StudentExam studentExam = new StudentExam();
        studentExam.addExercise(modelingExercise);
        studentExam.setUser(user);
        exam2.addStudentExam(studentExam);
        createdStudentExams.add(studentExamRepository.save(studentExam));
    }
    exam2 = examRepository.save(exam2);
    // invoke start exercises
    Integer noGeneratedParticipations = request.postWithResponseBody("/api/courses/" + course1.getId() + "/exams/" + exam2.getId() + "/student-exams/start-exercises", Optional.empty(), Integer.class, HttpStatus.OK);
    assertThat(noGeneratedParticipations).isEqualTo(exam2.getStudentExams().size());
    List<Participation> studentParticipations = participationTestRepository.findAllWithSubmissions();
    for (Participation participation : studentParticipations) {
        assertThat(participation.getExercise()).isEqualTo(modelingExercise);
        assertThat(participation.getExercise().getCourseViaExerciseGroupOrCourseMember()).isNotNull();
        assertThat(participation.getExercise().getExerciseGroup()).isEqualTo(exam2.getExerciseGroups().get(0));
        assertThat(participation.getSubmissions()).hasSize(1);
        var textSubmission = (ModelingSubmission) participation.getSubmissions().iterator().next();
        assertThat(textSubmission.getModel()).isNull();
        assertThat(textSubmission.getExplanationText()).isNull();
    }
    // Cleanup of Bidirectional Relationships
    for (StudentExam studentExam : createdStudentExams) {
        exam2.removeStudentExam(studentExam);
    }
    examRepository.save(exam2);
}
Also used : Participation(de.tum.in.www1.artemis.domain.participation.Participation) StudentParticipation(de.tum.in.www1.artemis.domain.participation.StudentParticipation) WithMockUser(org.springframework.security.test.context.support.WithMockUser) ModelingSubmission(de.tum.in.www1.artemis.domain.modeling.ModelingSubmission) ModelingExercise(de.tum.in.www1.artemis.domain.modeling.ModelingExercise) StudentExam(de.tum.in.www1.artemis.domain.exam.StudentExam) WithMockUser(org.springframework.security.test.context.support.WithMockUser) Test(org.junit.jupiter.api.Test)

Example 49 with Exam

use of de.tum.in.www1.artemis.domain.exam.Exam in project ArTEMiS by ls1intum.

the class ExamSessionIntegrationTest method initTestCase.

@BeforeEach
public void initTestCase() {
    List<User> users = database.addUsers(1, 1, 0, 1);
    Course course1 = database.addEmptyCourse();
    Exam exam1 = database.addActiveExamWithRegisteredUser(course1, users.get(0));
    studentExam1 = database.addStudentExam(exam1);
    studentExam1.setUser(users.get(0));
    studentExamRepository.save(studentExam1);
}
Also used : User(de.tum.in.www1.artemis.domain.User) WithMockUser(org.springframework.security.test.context.support.WithMockUser) Course(de.tum.in.www1.artemis.domain.Course) StudentExam(de.tum.in.www1.artemis.domain.exam.StudentExam) Exam(de.tum.in.www1.artemis.domain.exam.Exam) BeforeEach(org.junit.jupiter.api.BeforeEach)

Example 50 with Exam

use of de.tum.in.www1.artemis.domain.exam.Exam in project ArTEMiS by ls1intum.

the class FileUploadAssessmentIntegrationTest method multipleCorrectionRoundsForExam.

@Test
@WithMockUser(username = "tutor1", roles = "TA")
public void multipleCorrectionRoundsForExam() throws Exception {
    // Setup exam with 2 correction rounds and a programming exercise
    ExerciseGroup exerciseGroup1 = new ExerciseGroup();
    Exam exam = database.addExam(course);
    exam.setNumberOfCorrectionRoundsInExam(2);
    exam.addExerciseGroup(exerciseGroup1);
    exam.setVisibleDate(ZonedDateTime.now().minusHours(3));
    exam.setStartDate(ZonedDateTime.now().minusHours(2));
    exam.setEndDate(ZonedDateTime.now().minusHours(1));
    exam = examRepository.save(exam);
    Exam examWithExerciseGroups = examRepository.findWithExerciseGroupsAndExercisesById(exam.getId()).get();
    exerciseGroup1 = examWithExerciseGroups.getExerciseGroups().get(0);
    FileUploadExercise exercise = ModelFactory.generateFileUploadExerciseForExam("test.pdf", exerciseGroup1);
    exercise = fileUploadExerciseRepository.save(exercise);
    exerciseGroup1.addExercise(exercise);
    // add student submission
    var submission = ModelFactory.generateFileUploadSubmission(true);
    submission = database.addFileUploadSubmission(exercise, submission, "student1");
    // verify setup
    assertThat(exam.getNumberOfCorrectionRoundsInExam()).isEqualTo(2);
    assertThat(exam.getEndDate()).isBefore(ZonedDateTime.now());
    var optionalFetchedExercise = exerciseRepository.findWithEagerStudentParticipationsStudentAndSubmissionsById(exercise.getId());
    assertThat(optionalFetchedExercise).isPresent();
    final var exerciseWithParticipation = optionalFetchedExercise.get();
    final var studentParticipation = exerciseWithParticipation.getStudentParticipations().stream().iterator().next();
    // request to manually assess latest submission (correction round: 0)
    LinkedMultiValueMap<String, String> params = new LinkedMultiValueMap<>();
    params.add("lock", "true");
    params.add("correction-round", "0");
    FileUploadSubmission submissionWithoutFirstAssessment = request.get("/api/exercises/" + exerciseWithParticipation.getId() + "/file-upload-submission-without-assessment", HttpStatus.OK, FileUploadSubmission.class, params);
    // verify that no new submission was created
    assertThat(submissionWithoutFirstAssessment).isEqualTo(submission);
    // verify that the lock has been set
    assertThat(submissionWithoutFirstAssessment.getLatestResult()).isNotNull();
    assertThat(submissionWithoutFirstAssessment.getLatestResult().getAssessor().getLogin()).isEqualTo("tutor1");
    assertThat(submissionWithoutFirstAssessment.getLatestResult().getAssessmentType()).isEqualTo(AssessmentType.MANUAL);
    // make sure that new result correctly appears inside the continue box
    LinkedMultiValueMap<String, String> paramsGetAssessedCR1Tutor1 = new LinkedMultiValueMap<>();
    paramsGetAssessedCR1Tutor1.add("assessedByTutor", "true");
    paramsGetAssessedCR1Tutor1.add("correction-round", "0");
    var assessedSubmissionList = request.getList("/api/exercises/" + exerciseWithParticipation.getId() + "/file-upload-submissions", HttpStatus.OK, FileUploadSubmission.class, paramsGetAssessedCR1Tutor1);
    assertThat(assessedSubmissionList).hasSize(1);
    assertThat(assessedSubmissionList.get(0).getId()).isEqualTo(submissionWithoutFirstAssessment.getId());
    assertThat(assessedSubmissionList.get(0).getResultForCorrectionRound(0)).isEqualTo(submissionWithoutFirstAssessment.getLatestResult());
    // assess submission and submit
    List<Feedback> feedbacks = ModelFactory.generateFeedback().stream().peek(feedback -> feedback.setDetailText("Good work here")).collect(Collectors.toList());
    params = new LinkedMultiValueMap<>();
    params.add("submit", "true");
    final Result firstSubmittedManualResult = request.putWithResponseBodyAndParams(API_FILE_UPLOAD_SUBMISSIONS + submissionWithoutFirstAssessment.getId() + "/feedback", feedbacks, Result.class, HttpStatus.OK, params);
    // make sure that new result correctly appears after the assessment for first correction round
    assessedSubmissionList = request.getList("/api/exercises/" + exerciseWithParticipation.getId() + "/file-upload-submissions", HttpStatus.OK, FileUploadSubmission.class, paramsGetAssessedCR1Tutor1);
    assertThat(assessedSubmissionList).hasSize(1);
    assertThat(assessedSubmissionList.get(0).getId()).isEqualTo(submissionWithoutFirstAssessment.getId());
    assertThat(assessedSubmissionList.get(0).getResultForCorrectionRound(0)).isNotNull();
    assertThat(firstSubmittedManualResult.getAssessor().getLogin()).isEqualTo("tutor1");
    // verify that the result contains the relationship
    assertThat(firstSubmittedManualResult).isNotNull();
    assertThat(firstSubmittedManualResult.getParticipation()).isEqualTo(studentParticipation);
    // verify that the relationship between student participation,
    var databaseRelationshipStateOfResultsOverParticipation = studentParticipationRepository.findWithEagerLegalSubmissionsAndResultsAssessorsById(studentParticipation.getId());
    assertThat(databaseRelationshipStateOfResultsOverParticipation).isPresent();
    var fetchedParticipation = databaseRelationshipStateOfResultsOverParticipation.get();
    assertThat(fetchedParticipation.getSubmissions()).hasSize(1);
    assertThat(fetchedParticipation.findLatestSubmission()).contains(submissionWithoutFirstAssessment);
    assertThat(fetchedParticipation.findLatestLegalResult()).isEqualTo(firstSubmittedManualResult);
    var databaseRelationshipStateOfResultsOverSubmission = studentParticipationRepository.findAllWithEagerSubmissionsAndEagerResultsAndEagerAssessorByExerciseId(exercise.getId());
    assertThat(databaseRelationshipStateOfResultsOverSubmission).hasSize(1);
    fetchedParticipation = databaseRelationshipStateOfResultsOverSubmission.get(0);
    assertThat(fetchedParticipation.getSubmissions()).hasSize(1);
    assertThat(fetchedParticipation.findLatestSubmission()).isPresent();
    // it should contain the lock for the manual result
    assertThat(fetchedParticipation.findLatestSubmission().get().getResults()).hasSize(1);
    assertThat(fetchedParticipation.findLatestSubmission().get().getLatestResult()).isEqualTo(firstSubmittedManualResult);
    // SECOND ROUND OF CORRECTION
    database.changeUser("tutor2");
    LinkedMultiValueMap<String, String> paramsSecondCorrection = new LinkedMultiValueMap<>();
    paramsSecondCorrection.add("lock", "true");
    paramsSecondCorrection.add("correction-round", "1");
    final var submissionWithoutSecondAssessment = request.get("/api/exercises/" + exerciseWithParticipation.getId() + "/file-upload-submission-without-assessment", HttpStatus.OK, FileUploadSubmission.class, paramsSecondCorrection);
    // verify that the submission is not new
    assertThat(submissionWithoutSecondAssessment).isEqualTo(submission);
    // verify that the lock has been set
    assertThat(submissionWithoutSecondAssessment.getLatestResult()).isNotNull();
    assertThat(submissionWithoutSecondAssessment.getLatestResult().getAssessor().getLogin()).isEqualTo("tutor2");
    assertThat(submissionWithoutSecondAssessment.getLatestResult().getAssessmentType()).isEqualTo(AssessmentType.MANUAL);
    // verify that the relationship between student participation,
    databaseRelationshipStateOfResultsOverParticipation = studentParticipationRepository.findWithEagerLegalSubmissionsAndResultsAssessorsById(studentParticipation.getId());
    assertThat(databaseRelationshipStateOfResultsOverParticipation).isPresent();
    fetchedParticipation = databaseRelationshipStateOfResultsOverParticipation.get();
    assertThat(fetchedParticipation.getSubmissions()).hasSize(1);
    assertThat(fetchedParticipation.findLatestSubmission()).contains(submissionWithoutSecondAssessment);
    assertThat(fetchedParticipation.getResults().stream().filter(x -> x.getCompletionDate() == null).findFirst()).contains(submissionWithoutSecondAssessment.getLatestResult());
    databaseRelationshipStateOfResultsOverSubmission = studentParticipationRepository.findAllWithEagerSubmissionsAndEagerResultsAndEagerAssessorByExerciseId(exercise.getId());
    assertThat(databaseRelationshipStateOfResultsOverSubmission).hasSize(1);
    fetchedParticipation = databaseRelationshipStateOfResultsOverSubmission.get(0);
    assertThat(fetchedParticipation.getSubmissions()).hasSize(1);
    assertThat(fetchedParticipation.findLatestSubmission()).isPresent();
    assertThat(fetchedParticipation.findLatestSubmission().get().getResults()).hasSize(2);
    assertThat(fetchedParticipation.findLatestSubmission().get().getLatestResult()).isEqualTo(submissionWithoutSecondAssessment.getLatestResult());
    // assess submission and submit
    feedbacks = ModelFactory.generateFeedback().stream().peek(feedback -> feedback.setDetailText("Good work here")).collect(Collectors.toList());
    params = new LinkedMultiValueMap<>();
    params.add("submit", "true");
    final var secondSubmittedManualResult = request.putWithResponseBodyAndParams(API_FILE_UPLOAD_SUBMISSIONS + submissionWithoutFirstAssessment.getId() + "/feedback", feedbacks, Result.class, HttpStatus.OK, params);
    assertThat(secondSubmittedManualResult).isNotNull();
    // make sure that new result correctly appears after the assessment for second correction round
    LinkedMultiValueMap<String, String> paramsGetAssessedCR2 = new LinkedMultiValueMap<>();
    paramsGetAssessedCR2.add("assessedByTutor", "true");
    paramsGetAssessedCR2.add("correction-round", "1");
    assessedSubmissionList = request.getList("/api/exercises/" + exerciseWithParticipation.getId() + "/file-upload-submissions", HttpStatus.OK, FileUploadSubmission.class, paramsGetAssessedCR2);
    assertThat(assessedSubmissionList).hasSize(1);
    assertThat(assessedSubmissionList.get(0).getId()).isEqualTo(submissionWithoutSecondAssessment.getId());
    assertThat(assessedSubmissionList.get(0).getResultForCorrectionRound(1)).isEqualTo(secondSubmittedManualResult);
    // make sure that they do not appear for the first correction round as the tutor only assessed the second correction round
    LinkedMultiValueMap<String, String> paramsGetAssessedCR1 = new LinkedMultiValueMap<>();
    paramsGetAssessedCR1.add("assessedByTutor", "true");
    paramsGetAssessedCR1.add("correction-round", "0");
    assessedSubmissionList = request.getList("/api/exercises/" + exerciseWithParticipation.getId() + "/file-upload-submissions", HttpStatus.OK, FileUploadSubmission.class, paramsGetAssessedCR1);
    assertThat(assessedSubmissionList).isEmpty();
    // Student should not have received a result over WebSocket as manual correction is ongoing
    verify(messagingTemplate, never()).convertAndSendToUser(notNull(), eq(Constants.NEW_RESULT_TOPIC), isA(Result.class));
}
Also used : Offset(org.assertj.core.data.Offset) de.tum.in.www1.artemis.repository(de.tum.in.www1.artemis.repository) Assertions.assertThat(org.assertj.core.api.Assertions.assertThat) ZonedDateTime(java.time.ZonedDateTime) Autowired(org.springframework.beans.factory.annotation.Autowired) AssessmentType(de.tum.in.www1.artemis.domain.enumeration.AssessmentType) Collectors(java.util.stream.Collectors) ComplaintType(de.tum.in.www1.artemis.domain.enumeration.ComplaintType) Constants(de.tum.in.www1.artemis.config.Constants) ArrayList(java.util.ArrayList) Mockito(org.mockito.Mockito) HttpStatus(org.springframework.http.HttpStatus) List(java.util.List) de.tum.in.www1.artemis.domain(de.tum.in.www1.artemis.domain) WithMockUser(org.springframework.security.test.context.support.WithMockUser) org.junit.jupiter.api(org.junit.jupiter.api) ExerciseGroup(de.tum.in.www1.artemis.domain.exam.ExerciseGroup) StudentParticipation(de.tum.in.www1.artemis.domain.participation.StudentParticipation) ModelFactory(de.tum.in.www1.artemis.util.ModelFactory) IncludedInOverallScore(de.tum.in.www1.artemis.domain.enumeration.IncludedInOverallScore) Exam(de.tum.in.www1.artemis.domain.exam.Exam) LinkedMultiValueMap(org.springframework.util.LinkedMultiValueMap) FeedbackType(de.tum.in.www1.artemis.domain.enumeration.FeedbackType) LinkedMultiValueMap(org.springframework.util.LinkedMultiValueMap) ExerciseGroup(de.tum.in.www1.artemis.domain.exam.ExerciseGroup) Exam(de.tum.in.www1.artemis.domain.exam.Exam) WithMockUser(org.springframework.security.test.context.support.WithMockUser)

Aggregations

Exam (de.tum.in.www1.artemis.domain.exam.Exam)228 StudentExam (de.tum.in.www1.artemis.domain.exam.StudentExam)180 WithMockUser (org.springframework.security.test.context.support.WithMockUser)164 Test (org.junit.jupiter.api.Test)158 ExerciseGroup (de.tum.in.www1.artemis.domain.exam.ExerciseGroup)92 PreAuthorize (org.springframework.security.access.prepost.PreAuthorize)75 ModelingExercise (de.tum.in.www1.artemis.domain.modeling.ModelingExercise)52 EntityNotFoundException (de.tum.in.www1.artemis.web.rest.errors.EntityNotFoundException)48 AbstractSpringIntegrationBambooBitbucketJiraTest (de.tum.in.www1.artemis.AbstractSpringIntegrationBambooBitbucketJiraTest)46 StudentParticipation (de.tum.in.www1.artemis.domain.participation.StudentParticipation)46 QuizExercise (de.tum.in.www1.artemis.domain.quiz.QuizExercise)42 ZonedDateTime (java.time.ZonedDateTime)40 BadRequestAlertException (de.tum.in.www1.artemis.web.rest.errors.BadRequestAlertException)38 Course (de.tum.in.www1.artemis.domain.Course)36 GradingScale (de.tum.in.www1.artemis.domain.GradingScale)34 BeforeEach (org.junit.jupiter.api.BeforeEach)30 User (de.tum.in.www1.artemis.domain.User)27 Collectors (java.util.stream.Collectors)26 ModelingSubmission (de.tum.in.www1.artemis.domain.modeling.ModelingSubmission)24 de.tum.in.www1.artemis.repository (de.tum.in.www1.artemis.repository)24