Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -63,6 +63,11 @@ public class AssignmentSubmission {
private Double grade;
private String feedback;

@Column(columnDefinition = "text")
private String aiSummary;

private Integer qualityScore;

private String comment;

private Long assignmentid;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -300,10 +300,12 @@ public ResponseEntity<?> updateSubmission(
submission.setComment(comment == null ? "" : comment);
submission.setIsLate(Boolean.TRUE.equals(isLate));

// Only clear grade/feedback when the submission content actually changed
// Only clear grade/feedback/AI summary/quality score when the content actually changed
if (contentChanged) {
submission.setGrade(null);
submission.setFeedback(null);
submission.setAiSummary(null);
submission.setQualityScore(null);
}

AssignmentSubmission savedSubmission = submissionRepo.save(submission);
Expand Down Expand Up @@ -350,6 +352,45 @@ public ResponseEntity<?> gradeSubmission(
return ResponseEntity.ok(new AssignmentSubmissionReturnDto(savedSubmission));
}

/**
* Persist an AI-generated summary for a submission (admin/teacher only).
*
* @param submissionId the ID of the submission being summarized
* @param summary the generated summary text
* @return a ResponseEntity indicating success or an error if the submission is not found
*/
@PostMapping("/summary/{submissionId}")
@Transactional
public ResponseEntity<?> saveSubmissionSummary(
@PathVariable Long submissionId,
@AuthenticationPrincipal UserDetails userDetails,
@RequestParam String summary,
@RequestParam(required = false) Integer qualityScore
) {
Person currentUser = getAuthenticatedPerson(userDetails);
if (currentUser == null) {
return ResponseEntity.status(HttpStatus.UNAUTHORIZED)
.body(Map.of("error", "Authentication required"));
}
if (!canGradeOrDeleteSubmission(currentUser)) {
return ResponseEntity.status(HttpStatus.FORBIDDEN)
.body(Map.of("error", "Admin or teacher access required"));
}

AssignmentSubmission submission = submissionRepo.findById(submissionId).orElse(null);
if (submission == null) {
return ResponseEntity.status(HttpStatus.NOT_FOUND)
.body(Map.of("error", "Submission not found"));
}

submission.setAiSummary(summary);
if (qualityScore != null && qualityScore >= 1 && qualityScore <= 5) {
submission.setQualityScore(qualityScore);
}
AssignmentSubmission savedSubmission = submissionRepo.save(submission);
return ResponseEntity.ok(new AssignmentSubmissionReturnDto(savedSubmission));
}

/**
* Delete an existing assignment submission.
*
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,8 @@ public class AssignmentSubmissionReturnDto {
public Double grade;
public String feedback;
public Boolean isLate;
public String aiSummary;
public Integer qualityScore;

public AssignmentSubmissionReturnDto(AssignmentSubmission submission) {
this.id = submission.getId();
Expand All @@ -32,5 +34,7 @@ public AssignmentSubmissionReturnDto(AssignmentSubmission submission) {
this.grade = submission.getGrade();
this.feedback = submission.getFeedback();
this.isLate = submission.getIsLate();
this.aiSummary = submission.getAiSummary();
this.qualityScore = submission.getQualityScore();
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -153,6 +153,8 @@ public static class SubmissionListDTO {
private String feedback;
private Boolean isLate;
private Boolean isGroup;
private String aiSummary;
private Integer qualityScore;

// Private constructor for factory use
private SubmissionListDTO() {}
Expand Down Expand Up @@ -211,14 +213,18 @@ public static SubmissionListDTO from(AssignmentSubmission submission) {
dto.grade = submission.getGrade();
dto.feedback = submission.getFeedback() != null ? submission.getFeedback() : "";
dto.isLate = submission.getIsLate() != null ? submission.getIsLate() : false;
dto.aiSummary = submission.getAiSummary();
dto.qualityScore = submission.getQualityScore();
} catch (Exception e) {
dto.content = null;
dto.comment = "";
dto.grade = null;
dto.feedback = "";
dto.isLate = false;
dto.aiSummary = null;
dto.qualityScore = null;
}

return dto;
}

Expand All @@ -239,6 +245,8 @@ public static SubmissionListDTO createFallback(AssignmentSubmission submission)
dto.grade = null;
dto.feedback = "";
dto.isLate = false;
dto.aiSummary = null;
dto.qualityScore = null;
} catch (Exception e) {
logger.error("Error in SubmissionListDTO.createFallback()", e);
}
Expand All @@ -257,6 +265,8 @@ public static SubmissionListDTO createFallback(AssignmentSubmission submission)
public String getFeedback() { return feedback; }
public Boolean getIsLate() { return isLate; }
public Boolean getIsGroup() { return isGroup; }
public String getAiSummary() { return aiSummary; }
public Integer getQualityScore() { return qualityScore; }
}

/**
Expand Down