-
Notifications
You must be signed in to change notification settings - Fork 1
Feature/79 리뷰 등록 #102
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Merged
+790
−73
Merged
Feature/79 리뷰 등록 #102
Changes from all commits
Commits
Show all changes
18 commits
Select commit
Hold shift + click to select a range
6d2cefb
feat(volunteer-apply): 기본 엔티티 레포지토리 추가
leebs0521 e6f0414
feat(volunteer-apply): 기본 엔티티 레포지토리 테스트
leebs0521 7654061
feat(volunteer-apply): 리뷰 생성에 필요한 조회 기능 추가
leebs0521 d8106ff
test(volunteer-apply): 리뷰 생성에 필요한 조회 기능 테스트
leebs0521 62ffd5c
feat(review): 리뷰 엔티티 레포지토리 생성
leebs0521 3ffa4b9
test(review): 리뷰 엔티티 레포지토리 테스트
leebs0521 282d5f2
feat(review): 리뷰 생성 기능 추가
leebs0521 e64afd8
test(review): 리뷰 생성 기능 테스트
leebs0521 5aa9c90
fix: conflict remove
leebs0521 9846ca4
refactor: 불필요한 import 제거
leebs0521 47ac38e
chore(review): import 추가
leebs0521 d89ae97
feat(review): 리뷰 등록 컨트롤러
leebs0521 53fd38e
test(review): 리뷰 등록 컨트롤러 테스트
leebs0521 db50577
feat(exception-handler): 400 에러 title 문구 변경
leebs0521 d2bfe3c
test(review): 리뷰 사항 반영
leebs0521 fbb7ac6
refactor(review): @AuthenticationPrincipal 을 사용하여 userId 가져오도록 변경
leebs0521 b73407e
hotfix(recruit-board): recruitBoard 수정 시 이미지 파일 optional 변경
leebs0521 b2996f3
refactor(review): 생성 RequestDto 예제 문구 수정
leebs0521 File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file was deleted.
Oops, something went wrong.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
52 changes: 52 additions & 0 deletions
52
src/main/java/com/somemore/review/controller/ReviewCommandApiController.java
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,52 @@ | ||
| package com.somemore.review.controller; | ||
|
|
||
| import static org.springframework.http.MediaType.MULTIPART_FORM_DATA_VALUE; | ||
|
|
||
| import com.somemore.global.common.response.ApiResponse; | ||
| import com.somemore.imageupload.dto.ImageUploadRequestDto; | ||
| import com.somemore.imageupload.usecase.ImageUploadUseCase; | ||
| import com.somemore.review.dto.request.ReviewCreateRequestDto; | ||
| import com.somemore.review.usecase.CreateReviewUseCase; | ||
| import io.swagger.v3.oas.annotations.Operation; | ||
| import io.swagger.v3.oas.annotations.tags.Tag; | ||
| import jakarta.validation.Valid; | ||
| import java.util.UUID; | ||
| import lombok.RequiredArgsConstructor; | ||
| import org.springframework.security.access.annotation.Secured; | ||
| import org.springframework.security.core.annotation.AuthenticationPrincipal; | ||
| import org.springframework.web.bind.annotation.PostMapping; | ||
| import org.springframework.web.bind.annotation.RequestMapping; | ||
| import org.springframework.web.bind.annotation.RequestPart; | ||
| import org.springframework.web.bind.annotation.RestController; | ||
| import org.springframework.web.multipart.MultipartFile; | ||
|
|
||
| @Tag(name = "Review Command API", description = "리뷰 생성 수정 삭제 API") | ||
| @RequiredArgsConstructor | ||
| @RequestMapping("/api") | ||
| @RestController | ||
| public class ReviewCommandApiController { | ||
|
|
||
| private final CreateReviewUseCase createReviewUseCase; | ||
| private final ImageUploadUseCase imageUploadUseCase; | ||
|
|
||
| @Secured("ROLE_VOLUNTEER") | ||
| @Operation(summary = "리뷰 등록", description = "리뷰를 등록합니다.") | ||
| @PostMapping(value = "/review", consumes = MULTIPART_FORM_DATA_VALUE) | ||
| public ApiResponse<Long> createReview( | ||
| @AuthenticationPrincipal String userId, | ||
| @Valid @RequestPart("data") ReviewCreateRequestDto requestDto, | ||
| @RequestPart(value = "img_file", required = false) MultipartFile image) { | ||
|
|
||
| String imgUrl = imageUploadUseCase.uploadImage(new ImageUploadRequestDto(image)); | ||
| return ApiResponse.ok( | ||
| 201, | ||
| createReviewUseCase.createReview(requestDto, getId(userId), imgUrl), | ||
| "리뷰 등록 성공" | ||
| ); | ||
| } | ||
|
|
||
| private static UUID getId(String id) { | ||
| return UUID.fromString(id); | ||
| } | ||
|
|
||
| } |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,53 @@ | ||
| package com.somemore.review.domain; | ||
|
|
||
| import static jakarta.persistence.GenerationType.IDENTITY; | ||
| import static lombok.AccessLevel.PROTECTED; | ||
|
|
||
| import com.somemore.global.common.BaseEntity; | ||
| import jakarta.persistence.Column; | ||
| import jakarta.persistence.Entity; | ||
| import jakarta.persistence.GeneratedValue; | ||
| import jakarta.persistence.Id; | ||
| import jakarta.persistence.Lob; | ||
| import jakarta.persistence.Table; | ||
| import java.util.UUID; | ||
| import lombok.Builder; | ||
| import lombok.Getter; | ||
| import lombok.NoArgsConstructor; | ||
|
|
||
| @Getter | ||
| @NoArgsConstructor(access = PROTECTED) | ||
| @Entity | ||
| @Table(name = "review") | ||
| public class Review extends BaseEntity { | ||
|
|
||
| @Id | ||
| @GeneratedValue(strategy = IDENTITY) | ||
| private Long id; | ||
|
|
||
| @Column(name = "volunteer_apply_id", nullable = false) | ||
| private Long volunteerApplyId; | ||
|
|
||
| @Column(name = "volunteer_id", nullable = false, length = 16) | ||
| private UUID volunteerId; | ||
|
|
||
| @Column(name = "title", nullable = false) | ||
| private String title; | ||
|
|
||
| @Lob | ||
| @Column(name = "content", nullable = false) | ||
| private String content; | ||
|
|
||
| @Column(name = "img_url", nullable = false) | ||
| private String imgUrl; | ||
|
|
||
| @Builder | ||
| public Review(Long volunteerApplyId, UUID volunteerId, String title, | ||
| String content, String imgUrl) { | ||
| this.volunteerApplyId = volunteerApplyId; | ||
| this.volunteerId = volunteerId; | ||
| this.title = title; | ||
| this.content = content; | ||
| this.imgUrl = imgUrl; | ||
| } | ||
| } |
36 changes: 36 additions & 0 deletions
36
src/main/java/com/somemore/review/dto/request/ReviewCreateRequestDto.java
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,36 @@ | ||
| package com.somemore.review.dto.request; | ||
|
|
||
| import com.fasterxml.jackson.databind.PropertyNamingStrategies; | ||
| import com.fasterxml.jackson.databind.annotation.JsonNaming; | ||
| import com.somemore.review.domain.Review; | ||
| import com.somemore.volunteerapply.domain.VolunteerApply; | ||
| import io.swagger.v3.oas.annotations.media.Schema; | ||
| import jakarta.validation.constraints.NotBlank; | ||
| import jakarta.validation.constraints.NotNull; | ||
| import java.util.UUID; | ||
| import lombok.Builder; | ||
|
|
||
| @JsonNaming(PropertyNamingStrategies.SnakeCaseStrategy.class) | ||
| @Builder | ||
| public record ReviewCreateRequestDto( | ||
| @Schema(description = "봉사 모집글 아이디", example = "1") | ||
| @NotNull(message = "봉사 모집글 아이디는 필수 값입니다.") | ||
| Long recruitBoardId, | ||
| @Schema(description = "리뷰 제목", example = "내 인생 최고의 봉사 활동") | ||
| @NotBlank(message = "리뷰 제목은 필수 값입니다.") | ||
| String title, | ||
| @Schema(description = "리뷰 내용", example = "담당자님도 정말 친절하였고 정말 보람찬 봉사였어요 <br>") | ||
| @NotBlank(message = "리뷰 내용은 필수 값입니다.") | ||
| String content | ||
| ) { | ||
|
|
||
| public Review toEntity(VolunteerApply apply, UUID volunteerId, String imgUrl) { | ||
| return Review.builder() | ||
| .volunteerApplyId(apply.getId()) | ||
| .volunteerId(volunteerId) | ||
| .title(title) | ||
| .content(content) | ||
| .imgUrl(imgUrl) | ||
| .build(); | ||
| } | ||
| } |
15 changes: 15 additions & 0 deletions
15
src/main/java/com/somemore/review/repository/ReviewJpaRepository.java
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,15 @@ | ||
| package com.somemore.review.repository; | ||
|
|
||
| import com.somemore.review.domain.Review; | ||
| import java.util.Optional; | ||
| import org.springframework.data.jpa.repository.JpaRepository; | ||
| import org.springframework.data.jpa.repository.Query; | ||
|
|
||
| public interface ReviewJpaRepository extends JpaRepository<Review, Long> { | ||
|
|
||
| Optional<Review> findByIdAndDeletedFalse(Long id); | ||
|
|
||
| @Query("SELECT COUNT(r) > 0 FROM Review r WHERE r.volunteerApplyId = :volunteerId AND r.deleted = false") | ||
| boolean existsByVolunteerApplyId(Long volunteerId); | ||
leebs0521 marked this conversation as resolved.
Show resolved
Hide resolved
|
||
|
|
||
| } | ||
13 changes: 13 additions & 0 deletions
13
src/main/java/com/somemore/review/repository/ReviewRepository.java
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,13 @@ | ||
| package com.somemore.review.repository; | ||
|
|
||
| import com.somemore.review.domain.Review; | ||
| import java.util.Optional; | ||
|
|
||
| public interface ReviewRepository { | ||
|
|
||
| Review save(Review review); | ||
|
|
||
| Optional<Review> findById(Long id); | ||
|
|
||
| boolean existsByVolunteerApplyId(Long volunteerApplyId); | ||
| } |
30 changes: 30 additions & 0 deletions
30
src/main/java/com/somemore/review/repository/ReviewRepositoryImpl.java
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,30 @@ | ||
| package com.somemore.review.repository; | ||
|
|
||
| import com.querydsl.jpa.impl.JPAQueryFactory; | ||
| import com.somemore.review.domain.Review; | ||
| import java.util.Optional; | ||
| import lombok.RequiredArgsConstructor; | ||
| import org.springframework.stereotype.Repository; | ||
|
|
||
| @RequiredArgsConstructor | ||
| @Repository | ||
| public class ReviewRepositoryImpl implements ReviewRepository { | ||
|
|
||
| private final ReviewJpaRepository reviewJpaRepository; | ||
| private final JPAQueryFactory queryFactory; | ||
|
|
||
| @Override | ||
| public Review save(Review review) { | ||
| return reviewJpaRepository.save(review); | ||
| } | ||
|
|
||
| @Override | ||
| public Optional<Review> findById(Long id) { | ||
| return reviewJpaRepository.findByIdAndDeletedFalse(id); | ||
| } | ||
|
|
||
| @Override | ||
| public boolean existsByVolunteerApplyId(Long volunteerApplyId) { | ||
| return reviewJpaRepository.existsByVolunteerApplyId(volunteerApplyId); | ||
| } | ||
| } |
52 changes: 52 additions & 0 deletions
52
src/main/java/com/somemore/review/service/CreateReviewService.java
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,52 @@ | ||
| package com.somemore.review.service; | ||
|
|
||
| import static com.somemore.global.exception.ExceptionMessage.REVIEW_ALREADY_EXISTS; | ||
| import static com.somemore.global.exception.ExceptionMessage.REVIEW_RESTRICTED_TO_ATTENDED; | ||
|
|
||
| import com.somemore.global.exception.BadRequestException; | ||
| import com.somemore.review.domain.Review; | ||
| import com.somemore.review.dto.request.ReviewCreateRequestDto; | ||
| import com.somemore.review.repository.ReviewRepository; | ||
| import com.somemore.review.usecase.CreateReviewUseCase; | ||
| import com.somemore.volunteerapply.domain.VolunteerApply; | ||
| import com.somemore.volunteerapply.usecase.VolunteerApplyQueryUseCase; | ||
| import java.util.UUID; | ||
| import lombok.RequiredArgsConstructor; | ||
| import org.springframework.stereotype.Service; | ||
| import org.springframework.transaction.annotation.Transactional; | ||
|
|
||
| @RequiredArgsConstructor | ||
| @Transactional | ||
| @Service | ||
| public class CreateReviewService implements CreateReviewUseCase { | ||
|
|
||
| private final ReviewRepository reviewRepository; | ||
| private final VolunteerApplyQueryUseCase volunteerApplyQueryUseCase; | ||
|
|
||
| @Override | ||
| public Long createReview(ReviewCreateRequestDto requestDto, UUID volunteerId, String imgUrl) { | ||
| VolunteerApply apply = getVolunteerApply(requestDto.recruitBoardId(), volunteerId); | ||
| validateReviewNotExist(apply); | ||
| validateActivityCompletion(apply); | ||
leebs0521 marked this conversation as resolved.
Show resolved
Hide resolved
|
||
|
|
||
| Review review = requestDto.toEntity(apply, volunteerId, imgUrl); | ||
| return reviewRepository.save(review).getId(); | ||
| } | ||
|
|
||
| private VolunteerApply getVolunteerApply(Long recruitBoardId, UUID volunteerId) { | ||
| return volunteerApplyQueryUseCase.getByRecruitIdAndVolunteerId(recruitBoardId, volunteerId); | ||
| } | ||
|
|
||
| private void validateReviewNotExist(VolunteerApply apply) { | ||
| if (reviewRepository.existsByVolunteerApplyId(apply.getId())) { | ||
| throw new BadRequestException(REVIEW_ALREADY_EXISTS.getMessage()); | ||
| } | ||
| } | ||
|
|
||
| private void validateActivityCompletion(VolunteerApply apply) { | ||
| if (apply.isVolunteerActivityCompleted()) { | ||
| return; | ||
| } | ||
| throw new BadRequestException(REVIEW_RESTRICTED_TO_ATTENDED.getMessage()); | ||
| } | ||
| } | ||
11 changes: 11 additions & 0 deletions
11
src/main/java/com/somemore/review/usecase/CreateReviewUseCase.java
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,11 @@ | ||
| package com.somemore.review.usecase; | ||
|
|
||
| import com.somemore.review.dto.request.ReviewCreateRequestDto; | ||
| import java.util.UUID; | ||
|
|
||
| public interface CreateReviewUseCase { | ||
|
|
||
| Long createReview(ReviewCreateRequestDto requestDto, UUID volunteerId, String imgUrl); | ||
|
|
||
|
|
||
| } |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Oops, something went wrong.
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
좋아요 ㅎㅎ
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
감사합니다