Skip to content

Commit

Permalink
Feat: 게시글 리스트 조회 기능을 구현한다. (#62)
Browse files Browse the repository at this point in the history
* #61 - feat: 게시글 리스트 조회 api 구현

* #61 - test: 게시글 리스트 조회 api 테스트
  • Loading branch information
GGHDMS authored Feb 4, 2024
1 parent a70eba9 commit 8a5b1ad
Show file tree
Hide file tree
Showing 7 changed files with 96 additions and 7 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -8,18 +8,16 @@

public record BookListResponse(
int totalResults,
int totalPages,
int startIndex,
int itemsPerPage,
List<BookDto> bookList
) {

public static BookListResponse of(int totalResults, int startIndex, int itemsPerPage, List<BookDto> bookDtoList) {
return new BookListResponse(totalResults, startIndex, itemsPerPage, bookDtoList);
}

public static BookListResponse from(Page<Book> bookPage) {
return new BookListResponse(
(int) bookPage.getTotalElements(),
bookPage.getTotalPages(),
bookPage.getNumber(),
bookPage.getNumberOfElements(),
bookPage
Expand Down
Original file line number Diff line number Diff line change
@@ -1,12 +1,17 @@
package cotato.bookitlist.post.controller;

import cotato.bookitlist.book.controller.IsValidIsbn;
import cotato.bookitlist.config.security.jwt.AuthDetails;
import cotato.bookitlist.post.dto.requeset.PostRegisterRequest;
import cotato.bookitlist.post.dto.requeset.PostUpdateRequest;
import cotato.bookitlist.post.dto.response.PostListResponse;
import cotato.bookitlist.post.dto.response.PostResponse;
import cotato.bookitlist.post.service.PostService;
import jakarta.validation.Valid;
import lombok.RequiredArgsConstructor;
import org.springframework.data.domain.Pageable;
import org.springframework.data.domain.Sort;
import org.springframework.data.web.PageableDefault;
import org.springframework.http.ResponseEntity;
import org.springframework.security.core.annotation.AuthenticationPrincipal;
import org.springframework.web.bind.annotation.*;
Expand Down Expand Up @@ -55,4 +60,18 @@ public ResponseEntity<PostResponse> getPost(
return ResponseEntity.ok(PostResponse.from(postService.getPost(postId)));
}

@GetMapping("/all")
public ResponseEntity<PostListResponse> getAllPost(
@PageableDefault(sort = "createdAt", direction = Sort.Direction.DESC) Pageable pageable
) {
return ResponseEntity.ok(postService.getAllPost(pageable));
}

@GetMapping
public ResponseEntity<PostListResponse> searchPost(
@IsValidIsbn @RequestParam String isbn13,
@PageableDefault(sort = "createdAt", direction = Sort.Direction.DESC) Pageable pageable
) {
return ResponseEntity.ok(postService.searchPost(isbn13, pageable));
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
package cotato.bookitlist.post.dto.response;

import cotato.bookitlist.post.domain.Post;
import cotato.bookitlist.post.dto.PostDto;
import org.springframework.data.domain.Page;

import java.util.List;

public record PostListResponse(
int totalResults,
int totalPages,
int startIndex,
int itemsPerPage,
List<PostDto> postList
) {

public static PostListResponse from(Page<Post> page) {
return new PostListResponse(
(int) page.getTotalElements(),
page.getTotalPages(),
page.getNumber(),
page.getSize(),
page.stream().map(PostDto::from).toList()
);
}
}
Original file line number Diff line number Diff line change
@@ -1,7 +1,10 @@
package cotato.bookitlist.post.repository;

import cotato.bookitlist.post.domain.Post;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.Pageable;
import org.springframework.data.jpa.repository.JpaRepository;

public interface PostRepository extends JpaRepository<Post, Long> {
Page<Post> findByBook_Isbn13(String isbn13, Pageable pageable);
}
13 changes: 13 additions & 0 deletions src/main/java/cotato/bookitlist/post/service/PostService.java
Original file line number Diff line number Diff line change
Expand Up @@ -6,11 +6,13 @@
import cotato.bookitlist.member.repository.MemberRepository;
import cotato.bookitlist.post.domain.Post;
import cotato.bookitlist.post.dto.PostDto;
import cotato.bookitlist.post.dto.response.PostListResponse;
import cotato.bookitlist.post.dto.requeset.PostRegisterRequest;
import cotato.bookitlist.post.dto.requeset.PostUpdateRequest;
import cotato.bookitlist.post.repository.PostRepository;
import jakarta.persistence.EntityNotFoundException;
import lombok.RequiredArgsConstructor;
import org.springframework.data.domain.Pageable;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

Expand Down Expand Up @@ -43,8 +45,19 @@ public void updatePost(Long postId, PostUpdateRequest request, Long memberId) {
post.updatePost(member, request.title(), request.content());
}

@Transactional(readOnly = true)
public PostDto getPost(Long postId) {
return PostDto.from(postRepository.findById(postId)
.orElseThrow(() -> new EntityNotFoundException("게시글을 찾을 수 없습니다.")));
}

@Transactional(readOnly = true)
public PostListResponse getAllPost(Pageable pageable) {
return PostListResponse.from(postRepository.findAll(pageable));
}

@Transactional(readOnly = true)
public PostListResponse searchPost(String isbn13, Pageable pageable) {
return PostListResponse.from(postRepository.findByBook_Isbn13(isbn13, pageable));
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -20,8 +20,7 @@

import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.*;
import static org.springframework.test.web.servlet.result.MockMvcResultHandlers.print;
import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.header;
import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.status;
import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.*;


@Transactional
Expand Down Expand Up @@ -179,5 +178,32 @@ void givenNonExistedPostId_whenGettingPost_thenErrorResponse() throws Exception
.andExpect(status().isNotFound())
;
}

@Test
@DisplayName("isbn13을 이용해 게시글을 조회한다.")
void givenIsbn13_whenSearchingPost_thenReturnPostListResponse() throws Exception {
//given
String isbn13 = "9788931514810";

//when & then
mockMvc.perform(get("/posts")
.param("isbn13", isbn13)
.contentType(MediaType.APPLICATION_JSON))
.andExpect(status().isOk())
.andExpect(jsonPath("$.totalResults").value(4))
;
}

@Test
@DisplayName("전체 게시글을 조회한다.")
void givenNothing_whenSearchingPost_thenReturnPostListResponse() throws Exception {
//given
//when & then
mockMvc.perform(get("/posts/all")
.contentType(MediaType.APPLICATION_JSON))
.andExpect(status().isOk())
.andExpect(jsonPath("$.totalResults").value(6))
;
}
}

6 changes: 5 additions & 1 deletion src/test/resources/data.sql
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,11 @@ VALUES ('[email protected]', 'test', 'test', 'KAKAO', 0, false, CURRENT_TIMESTAMP,

INSERT INTO post (member_id, book_id, title, content, like_count, view_count, deleted)
VALUES (1, 1, 'postTitle', 'postContent', 0, 0, false),
(2, 1, 'postTitle', 'postContent', 0, 0, false);
(2, 1, 'postTitle1', 'Content', 0, 0, false),
(2, 1, 'postTitle2', '제목', 0, 0, false),
(2, 1, 'postTitle3', 'post', 0, 0, false),
(2, 2, 'posTitle', 'ptent', 0, 0, false),
(2, 2, 'positle', 'postent', 0, 0, false);

INSERT INTO review (member_id, book_id, content, like_count, view_count, deleted)
VALUES (1, 1, 'reviewContent', 0, 0, false),
Expand Down

0 comments on commit 8a5b1ad

Please sign in to comment.