From 6b3cfe8dfcef04d50672d2aea5e533dbf8771e30 Mon Sep 17 00:00:00 2001 From: Jihwan Jung Date: Fri, 26 Apr 2024 00:19:44 +0900 Subject: [PATCH 1/3] =?UTF-8?q?#32=20feat:=20member=20=EC=A1=B0=ED=9A=8C?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../auth/controller/dto/SignupRequest.java | 4 +- .../club/controller/dto/ClubResponse.java | 15 +++- .../project/capstone/club/domain/Club.java | 12 ++- .../capstone/club/service/ClubService.java | 14 +--- .../controller/dto/CommentResponse.java | 4 +- .../controller/dto/ContentResponse.java | 4 +- .../member/controller/MemberController.java | 15 +++- .../member/controller/dto/MemberResponse.java | 74 +++++++++++++++++++ .../capstone/member/domain/Gender.java | 25 +++++++ .../capstone/member/domain/Member.java | 5 +- .../member/service/MemberService.java | 27 +++++++ .../memberclub/domain/MemberClub.java | 5 ++ .../domain/MemberClubRepository.java | 2 + .../post/controller/dto/PostResponse.java | 19 ++++- .../controller/dto/SimplePostResponse.java | 16 ++++ .../project/capstone/post/domain/Post.java | 3 + .../quiz/controller/dto/QuizResponse.java | 4 +- .../project/capstone/quiz/domain/Quiz.java | 4 + backend/src/main/resources/data.sql | 12 +-- 19 files changed, 228 insertions(+), 36 deletions(-) create mode 100644 backend/src/main/java/com/project/capstone/member/controller/dto/MemberResponse.java create mode 100644 backend/src/main/java/com/project/capstone/member/domain/Gender.java create mode 100644 backend/src/main/java/com/project/capstone/member/service/MemberService.java create mode 100644 backend/src/main/java/com/project/capstone/post/controller/dto/SimplePostResponse.java diff --git a/backend/src/main/java/com/project/capstone/auth/controller/dto/SignupRequest.java b/backend/src/main/java/com/project/capstone/auth/controller/dto/SignupRequest.java index ce7cd39be6..8dd07a1383 100644 --- a/backend/src/main/java/com/project/capstone/auth/controller/dto/SignupRequest.java +++ b/backend/src/main/java/com/project/capstone/auth/controller/dto/SignupRequest.java @@ -1,9 +1,11 @@ package com.project.capstone.auth.controller.dto; +import com.project.capstone.member.domain.Gender; + public record SignupRequest( String email, String name, int age, - String gender + Gender gender ) { } diff --git a/backend/src/main/java/com/project/capstone/club/controller/dto/ClubResponse.java b/backend/src/main/java/com/project/capstone/club/controller/dto/ClubResponse.java index 204b647f92..32ba370d47 100644 --- a/backend/src/main/java/com/project/capstone/club/controller/dto/ClubResponse.java +++ b/backend/src/main/java/com/project/capstone/club/controller/dto/ClubResponse.java @@ -3,9 +3,11 @@ import com.fasterxml.jackson.annotation.JsonIgnore; import com.project.capstone.club.domain.Club; import com.project.capstone.club.domain.PublicStatus; +import com.project.capstone.post.controller.dto.PostResponse; import com.project.capstone.post.domain.Post; import java.time.LocalDateTime; +import java.util.ArrayList; import java.util.List; public record ClubResponse ( @@ -16,10 +18,19 @@ public record ClubResponse ( LocalDateTime createdAt, int maximum, PublicStatus publicstatus, - List posts + List posts ) { public ClubResponse(Club club) { - this(club.getId(), club.getBook() == null ? null : club.getBook().getId(), club.getTopic(), club.getName(), club.getCreatedAt(), club.getMaximum(), club.getPublicStatus(), club.getPosts()); + this(club.getId(), club.getBook() == null ? null : club.getBook().getId(), club.getTopic(), club.getName(), club.getCreatedAt(), club.getMaximum(), + club.getPublicStatus(), createPostResponseList(club.getPosts())); + } + + private static List createPostResponseList(List postList) { + List postResponseList = new ArrayList<>(); + for (Post post : postList) { + postResponseList.add(new PostResponse(post)); + } + return postResponseList; } } \ No newline at end of file diff --git a/backend/src/main/java/com/project/capstone/club/domain/Club.java b/backend/src/main/java/com/project/capstone/club/domain/Club.java index deb76b3cd4..49ec27da46 100644 --- a/backend/src/main/java/com/project/capstone/club/domain/Club.java +++ b/backend/src/main/java/com/project/capstone/club/domain/Club.java @@ -3,15 +3,13 @@ import com.fasterxml.jackson.annotation.JsonIgnore; import com.fasterxml.jackson.annotation.JsonManagedReference; import com.project.capstone.book.domain.Book; +import com.project.capstone.club.controller.dto.ClubCreateRequest; import com.project.capstone.memberclub.domain.MemberClub; import com.project.capstone.content.domain.Content; import com.project.capstone.post.domain.Post; import com.project.capstone.quiz.domain.Quiz; import jakarta.persistence.*; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Getter; -import lombok.NoArgsConstructor; +import lombok.*; import org.springframework.data.annotation.CreatedDate; import org.springframework.data.jpa.domain.support.AuditingEntityListener; @@ -26,6 +24,7 @@ @AllArgsConstructor @Getter @Builder +@ToString public class Club { @Id @GeneratedValue(strategy = GenerationType.IDENTITY) @@ -62,4 +61,9 @@ public class Club { @ManyToOne private Book book; + public Club(ClubCreateRequest request, UUID memberId) { + this(null, memberId, request.topic(), request.name(), null, request.maximum(), request.publicStatus(), request.password(), + new ArrayList<>(), new ArrayList<>(), new ArrayList<>(), new ArrayList<>(), null); + } + } diff --git a/backend/src/main/java/com/project/capstone/club/service/ClubService.java b/backend/src/main/java/com/project/capstone/club/service/ClubService.java index 23b82d3b96..32b3881b18 100644 --- a/backend/src/main/java/com/project/capstone/club/service/ClubService.java +++ b/backend/src/main/java/com/project/capstone/club/service/ClubService.java @@ -53,15 +53,7 @@ public List searchByName(String name) { @Transactional public void createClub(ClubCreateRequest request, String memberId) { - Club savedClub = clubRepository.save(Club.builder() - .managerId(UUID.fromString(memberId)) - .topic(request.topic()) - .name(request.name()) - .maximum(request.maximum()) - .publicStatus(request.publicStatus()) - .password(request.password()) - .build()); - + Club savedClub = clubRepository.save(new Club(request, UUID.fromString(memberId))); join(memberId, savedClub.getId()); } @@ -75,7 +67,9 @@ public void join(String memberId, Long clubId) { if (memberClubRepository.findMemberClubByMember_IdAndClub_Id(UUID.fromString(memberId), clubId).isPresent()) { throw new MemberClubException(ALREADY_JOIN); } - memberClubRepository.save(new MemberClub(null, member, club)); + MemberClub saved = memberClubRepository.save(new MemberClub(null, member, club)); + member.getClubs().add(saved); + club.getMembers().add(saved); } @Transactional diff --git a/backend/src/main/java/com/project/capstone/comment/controller/dto/CommentResponse.java b/backend/src/main/java/com/project/capstone/comment/controller/dto/CommentResponse.java index fb8d6d3e19..049891e5ab 100644 --- a/backend/src/main/java/com/project/capstone/comment/controller/dto/CommentResponse.java +++ b/backend/src/main/java/com/project/capstone/comment/controller/dto/CommentResponse.java @@ -8,11 +8,11 @@ public record CommentResponse( Long id, Long postId, - UUID memberId, + String writer, String body, LocalDateTime createdAt ) { public CommentResponse(Comment comment) { - this(comment.getId(), comment.getPost().getId(), comment.getMember().getId(), comment.getBody(), comment.getCreatedAt()); + this(comment.getId(), comment.getPost().getId(), comment.getMember().getName(), comment.getBody(), comment.getCreatedAt()); } } diff --git a/backend/src/main/java/com/project/capstone/content/controller/dto/ContentResponse.java b/backend/src/main/java/com/project/capstone/content/controller/dto/ContentResponse.java index 13352f609e..047c11f1aa 100644 --- a/backend/src/main/java/com/project/capstone/content/controller/dto/ContentResponse.java +++ b/backend/src/main/java/com/project/capstone/content/controller/dto/ContentResponse.java @@ -7,7 +7,7 @@ public record ContentResponse( Long id, - UUID memberId, + String writer, Long bookId, Long clubId, ContentType type, @@ -16,7 +16,7 @@ public record ContentResponse( int likes ) { public ContentResponse(Content content) { - this(content.getId(), content.getMember().getId(), content.getBook().getId(), + this(content.getId(), content.getMember().getName(), content.getBook().getId(), content.getClub() == null ? null : content.getClub().getId(), content.getType(), content.getTitle(), content.getBody(), content.getLikes()); } } diff --git a/backend/src/main/java/com/project/capstone/member/controller/MemberController.java b/backend/src/main/java/com/project/capstone/member/controller/MemberController.java index 3f809acad5..289b56a18e 100644 --- a/backend/src/main/java/com/project/capstone/member/controller/MemberController.java +++ b/backend/src/main/java/com/project/capstone/member/controller/MemberController.java @@ -1,17 +1,26 @@ package com.project.capstone.member.controller; +import com.project.capstone.member.controller.dto.MemberResponse; +import com.project.capstone.member.service.MemberService; import lombok.RequiredArgsConstructor; import org.springframework.http.ResponseEntity; import org.springframework.web.bind.annotation.GetMapping; +import org.springframework.web.bind.annotation.PathVariable; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.RestController; +import java.util.UUID; + @RestController @RequiredArgsConstructor @RequestMapping("/member") public class MemberController { - @GetMapping("/test") - public ResponseEntity test() { - return ResponseEntity.ok("ok"); + + private final MemberService memberService; + + @GetMapping("/{id}") + public ResponseEntity getMember(@PathVariable UUID id) { + MemberResponse memberResponse = memberService.getMember(id); + return ResponseEntity.ok().body(memberResponse); } } diff --git a/backend/src/main/java/com/project/capstone/member/controller/dto/MemberResponse.java b/backend/src/main/java/com/project/capstone/member/controller/dto/MemberResponse.java new file mode 100644 index 0000000000..6c490bbf2f --- /dev/null +++ b/backend/src/main/java/com/project/capstone/member/controller/dto/MemberResponse.java @@ -0,0 +1,74 @@ +package com.project.capstone.member.controller.dto; + +import com.project.capstone.club.domain.Club; +import com.project.capstone.comment.controller.dto.CommentResponse; +import com.project.capstone.comment.domain.Comment; +import com.project.capstone.content.controller.dto.ContentResponse; +import com.project.capstone.content.domain.Content; +import com.project.capstone.member.domain.Gender; +import com.project.capstone.member.domain.Member; +import com.project.capstone.memberclub.domain.MemberClub; +import com.project.capstone.post.controller.dto.PostResponse; +import com.project.capstone.post.controller.dto.SimplePostResponse; +import com.project.capstone.post.domain.Post; +import com.project.capstone.quiz.controller.dto.QuizResponse; +import com.project.capstone.quiz.domain.Quiz; + +import java.time.LocalDateTime; +import java.util.ArrayList; +import java.util.List; +import java.util.UUID; + +public record MemberResponse ( + UUID id, + String email, + String name, + int age, + Gender gender, + LocalDateTime createdAt, + List clubsList, + List postList, + List commentList, + List contentList, + List quizList +) { + public MemberResponse(Member member) { + this(member.getId(), member.getEmail(), member.getName(), member.getAge(), member.getGender(), member.getCreatedAt(), + member.getClubs(), createSimplePostResponseList(member.getPosts()), createCommentResponseList(member.getComments()), + createContentResponseList(member.getContents()), createQuizResponseList(member.getQuizzes())); + } + + private static List createSimplePostResponseList(List postList) { + List simplePostResponses = new ArrayList<>(); + for (Post post: postList) { + simplePostResponses.add(new SimplePostResponse(post)); + } + return simplePostResponses; + } + + private static List createCommentResponseList(List commentList) { + List commentResponseList = new ArrayList<>(); + for (Comment comment: commentList) { + commentResponseList.add(new CommentResponse(comment)); + } + return commentResponseList; + } + + private static List createContentResponseList(List contentList) { + List contentResponseList = new ArrayList<>(); + for (Content content : contentList) { + contentResponseList.add(new ContentResponse(content)); + } + return contentResponseList; + } + private static List createQuizResponseList(List quizList) { + List quizResponseList = new ArrayList<>(); + for (Quiz quiz : quizList) { + quizResponseList.add(new QuizResponse(quiz)); + } + return quizResponseList; + } + + + +} diff --git a/backend/src/main/java/com/project/capstone/member/domain/Gender.java b/backend/src/main/java/com/project/capstone/member/domain/Gender.java new file mode 100644 index 0000000000..44e8385925 --- /dev/null +++ b/backend/src/main/java/com/project/capstone/member/domain/Gender.java @@ -0,0 +1,25 @@ +package com.project.capstone.member.domain; + +import com.fasterxml.jackson.annotation.JsonCreator; +import com.project.capstone.quiz.domain.QuizType; +import lombok.AllArgsConstructor; +import lombok.Getter; + +@AllArgsConstructor +@Getter +public enum Gender { + MALE("남자"), + FEMALE("여자") + ; + private final String type; + + @JsonCreator(mode = JsonCreator.Mode.DELEGATING) + public static Gender from(String type) { + for (Gender gender: Gender.values()) { + if (gender.getType().equals(type)) { + return gender; + } + } + throw new RuntimeException("잘못된 성별 입니다."); + } +} diff --git a/backend/src/main/java/com/project/capstone/member/domain/Member.java b/backend/src/main/java/com/project/capstone/member/domain/Member.java index 5f926c1ed1..5e28cef5c2 100644 --- a/backend/src/main/java/com/project/capstone/member/domain/Member.java +++ b/backend/src/main/java/com/project/capstone/member/domain/Member.java @@ -2,6 +2,7 @@ import com.fasterxml.jackson.annotation.JsonManagedReference; import com.project.capstone.auth.controller.dto.SignupRequest; +import com.project.capstone.club.domain.Club; import com.project.capstone.comment.domain.Comment; import com.project.capstone.memberclub.domain.MemberClub; import com.project.capstone.content.domain.Content; @@ -35,7 +36,8 @@ public class Member { private String email; private String name; private int age; - private String gender; + @Enumerated(EnumType.STRING) + private Gender gender; @CreatedDate @Column(name = "created_at") private LocalDateTime createdAt; @@ -64,4 +66,5 @@ public Member(SignupRequest request) { this(null, request.email(), request.name(), request.age(), request.gender(), null, new ArrayList<>(), new ArrayList<>(), new ArrayList<>(), new ArrayList<>(), new ArrayList<>()); } + } diff --git a/backend/src/main/java/com/project/capstone/member/service/MemberService.java b/backend/src/main/java/com/project/capstone/member/service/MemberService.java new file mode 100644 index 0000000000..7f80d5df6c --- /dev/null +++ b/backend/src/main/java/com/project/capstone/member/service/MemberService.java @@ -0,0 +1,27 @@ +package com.project.capstone.member.service; + +import com.project.capstone.member.controller.dto.MemberResponse; +import com.project.capstone.member.domain.Member; +import com.project.capstone.member.domain.MemberRepository; +import com.project.capstone.member.exception.MemberException; +import lombok.RequiredArgsConstructor; +import lombok.extern.slf4j.Slf4j; +import org.springframework.stereotype.Service; + +import java.util.UUID; + +import static com.project.capstone.member.exception.MemberExceptionType.MEMBER_NOT_FOUND; + +@Service +@RequiredArgsConstructor +@Slf4j +public class MemberService { + private final MemberRepository memberRepository; + + public MemberResponse getMember(UUID id) { + Member member = memberRepository.findMemberById(id).orElseThrow( + () -> new MemberException(MEMBER_NOT_FOUND) + ); + return new MemberResponse(member); + } +} diff --git a/backend/src/main/java/com/project/capstone/memberclub/domain/MemberClub.java b/backend/src/main/java/com/project/capstone/memberclub/domain/MemberClub.java index 9d2dd93f28..2e78b7dd3a 100644 --- a/backend/src/main/java/com/project/capstone/memberclub/domain/MemberClub.java +++ b/backend/src/main/java/com/project/capstone/memberclub/domain/MemberClub.java @@ -1,24 +1,29 @@ package com.project.capstone.memberclub.domain; +import com.fasterxml.jackson.annotation.JsonBackReference; import com.project.capstone.club.domain.Club; import com.project.capstone.member.domain.Member; import jakarta.persistence.*; import lombok.AllArgsConstructor; +import lombok.Getter; import lombok.NoArgsConstructor; @Entity @AllArgsConstructor @NoArgsConstructor +@Getter public class MemberClub { @Id @GeneratedValue(strategy = GenerationType.IDENTITY) private Long id; + @JsonBackReference @ManyToOne @JoinColumn(name = "member_id") private Member member; + @JsonBackReference @ManyToOne @JoinColumn(name = "club_id") private Club club; diff --git a/backend/src/main/java/com/project/capstone/memberclub/domain/MemberClubRepository.java b/backend/src/main/java/com/project/capstone/memberclub/domain/MemberClubRepository.java index 29e670e79b..57db974b48 100644 --- a/backend/src/main/java/com/project/capstone/memberclub/domain/MemberClubRepository.java +++ b/backend/src/main/java/com/project/capstone/memberclub/domain/MemberClubRepository.java @@ -2,6 +2,7 @@ import org.springframework.data.jpa.repository.JpaRepository; +import java.util.List; import java.util.Optional; import java.util.UUID; @@ -9,4 +10,5 @@ public interface MemberClubRepository extends JpaRepository { void deleteMemberClubByClub_IdAndMember_Id(Long clubId, UUID memberId); Optional findMemberClubByMember_IdAndClub_Id(UUID memberId, Long clubId); + List findMemberClubsByMember_Id(UUID memberId); } diff --git a/backend/src/main/java/com/project/capstone/post/controller/dto/PostResponse.java b/backend/src/main/java/com/project/capstone/post/controller/dto/PostResponse.java index cf0f388231..ee450ed220 100644 --- a/backend/src/main/java/com/project/capstone/post/controller/dto/PostResponse.java +++ b/backend/src/main/java/com/project/capstone/post/controller/dto/PostResponse.java @@ -1,22 +1,35 @@ package com.project.capstone.post.controller.dto; +import com.project.capstone.comment.controller.dto.CommentResponse; import com.project.capstone.comment.domain.Comment; import com.project.capstone.post.domain.Post; +import lombok.Builder; +import java.util.ArrayList; import java.util.List; import java.util.UUID; +@Builder public record PostResponse( Long id, - UUID memberId, + String writer, Long clubId, String title, String body, boolean isSticky, - List comments + List commentResponseList ) { public PostResponse(Post post) { - this(post.getId(), post.getMember().getId(), post.getClub().getId(), post.getTitle(), post.getBody(), post.isSticky(), post.getComments()); + this(post.getId(), post.getMember().getName(), post.getClub().getId(), post.getTitle(), post.getBody(), post.isSticky(), createCommentResponseList(post.getComments())); } + + private static List createCommentResponseList(List commentList) { + List commentResponseList = new ArrayList<>(); + for (Comment comment : commentList) { + commentResponseList.add(new CommentResponse(comment)); + } + return commentResponseList; + } + } diff --git a/backend/src/main/java/com/project/capstone/post/controller/dto/SimplePostResponse.java b/backend/src/main/java/com/project/capstone/post/controller/dto/SimplePostResponse.java new file mode 100644 index 0000000000..306839ec4f --- /dev/null +++ b/backend/src/main/java/com/project/capstone/post/controller/dto/SimplePostResponse.java @@ -0,0 +1,16 @@ +package com.project.capstone.post.controller.dto; + +import com.project.capstone.post.domain.Post; + +public record SimplePostResponse( + Long id, + String writer, + Long clubId, + String title, + String body, + boolean isSticky +) { + public SimplePostResponse(Post post) { + this(post.getId(), post.getMember().getName(), post.getClub().getId(), post.getTitle(), post.getBody(), post.isSticky()); + } +} diff --git a/backend/src/main/java/com/project/capstone/post/domain/Post.java b/backend/src/main/java/com/project/capstone/post/domain/Post.java index f8f21ad34e..fcc0728c27 100644 --- a/backend/src/main/java/com/project/capstone/post/domain/Post.java +++ b/backend/src/main/java/com/project/capstone/post/domain/Post.java @@ -27,6 +27,7 @@ public class Post { @Id @GeneratedValue(strategy = GenerationType.IDENTITY) private Long id; + private String writer; private String title; private String body; @CreatedDate @@ -46,4 +47,6 @@ public class Post { @JsonBackReference @ManyToOne private Club club; + + } diff --git a/backend/src/main/java/com/project/capstone/quiz/controller/dto/QuizResponse.java b/backend/src/main/java/com/project/capstone/quiz/controller/dto/QuizResponse.java index 13a7484279..908913e44d 100644 --- a/backend/src/main/java/com/project/capstone/quiz/controller/dto/QuizResponse.java +++ b/backend/src/main/java/com/project/capstone/quiz/controller/dto/QuizResponse.java @@ -7,7 +7,7 @@ public record QuizResponse ( Long id, - UUID memberId, + String writer, Long bookId, Long clubId, QuizType type, @@ -19,7 +19,7 @@ public record QuizResponse ( String example4 ) { public QuizResponse(Quiz quiz) { - this(quiz.getId(), quiz.getMember().getId(), quiz.getBook().getId(), quiz.getClub() == null ? null : quiz.getClub().getId(), quiz.getType(), + this(quiz.getId(), quiz.getMember().getName(), quiz.getBook().getId(), quiz.getClub() == null ? null : quiz.getClub().getId(), quiz.getType(), quiz.getDescription(), quiz.getAnswer(), quiz.getExample1(), quiz.getExample2(), quiz.getExample3(), quiz.getExample4()); } } diff --git a/backend/src/main/java/com/project/capstone/quiz/domain/Quiz.java b/backend/src/main/java/com/project/capstone/quiz/domain/Quiz.java index d3849b80e8..876b649eff 100644 --- a/backend/src/main/java/com/project/capstone/quiz/domain/Quiz.java +++ b/backend/src/main/java/com/project/capstone/quiz/domain/Quiz.java @@ -1,5 +1,6 @@ package com.project.capstone.quiz.domain; +import com.fasterxml.jackson.annotation.JsonBackReference; import com.project.capstone.book.domain.Book; import com.project.capstone.club.domain.Club; import com.project.capstone.member.domain.Member; @@ -31,12 +32,15 @@ public class Quiz { private String example3; private String example4; + @JsonBackReference @ManyToOne private Member member; + @JsonBackReference @ManyToOne private Book book; + @JsonBackReference @ManyToOne private Club club; diff --git a/backend/src/main/resources/data.sql b/backend/src/main/resources/data.sql index e0280d343d..d0984d6140 100644 --- a/backend/src/main/resources/data.sql +++ b/backend/src/main/resources/data.sql @@ -1,15 +1,15 @@ insert into member (id, email, name, age, gender, created_at) values -(UNHEX(REPLACE("3f06af63-a93c-11e4-9797-00505690773f", "-","")), 'example1@gmail.com', '홍길동1', 17, '남자', '2023-05-16 15:48:57.450179'); +(UNHEX(REPLACE("3f06af63-a93c-11e4-9797-00505690773f", "-","")), 'example1@gmail.com', '홍길동1', 17, 'MALE', '2023-05-16 15:48:57.450179'); insert into member (id, email, name, age, gender, created_at) values -(UNHEX(REPLACE("8fbcec61-e527-15ee-bd3d-0242ac120002", "-","")), 'example2@gmail.com', '홍길동2', 17, '남자', '2023-05-26 15:48:57.450179'); +(UNHEX(REPLACE("8fbcec61-e527-15ee-bd3d-0242ac120002", "-","")), 'example2@gmail.com', '홍길동2', 17, 'MALE', '2023-05-26 15:48:57.450179'); insert into member (id, email, name, age, gender, created_at) values -(UNHEX(REPLACE("8fbcec62-e527-14ee-bd3d-0242ac120002", "-","")), 'example3@gmail.com', '홍길동3', 17, '남자', '2023-05-26 15:48:57.450179'); +(UNHEX(REPLACE("8fbcec62-e527-14ee-bd3d-0242ac120002", "-","")), 'example3@gmail.com', '홍길동3', 17, 'MALE', '2023-05-26 15:48:57.450179'); insert into member (id, email, name, age, gender, created_at) values -(UNHEX(REPLACE("8fbcec63-e527-10ee-bd3d-0242ac120002", "-","")), 'example4@gmail.com', '홍길동4', 17, '남자', '2023-05-26 15:48:57.450179'); +(UNHEX(REPLACE("8fbcec63-e527-10ee-bd3d-0242ac120002", "-","")), 'example4@gmail.com', '홍길동4', 17, 'MALE', '2023-05-26 15:48:57.450179'); insert into member (id, email, name, age, gender, created_at) values -(UNHEX(REPLACE("8fbcec64-e527-11ee-bd3d-0242ac120002", "-","")), 'example5@gmail.com', '홍길동5', 17, '남자', '2023-05-26 15:48:57.450179'); +(UNHEX(REPLACE("8fbcec64-e527-11ee-bd3d-0242ac120002", "-","")), 'example5@gmail.com', '홍길동5', 17, 'MALE', '2023-05-26 15:48:57.450179'); insert into member (id, email, name, age, gender, created_at) values -(UNHEX(REPLACE("8fbcec65-e527-12ee-bd3d-0242ac120002", "-","")), 'example6@gmail.com', '홍길동6', 17, '남자', '2023-05-26 15:48:57.450179'); +(UNHEX(REPLACE("8fbcec65-e527-12ee-bd3d-0242ac120002", "-","")), 'example6@gmail.com', '홍길동6', 17, 'MALE', '2023-05-26 15:48:57.450179'); insert into book (id, title, category_1d, category_2d, category_3d, author, publisher, publish_date) values (1, '제목1', '카테고리1', '카테고리2', '카테고리3', '저자1', '출판사1', '2022-04-10'); From c6e3ea128f1275c8dad26d0d7ca68c2e0af0afee Mon Sep 17 00:00:00 2001 From: Jihwan Jung Date: Fri, 26 Apr 2024 17:43:47 +0900 Subject: [PATCH 2/3] =?UTF-8?q?#32=20feat:=20=EB=82=98=EB=A7=8C=EC=9D=98?= =?UTF-8?q?=20=EC=84=9C=EC=9E=AC=20=EC=A1=B0=ED=9A=8C?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../member/controller/MemberController.java | 22 +++++++++++--- .../controller/dto/AddMyBookRequest.java | 6 ++++ .../member/controller/dto/MyBookResponse.java | 14 +++++++++ .../capstone/member/domain/Member.java | 7 ++++- .../member/service/MemberService.java | 19 ++++++++++++ .../capstone/mybook/domain/MyBook.java | 29 +++++++++++++++++++ .../mybook/domain/MyBookRepository.java | 11 +++++++ 7 files changed, 103 insertions(+), 5 deletions(-) create mode 100644 backend/src/main/java/com/project/capstone/member/controller/dto/AddMyBookRequest.java create mode 100644 backend/src/main/java/com/project/capstone/member/controller/dto/MyBookResponse.java create mode 100644 backend/src/main/java/com/project/capstone/mybook/domain/MyBook.java create mode 100644 backend/src/main/java/com/project/capstone/mybook/domain/MyBookRepository.java diff --git a/backend/src/main/java/com/project/capstone/member/controller/MemberController.java b/backend/src/main/java/com/project/capstone/member/controller/MemberController.java index 289b56a18e..132ceddb51 100644 --- a/backend/src/main/java/com/project/capstone/member/controller/MemberController.java +++ b/backend/src/main/java/com/project/capstone/member/controller/MemberController.java @@ -1,14 +1,15 @@ package com.project.capstone.member.controller; +import com.project.capstone.auth.domain.PrincipalDetails; import com.project.capstone.member.controller.dto.MemberResponse; +import com.project.capstone.member.controller.dto.MyBookResponse; import com.project.capstone.member.service.MemberService; import lombok.RequiredArgsConstructor; import org.springframework.http.ResponseEntity; -import org.springframework.web.bind.annotation.GetMapping; -import org.springframework.web.bind.annotation.PathVariable; -import org.springframework.web.bind.annotation.RequestMapping; -import org.springframework.web.bind.annotation.RestController; +import org.springframework.security.core.annotation.AuthenticationPrincipal; +import org.springframework.web.bind.annotation.*; +import java.util.List; import java.util.UUID; @RestController @@ -23,4 +24,17 @@ public ResponseEntity getMember(@PathVariable UUID id) { MemberResponse memberResponse = memberService.getMember(id); return ResponseEntity.ok().body(memberResponse); } + + // 나만의 서재 조회 + @GetMapping("/my-book") + public ResponseEntity> getMyBook(@AuthenticationPrincipal PrincipalDetails details) { + List myBooks = memberService.getMyBooks(details.getUserId()); + return ResponseEntity.ok().body(myBooks); + } + + // 나만의 서재 추가 +// @PostMapping("/my-book/add") +// public ResponseEntity addMyBook() { +// +// } } diff --git a/backend/src/main/java/com/project/capstone/member/controller/dto/AddMyBookRequest.java b/backend/src/main/java/com/project/capstone/member/controller/dto/AddMyBookRequest.java new file mode 100644 index 0000000000..6e024cd39f --- /dev/null +++ b/backend/src/main/java/com/project/capstone/member/controller/dto/AddMyBookRequest.java @@ -0,0 +1,6 @@ +package com.project.capstone.member.controller.dto; + +public record AddMyBookRequest( + +) { +} diff --git a/backend/src/main/java/com/project/capstone/member/controller/dto/MyBookResponse.java b/backend/src/main/java/com/project/capstone/member/controller/dto/MyBookResponse.java new file mode 100644 index 0000000000..109180cf6d --- /dev/null +++ b/backend/src/main/java/com/project/capstone/member/controller/dto/MyBookResponse.java @@ -0,0 +1,14 @@ +package com.project.capstone.member.controller.dto; + +import com.project.capstone.mybook.domain.MyBook; + +public record MyBookResponse( + Long id, + String title, + String author, + String publisher +) { + public MyBookResponse(MyBook myBook) { + this(myBook.getId(), myBook.getBook().getTitle(), myBook.getBook().getAuthor(), myBook.getBook().getPublisher()); + } +} diff --git a/backend/src/main/java/com/project/capstone/member/domain/Member.java b/backend/src/main/java/com/project/capstone/member/domain/Member.java index 5e28cef5c2..bdd7e2b2a8 100644 --- a/backend/src/main/java/com/project/capstone/member/domain/Member.java +++ b/backend/src/main/java/com/project/capstone/member/domain/Member.java @@ -6,6 +6,7 @@ import com.project.capstone.comment.domain.Comment; import com.project.capstone.memberclub.domain.MemberClub; import com.project.capstone.content.domain.Content; +import com.project.capstone.mybook.domain.MyBook; import com.project.capstone.post.domain.Post; import com.project.capstone.quiz.domain.Quiz; import jakarta.persistence.*; @@ -62,9 +63,13 @@ public class Member { @OneToMany(mappedBy = "member") private List quizzes = new ArrayList<>(); + @JsonManagedReference + @OneToMany(mappedBy = "member") + private List myBooks = new ArrayList<>(); + public Member(SignupRequest request) { this(null, request.email(), request.name(), request.age(), request.gender(), null, - new ArrayList<>(), new ArrayList<>(), new ArrayList<>(), new ArrayList<>(), new ArrayList<>()); + new ArrayList<>(), new ArrayList<>(), new ArrayList<>(), new ArrayList<>(), new ArrayList<>(), new ArrayList<>()); } } diff --git a/backend/src/main/java/com/project/capstone/member/service/MemberService.java b/backend/src/main/java/com/project/capstone/member/service/MemberService.java index 7f80d5df6c..658e00a5cb 100644 --- a/backend/src/main/java/com/project/capstone/member/service/MemberService.java +++ b/backend/src/main/java/com/project/capstone/member/service/MemberService.java @@ -1,13 +1,18 @@ package com.project.capstone.member.service; import com.project.capstone.member.controller.dto.MemberResponse; +import com.project.capstone.member.controller.dto.MyBookResponse; import com.project.capstone.member.domain.Member; import com.project.capstone.member.domain.MemberRepository; import com.project.capstone.member.exception.MemberException; +import com.project.capstone.mybook.domain.MyBook; +import com.project.capstone.mybook.domain.MyBookRepository; import lombok.RequiredArgsConstructor; import lombok.extern.slf4j.Slf4j; import org.springframework.stereotype.Service; +import java.util.ArrayList; +import java.util.List; import java.util.UUID; import static com.project.capstone.member.exception.MemberExceptionType.MEMBER_NOT_FOUND; @@ -17,6 +22,8 @@ @Slf4j public class MemberService { private final MemberRepository memberRepository; + private final MyBookRepository myBookRepository; + public MemberResponse getMember(UUID id) { Member member = memberRepository.findMemberById(id).orElseThrow( @@ -24,4 +31,16 @@ public MemberResponse getMember(UUID id) { ); return new MemberResponse(member); } + + public List getMyBooks(String userId) { + Member member = memberRepository.findMemberById(UUID.fromString(userId)).orElseThrow( + () -> new MemberException(MEMBER_NOT_FOUND) + ); + List myBooksByMember = myBookRepository.findMyBooksByMember(member); + List books = new ArrayList<>(); + for (MyBook book : myBooksByMember) { + books.add(new MyBookResponse(book)); + } + return books; + } } diff --git a/backend/src/main/java/com/project/capstone/mybook/domain/MyBook.java b/backend/src/main/java/com/project/capstone/mybook/domain/MyBook.java new file mode 100644 index 0000000000..c0e7a75c66 --- /dev/null +++ b/backend/src/main/java/com/project/capstone/mybook/domain/MyBook.java @@ -0,0 +1,29 @@ +package com.project.capstone.mybook.domain; + +import com.fasterxml.jackson.annotation.JsonBackReference; +import com.project.capstone.book.domain.Book; +import com.project.capstone.member.domain.Member; +import jakarta.persistence.*; +import lombok.AllArgsConstructor; +import lombok.Getter; +import lombok.NoArgsConstructor; + +@Entity +@AllArgsConstructor +@NoArgsConstructor +@Getter +public class MyBook { + + @Id + @GeneratedValue(strategy = GenerationType.IDENTITY) + private Long id; + + @JsonBackReference + @ManyToOne + private Member member; + + @JsonBackReference + @ManyToOne + private Book book; + +} diff --git a/backend/src/main/java/com/project/capstone/mybook/domain/MyBookRepository.java b/backend/src/main/java/com/project/capstone/mybook/domain/MyBookRepository.java new file mode 100644 index 0000000000..74d405a32f --- /dev/null +++ b/backend/src/main/java/com/project/capstone/mybook/domain/MyBookRepository.java @@ -0,0 +1,11 @@ +package com.project.capstone.mybook.domain; + +import com.project.capstone.member.domain.Member; +import org.springframework.data.jpa.repository.JpaRepository; + +import java.util.List; +import java.util.UUID; + +public interface MyBookRepository extends JpaRepository { + List findMyBooksByMember(Member member); +} From 669feebdf40d83f72660dc5b0331f172314c8c42 Mon Sep 17 00:00:00 2001 From: ji hwan Date: Fri, 26 Apr 2024 19:58:38 +0900 Subject: [PATCH 3/3] =?UTF-8?q?#32=20feat:=20=EB=82=98=EB=A7=8C=EC=9D=98?= =?UTF-8?q?=20=EC=84=9C=EC=9E=AC=20=EC=B6=94=EA=B0=80?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../project/capstone/book/domain/Book.java | 19 ++++++++++- .../capstone/book/domain/BookRepository.java | 1 + .../member/controller/MemberController.java | 10 +++--- .../controller/dto/AddMyBookRequest.java | 11 ++++++- .../member/controller/dto/MemberResponse.java | 15 ++++++--- .../member/controller/dto/MyBookResponse.java | 3 +- .../member/service/MemberService.java | 28 +++++++++++++++- .../mybook/domain/MyBookRepository.java | 3 ++ .../mybook/exception/MyBookException.java | 10 ++++++ .../mybook/exception/MyBookExceptionType.java | 32 +++++++++++++++++++ 10 files changed, 120 insertions(+), 12 deletions(-) create mode 100644 backend/src/main/java/com/project/capstone/mybook/exception/MyBookException.java create mode 100644 backend/src/main/java/com/project/capstone/mybook/exception/MyBookExceptionType.java diff --git a/backend/src/main/java/com/project/capstone/book/domain/Book.java b/backend/src/main/java/com/project/capstone/book/domain/Book.java index 17e849b33a..ed1db8f5c2 100644 --- a/backend/src/main/java/com/project/capstone/book/domain/Book.java +++ b/backend/src/main/java/com/project/capstone/book/domain/Book.java @@ -1,7 +1,10 @@ package com.project.capstone.book.domain; +import com.fasterxml.jackson.annotation.JsonManagedReference; import com.project.capstone.club.domain.Club; import com.project.capstone.content.domain.Content; +import com.project.capstone.member.controller.dto.AddMyBookRequest; +import com.project.capstone.mybook.domain.MyBook; import com.project.capstone.quiz.domain.Quiz; import jakarta.persistence.*; import lombok.AllArgsConstructor; @@ -21,6 +24,7 @@ public class Book { @Id @GeneratedValue(strategy = GenerationType.IDENTITY) private Long id; + private String isbn; private String title; @Column(name = "category_1d") private String category1d; @@ -30,14 +34,27 @@ public class Book { private String category3d; private String author; private String publisher; - private String publish_date; + @Column(name = "publish_date") + private String publishDate; + @JsonManagedReference @OneToMany(mappedBy = "book") private List clubs = new ArrayList<>(); + @JsonManagedReference @OneToMany(mappedBy = "book") private List contents = new ArrayList<>(); + @JsonManagedReference @OneToMany(mappedBy = "book") private List quizzes = new ArrayList<>(); + + @JsonManagedReference + @OneToMany(mappedBy = "book") + private List membersAddThisBook = new ArrayList<>(); + + public Book(AddMyBookRequest request) { + this(null, request.isbn(), request.title(), request.category1d(), request.category2d(), request.category3d(), + request.author(), request.publisher(), request.publishDate(), new ArrayList<>(), new ArrayList<>(), new ArrayList<>(), new ArrayList<>()); + } } diff --git a/backend/src/main/java/com/project/capstone/book/domain/BookRepository.java b/backend/src/main/java/com/project/capstone/book/domain/BookRepository.java index 6da8fcbdde..311c458d53 100644 --- a/backend/src/main/java/com/project/capstone/book/domain/BookRepository.java +++ b/backend/src/main/java/com/project/capstone/book/domain/BookRepository.java @@ -6,4 +6,5 @@ public interface BookRepository extends JpaRepository { Optional findBookById(Long id); + Optional findBookByIsbn(String isbn); } diff --git a/backend/src/main/java/com/project/capstone/member/controller/MemberController.java b/backend/src/main/java/com/project/capstone/member/controller/MemberController.java index 132ceddb51..4098019e27 100644 --- a/backend/src/main/java/com/project/capstone/member/controller/MemberController.java +++ b/backend/src/main/java/com/project/capstone/member/controller/MemberController.java @@ -1,6 +1,7 @@ package com.project.capstone.member.controller; import com.project.capstone.auth.domain.PrincipalDetails; +import com.project.capstone.member.controller.dto.AddMyBookRequest; import com.project.capstone.member.controller.dto.MemberResponse; import com.project.capstone.member.controller.dto.MyBookResponse; import com.project.capstone.member.service.MemberService; @@ -33,8 +34,9 @@ public ResponseEntity> getMyBook(@AuthenticationPrincipal P } // 나만의 서재 추가 -// @PostMapping("/my-book/add") -// public ResponseEntity addMyBook() { -// -// } + @PostMapping("/my-book/add") + public ResponseEntity addMyBook(@AuthenticationPrincipal PrincipalDetails details, @RequestBody AddMyBookRequest request) { + memberService.addMyBook(details.getUserId(), request); + return ResponseEntity.ok().body("추가 완료"); + } } diff --git a/backend/src/main/java/com/project/capstone/member/controller/dto/AddMyBookRequest.java b/backend/src/main/java/com/project/capstone/member/controller/dto/AddMyBookRequest.java index 6e024cd39f..2856a55f4e 100644 --- a/backend/src/main/java/com/project/capstone/member/controller/dto/AddMyBookRequest.java +++ b/backend/src/main/java/com/project/capstone/member/controller/dto/AddMyBookRequest.java @@ -1,6 +1,15 @@ package com.project.capstone.member.controller.dto; -public record AddMyBookRequest( +import java.time.LocalDateTime; +public record AddMyBookRequest ( + String isbn, + String title, + String category1d, + String category2d, + String category3d, + String author, + String publisher, + String publishDate ) { } diff --git a/backend/src/main/java/com/project/capstone/member/controller/dto/MemberResponse.java b/backend/src/main/java/com/project/capstone/member/controller/dto/MemberResponse.java index 6c490bbf2f..d1126f78c9 100644 --- a/backend/src/main/java/com/project/capstone/member/controller/dto/MemberResponse.java +++ b/backend/src/main/java/com/project/capstone/member/controller/dto/MemberResponse.java @@ -8,6 +8,7 @@ import com.project.capstone.member.domain.Gender; import com.project.capstone.member.domain.Member; import com.project.capstone.memberclub.domain.MemberClub; +import com.project.capstone.mybook.domain.MyBook; import com.project.capstone.post.controller.dto.PostResponse; import com.project.capstone.post.controller.dto.SimplePostResponse; import com.project.capstone.post.domain.Post; @@ -30,12 +31,13 @@ public record MemberResponse ( List postList, List commentList, List contentList, - List quizList + List quizList, + List myBookList ) { public MemberResponse(Member member) { this(member.getId(), member.getEmail(), member.getName(), member.getAge(), member.getGender(), member.getCreatedAt(), member.getClubs(), createSimplePostResponseList(member.getPosts()), createCommentResponseList(member.getComments()), - createContentResponseList(member.getContents()), createQuizResponseList(member.getQuizzes())); + createContentResponseList(member.getContents()), createQuizResponseList(member.getQuizzes()), createMyBookResponseList(member.getMyBooks())); } private static List createSimplePostResponseList(List postList) { @@ -69,6 +71,11 @@ private static List createQuizResponseList(List quizList) { return quizResponseList; } - - + private static List createMyBookResponseList(List myBookList) { + List myBookResponseList = new ArrayList<>(); + for (MyBook myBook : myBookList) { + myBookResponseList.add(new MyBookResponse(myBook)); + } + return myBookResponseList; + } } diff --git a/backend/src/main/java/com/project/capstone/member/controller/dto/MyBookResponse.java b/backend/src/main/java/com/project/capstone/member/controller/dto/MyBookResponse.java index 109180cf6d..1a3844f144 100644 --- a/backend/src/main/java/com/project/capstone/member/controller/dto/MyBookResponse.java +++ b/backend/src/main/java/com/project/capstone/member/controller/dto/MyBookResponse.java @@ -4,11 +4,12 @@ public record MyBookResponse( Long id, + String isbn, String title, String author, String publisher ) { public MyBookResponse(MyBook myBook) { - this(myBook.getId(), myBook.getBook().getTitle(), myBook.getBook().getAuthor(), myBook.getBook().getPublisher()); + this(myBook.getId(), myBook.getBook().getIsbn(), myBook.getBook().getTitle(), myBook.getBook().getAuthor(), myBook.getBook().getPublisher()); } } diff --git a/backend/src/main/java/com/project/capstone/member/service/MemberService.java b/backend/src/main/java/com/project/capstone/member/service/MemberService.java index 658e00a5cb..8207638e45 100644 --- a/backend/src/main/java/com/project/capstone/member/service/MemberService.java +++ b/backend/src/main/java/com/project/capstone/member/service/MemberService.java @@ -1,5 +1,10 @@ package com.project.capstone.member.service; +import com.project.capstone.book.domain.Book; +import com.project.capstone.book.domain.BookRepository; +import com.project.capstone.book.exception.BookException; +import com.project.capstone.book.exception.BookExceptionType; +import com.project.capstone.member.controller.dto.AddMyBookRequest; import com.project.capstone.member.controller.dto.MemberResponse; import com.project.capstone.member.controller.dto.MyBookResponse; import com.project.capstone.member.domain.Member; @@ -7,15 +12,20 @@ import com.project.capstone.member.exception.MemberException; import com.project.capstone.mybook.domain.MyBook; import com.project.capstone.mybook.domain.MyBookRepository; +import com.project.capstone.mybook.exception.MyBookException; +import com.project.capstone.mybook.exception.MyBookExceptionType; import lombok.RequiredArgsConstructor; import lombok.extern.slf4j.Slf4j; import org.springframework.stereotype.Service; import java.util.ArrayList; import java.util.List; +import java.util.Optional; import java.util.UUID; +import static com.project.capstone.book.exception.BookExceptionType.BOOK_NOT_FOUND; import static com.project.capstone.member.exception.MemberExceptionType.MEMBER_NOT_FOUND; +import static com.project.capstone.mybook.exception.MyBookExceptionType.ALREADY_EXIST_MYBOOK; @Service @RequiredArgsConstructor @@ -23,7 +33,7 @@ public class MemberService { private final MemberRepository memberRepository; private final MyBookRepository myBookRepository; - + private final BookRepository bookRepository; public MemberResponse getMember(UUID id) { Member member = memberRepository.findMemberById(id).orElseThrow( @@ -43,4 +53,20 @@ public List getMyBooks(String userId) { } return books; } + + public void addMyBook(String userId, AddMyBookRequest request) { + Member member = memberRepository.findMemberById(UUID.fromString(userId)).orElseThrow( + () -> new MemberException(MEMBER_NOT_FOUND) + ); + Book book = bookRepository.findBookByIsbn(request.isbn()).orElseGet( + () -> bookRepository.save(new Book(request)) + ); + if (myBookRepository.findMyBookByMemberAndBook(member, book).isPresent()) { + throw new MyBookException(ALREADY_EXIST_MYBOOK); + } + + MyBook saved = myBookRepository.save(new MyBook(null, member, book)); + member.getMyBooks().add(saved); + book.getMembersAddThisBook().add(saved); + } } diff --git a/backend/src/main/java/com/project/capstone/mybook/domain/MyBookRepository.java b/backend/src/main/java/com/project/capstone/mybook/domain/MyBookRepository.java index 74d405a32f..f6958c20a7 100644 --- a/backend/src/main/java/com/project/capstone/mybook/domain/MyBookRepository.java +++ b/backend/src/main/java/com/project/capstone/mybook/domain/MyBookRepository.java @@ -1,11 +1,14 @@ package com.project.capstone.mybook.domain; +import com.project.capstone.book.domain.Book; import com.project.capstone.member.domain.Member; import org.springframework.data.jpa.repository.JpaRepository; import java.util.List; +import java.util.Optional; import java.util.UUID; public interface MyBookRepository extends JpaRepository { List findMyBooksByMember(Member member); + Optional findMyBookByMemberAndBook(Member member, Book book); } diff --git a/backend/src/main/java/com/project/capstone/mybook/exception/MyBookException.java b/backend/src/main/java/com/project/capstone/mybook/exception/MyBookException.java new file mode 100644 index 0000000000..59b1a11ff2 --- /dev/null +++ b/backend/src/main/java/com/project/capstone/mybook/exception/MyBookException.java @@ -0,0 +1,10 @@ +package com.project.capstone.mybook.exception; + +import com.project.capstone.common.exception.BaseException; +import com.project.capstone.common.exception.ExceptionType; + +public class MyBookException extends BaseException { + public MyBookException(ExceptionType exceptionType) { + super(exceptionType); + } +} diff --git a/backend/src/main/java/com/project/capstone/mybook/exception/MyBookExceptionType.java b/backend/src/main/java/com/project/capstone/mybook/exception/MyBookExceptionType.java new file mode 100644 index 0000000000..2ff5b8b136 --- /dev/null +++ b/backend/src/main/java/com/project/capstone/mybook/exception/MyBookExceptionType.java @@ -0,0 +1,32 @@ +package com.project.capstone.mybook.exception; + +import com.project.capstone.common.exception.ExceptionType; +import lombok.AllArgsConstructor; +import org.springframework.http.HttpStatus; + +import static org.springframework.http.HttpStatus.BAD_REQUEST; + +@AllArgsConstructor +public enum MyBookExceptionType implements ExceptionType { + ALREADY_EXIST_MYBOOK(BAD_REQUEST, 2001, "이미 나만의 서재에 등록된 책 입니다.") + ; + + private final HttpStatus status; + private final int exceptionCode; + private final String message; + + @Override + public HttpStatus httpStatus() { + return status; + } + + @Override + public int exceptionCode() { + return exceptionCode; + } + + @Override + public String message() { + return message; + } +}