SPRING
[Spring Boot + JPA] LV.7
도원좀비
2025. 3. 28. 15:30
1️⃣ 요구사항 정리
Lv 7. 댓글 CRUD 도전
- 생성한 일정에 댓글을 남길 수 있습니다.
- 댓글과 일정은 연관관계를 가집니다.
- 댓글을 저장, 조회, 수정, 삭제할 수 있습니다.
- 댓글은 아래와 같은 필드를 가집니다.
- 댓글 내용, 작성일, 수정일, 유저 고유 식별자, 일정 고유 식별자 필드
- 작성일, 수정일 필드는 JPA Auditing을 활용하여 적용합니다.
2️⃣ API 명세
| Method | URL | 설명 |
| POST | /comments/schedules/{scheduleId} | 댓글 등록 |
| GET | /comments/schedules/{scheduleId} | 특정 일정의 댓글 전체 조회 |
| PATCH | /comments/schedules/{scheduleId}/{commentId} | 댓글 수정 |
| DELETE | /comments/schedules/{scheduleId}/{commentId} | 댓글 삭제 |
3️⃣ ERD

4️⃣ 주요 코드(댓글 수정)
더보기
(CommentController.java)
@RestController
@RequiredArgsConstructor
@RequestMapping("/comments")
public class CommentController {
private final CommentService commentService;
@PatchMapping("/schedules/{scheduleId}/{commentId}")
public ResponseEntity<UpdateCommentReponseDto> updateComment(
@PathVariable Long scheduleId,
@PathVariable Long commentId,
@Valid @RequestBody UpdateCommentRequestDto dto,
HttpServletRequest request
) {
Long authorId = (Long) request.getSession().getAttribute(SessionConst.LOGIN_AUTHOR);
UpdateCommentReponseDto updateCommentReponseDto = commentService.updateComment(dto, commentId, authorId, scheduleId);
return new ResponseEntity<>(updateCommentReponseDto, HttpStatus.OK);
}
}
(UpdateCommentRequestDto.java)
@Getter
@NoArgsConstructor
public class UpdateCommentRequestDto {
@NotBlank(message = "내용을 적어주세요")
@Size(max = 100, message = "내용은 100자 이하로 적어주세요")
private String content;
}
(CommentService.java)
@Override
@Transactional
public UpdateCommentReponseDto updateComment(UpdateCommentRequestDto dto, Long commentId, Long authorId, Long scheduleId) {
Comment comment = commentRepository.findByIdOrElseThrow(commentId);
comment.isAuthorId(authorId);
comment.isScheduleId(scheduleId);
comment.update(dto.getContent());
return new UpdateCommentReponseDto(comment.getAuthor().getName(), comment.getContent(), comment.getUpdatedDate());
}
}
(CommentRepository.java)
public interface CommentRepository extends JpaRepository<Comment, Long> {
default Comment findByIdOrElseThrow(Long commentId) {
return findById(commentId).orElseThrow(() -> new CustomException(ExceptionCode.COMMENT_NOT_FOUND));
}
List<Comment> findBySchedule_ScheduleId(Long scheduleId);
}
(Commnet.java)
@Getter
@Entity
@Table(name = "comment")
public class Comment extends BaseEntity {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private Long commentId;
@ManyToOne(fetch = FetchType.LAZY)
@JoinColumn(name = "schedule_id")
private Schedule schedule;
@ManyToOne(fetch = FetchType.LAZY)
@JoinColumn(name = "author_id")
private Author author;
@Column(nullable = false)
private String content;
public Comment() {
}
public void update(String content) {
this.content = content;
}
}
📌 GitHub 저장소: https://github.com/sukh115/schedulerJpa/lv7