package edu.pdx.cs410J.grader; import edu.pdx.cs410J.grader.ProjectGradesImporter.ProjectScore; import org.junit.Test; import org.mockito.ArgumentCaptor; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import java.io.Reader; import java.io.StringReader; import java.util.regex.Matcher; import static org.hamcrest.MatcherAssert.assertThat; import static org.hamcrest.Matchers.containsString; import static org.hamcrest.Matchers.equalTo; import static org.mockito.Mockito.*; public class ProjectGradesImporterTest { private Logger logger = LoggerFactory.getLogger(this.getClass().getPackage().getName()); @Test(expected = ProjectGradesImporter.ScoreNotFoundException.class) public void gradedProjectWithNoGradeThrowsScoreNotFoundException() throws ProjectGradesImporter.ScoreNotFoundException { GradedProject project = new GradedProject(); project.addLine("asdfhjkl"); project.addLine("iadguow"); ProjectGradesImporter.getScoreFrom(project.getReader()); } @Test public void scoreRegularExpressionWorkWithSimpleCase() { Matcher matcher = ProjectGradesImporter.scorePattern.matcher("3.0 out of 4.5"); assertThat(matcher.find(), equalTo(true)); assertThat(matcher.groupCount(), equalTo(2)); assertThat(matcher.group(1), equalTo("3.0")); assertThat(matcher.group(2), equalTo("4.5")); } @Test public void gradedProjectWithOutOfHasValidScore() throws ProjectGradesImporter.ScoreNotFoundException { GradedProject project = new GradedProject(); project.addLine("3.4 out of 3.5"); project.addLine("iadguow"); ProjectScore score = ProjectGradesImporter.getScoreFrom(project.getReader()); assertThat(score.getScore(), equalTo(3.4)); assertThat(score.getTotalPoints(), equalTo(3.5)); } @Test public void scoreMatchesRegardlessOfCase() { Matcher matcher = ProjectGradesImporter.scorePattern.matcher("4.0 OUT OF 5.0"); assertThat(matcher.find(), equalTo(true)); assertThat(matcher.groupCount(), equalTo(2)); assertThat(matcher.group(1), equalTo("4.0")); assertThat(matcher.group(2), equalTo("5.0")); } @Test public void scoreMatchesIntegerPoints() { Matcher matcher = ProjectGradesImporter.scorePattern.matcher("4 out of 5"); assertThat(matcher.find(), equalTo(true)); assertThat(matcher.groupCount(), equalTo(2)); assertThat(matcher.group(1), equalTo("4")); assertThat(matcher.group(2), equalTo("5")); } @Test public void scoreMatchesInTheMiddleOfOtherText() { Matcher matcher = ProjectGradesImporter.scorePattern.matcher("You got 4 out of 5 points"); assertThat(matcher.find(), equalTo(true)); assertThat(matcher.groupCount(), equalTo(2)); assertThat(matcher.group(1), equalTo("4")); assertThat(matcher.group(2), equalTo("5")); } @Test public void gradedProjectWithIntegerPoints() throws ProjectGradesImporter.ScoreNotFoundException { GradedProject project = new GradedProject(); project.addLine("3 out of 5"); project.addLine("iadguow"); ProjectScore score = ProjectGradesImporter.getScoreFrom(project.getReader()); assertThat(score.getScore(), equalTo(3.0)); assertThat(score.getTotalPoints(), equalTo(5.0)); } private class GradedProject { private StringBuilder sb = new StringBuilder(); public void addLine(String line) { sb.append(line); sb.append("\n"); } public Reader getReader() { return new StringReader(sb.toString()); } } @Test public void onlyFirstScoreIsReturned() throws ProjectGradesImporter.ScoreNotFoundException { GradedProject project = new GradedProject(); project.addLine("3.4 out of 3.5"); project.addLine("iadguow"); project.addLine("3.3 out of 3.4"); ProjectScore score = ProjectGradesImporter.getScoreFrom(project.getReader()); assertThat(score.getScore(), equalTo(3.4)); assertThat(score.getTotalPoints(), equalTo(3.5)); } @Test public void scoreIsRecordedInGradeBook() throws ProjectGradesImporter.ScoreNotFoundException { String studentId = "student"; Assignment assignment = new Assignment("project", 6.0); GradeBook gradeBook = new GradeBook("test"); gradeBook.addStudent(new Student(studentId)); gradeBook.addAssignment(assignment); String score = "5.8"; GradedProject project = new GradedProject(); project.addLine(score + " out of 6.0"); project.addLine(""); project.addLine("asdfasd"); Logger logger = mock(Logger.class); ProjectGradesImporter importer = new ProjectGradesImporter(gradeBook, assignment, logger); importer.recordScoreFromProjectReport(studentId, project.getReader()); assertThat(gradeBook.getStudent(studentId).get().getGrade(assignment.getName()).getScore(), equalTo(5.8)); assertThat(gradeBook.isDirty(), equalTo(true)); ArgumentCaptor<String> message = ArgumentCaptor.forClass(String.class); verify(logger).info(message.capture()); assertThat(message.getValue(), containsString("Recorded grade of " + score + " for " + studentId)); } @Test(expected = IllegalStateException.class) public void throwIllegalStateExceptionWhenTotalPointsInReportDoesNotMatchGradeBook() throws ProjectGradesImporter.ScoreNotFoundException { String studentId = "student"; Assignment assignment = new Assignment("project", 8.0); GradeBook gradeBook = new GradeBook("test"); gradeBook.addStudent(new Student(studentId)); gradeBook.addAssignment(assignment); GradedProject project = new GradedProject(); project.addLine("5.8 out of 6.0"); project.addLine(""); project.addLine("asdfasd"); ProjectGradesImporter importer = new ProjectGradesImporter(gradeBook, assignment, logger); importer.recordScoreFromProjectReport(studentId, project.getReader()); } @Test public void logWarningWhenStudentDoesNotExistInGradeBook() throws ProjectGradesImporter.ScoreNotFoundException { String studentId = "student"; Assignment assignment = new Assignment("project", 6.0); GradeBook gradeBook = new GradeBook("test"); gradeBook.addAssignment(assignment); GradedProject project = new GradedProject(); project.addLine("5.8 out of 6.0"); project.addLine(""); project.addLine("asdfasd"); Logger logger = mock(Logger.class); ProjectGradesImporter importer = new ProjectGradesImporter(gradeBook, assignment, logger); importer.recordScoreFromProjectReport(studentId, project.getReader()); assertThat(gradeBook.containsStudent(studentId), equalTo(false)); ArgumentCaptor<String> message = ArgumentCaptor.forClass(String.class); verify(logger, times(1)).warn(message.capture()); assertThat(message.getValue(), containsString("Student \"" + studentId + "\" not found in gradebook")); } }