-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Merge pull request #18 from jisung-in/feature/14-talkrooms-get-api
[Feature] TalkRoom 페이징 조회 API 구현
- Loading branch information
Showing
15 changed files
with
750 additions
and
16 deletions.
There are no files selected for viewing
This file contains 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 |
---|---|---|
|
@@ -3,10 +3,14 @@ | |
import com.jisungin.api.ApiResponse; | ||
import com.jisungin.api.talkroom.request.TalkRoomCreateRequest; | ||
import com.jisungin.api.talkroom.request.TalkRoomEditRequest; | ||
import com.jisungin.api.talkroom.request.TalkRoomSearchRequest; | ||
import com.jisungin.application.response.PageResponse; | ||
import com.jisungin.application.talkroom.TalkRoomService; | ||
import com.jisungin.application.talkroom.response.TalkRoomResponse; | ||
import jakarta.validation.Valid; | ||
import lombok.RequiredArgsConstructor; | ||
import org.springframework.web.bind.annotation.GetMapping; | ||
import org.springframework.web.bind.annotation.ModelAttribute; | ||
import org.springframework.web.bind.annotation.PatchMapping; | ||
import org.springframework.web.bind.annotation.PostMapping; | ||
import org.springframework.web.bind.annotation.RequestBody; | ||
|
@@ -26,6 +30,11 @@ public ApiResponse<TalkRoomResponse> createTalkRoom(@Valid @RequestBody TalkRoom | |
return ApiResponse.ok(talkRoomService.createTalkRoom(request.toServiceRequest(), "[email protected]")); | ||
} | ||
|
||
@GetMapping("/talk-rooms") | ||
public ApiResponse<PageResponse> getTalkRooms(@ModelAttribute TalkRoomSearchRequest search) { | ||
return ApiResponse.ok(talkRoomService.getTalkRooms(search.toService())); | ||
} | ||
|
||
@PatchMapping("/talk-rooms") | ||
public ApiResponse<TalkRoomResponse> editTalkRoom(@Valid @RequestBody TalkRoomEditRequest request) { | ||
return ApiResponse.ok(talkRoomService.editTalkRoom(request.toServiceRequest(), "[email protected]")); | ||
|
35 changes: 35 additions & 0 deletions
35
src/main/java/com/jisungin/api/talkroom/request/TalkRoomSearchRequest.java
This file contains 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,35 @@ | ||
package com.jisungin.api.talkroom.request; | ||
|
||
import com.jisungin.application.talkroom.request.TalkRoomSearchServiceRequest; | ||
import lombok.Builder; | ||
import lombok.Getter; | ||
import lombok.NoArgsConstructor; | ||
import lombok.Setter; | ||
|
||
@Getter | ||
@Setter | ||
@NoArgsConstructor | ||
public class TalkRoomSearchRequest { | ||
|
||
private Integer page = 1; | ||
|
||
private Integer size = 10; | ||
|
||
private String order; | ||
|
||
@Builder | ||
private TalkRoomSearchRequest(Integer page, Integer size, String order) { | ||
this.page = page != null ? page : 1; | ||
this.size = size != null ? size : 1; | ||
this.order = order != null ? order : "recent"; | ||
} | ||
|
||
public TalkRoomSearchServiceRequest toService() { | ||
return TalkRoomSearchServiceRequest.builder() | ||
.page(page) | ||
.size(size) | ||
.order(order) | ||
.build(); | ||
} | ||
|
||
} |
26 changes: 26 additions & 0 deletions
26
src/main/java/com/jisungin/application/response/PageResponse.java
This file contains 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,26 @@ | ||
package com.jisungin.application.response; | ||
|
||
import java.util.ArrayList; | ||
import java.util.List; | ||
import lombok.Builder; | ||
import lombok.Getter; | ||
import lombok.NoArgsConstructor; | ||
|
||
@Getter | ||
@NoArgsConstructor | ||
public class PageResponse<T> { | ||
|
||
private List<T> queryResponse = new ArrayList<>(); | ||
|
||
private long totalCount; | ||
|
||
private int size; | ||
|
||
@Builder | ||
private PageResponse(List<T> queryResponse, long totalCount, int size) { | ||
this.queryResponse = queryResponse; | ||
this.totalCount = totalCount; | ||
this.size = size; | ||
} | ||
|
||
} |
This file contains 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
33 changes: 33 additions & 0 deletions
33
src/main/java/com/jisungin/application/talkroom/request/TalkRoomSearchServiceRequest.java
This file contains 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,33 @@ | ||
package com.jisungin.application.talkroom.request; | ||
|
||
import static java.lang.Math.max; | ||
import static java.lang.Math.min; | ||
|
||
import lombok.Builder; | ||
import lombok.Getter; | ||
import lombok.NoArgsConstructor; | ||
|
||
@Getter | ||
@NoArgsConstructor | ||
public class TalkRoomSearchServiceRequest { | ||
|
||
private static final int MAX_SIZE = 2000; | ||
|
||
private Integer page; | ||
|
||
private Integer size; | ||
|
||
private String order; | ||
|
||
@Builder | ||
private TalkRoomSearchServiceRequest(Integer page, Integer size, String order) { | ||
this.page = page; | ||
this.size = size; | ||
this.order = order; | ||
} | ||
|
||
public long getOffset() { | ||
return (long) (max(1, page) - 1) * min(size, MAX_SIZE); | ||
} | ||
|
||
} |
24 changes: 24 additions & 0 deletions
24
src/main/java/com/jisungin/application/talkroom/response/TalkRoomQueryReadingStatus.java
This file contains 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,24 @@ | ||
package com.jisungin.application.talkroom.response; | ||
|
||
import com.jisungin.domain.ReadingStatus; | ||
import com.querydsl.core.annotations.QueryProjection; | ||
import lombok.Builder; | ||
import lombok.Getter; | ||
import lombok.NoArgsConstructor; | ||
|
||
@Getter | ||
@NoArgsConstructor | ||
public class TalkRoomQueryReadingStatus { | ||
|
||
private Long talkRoomId; | ||
|
||
private ReadingStatus readingStatus; | ||
|
||
@Builder | ||
@QueryProjection | ||
public TalkRoomQueryReadingStatus(Long talkRoomId, ReadingStatus readingStatus) { | ||
this.talkRoomId = talkRoomId; | ||
this.readingStatus = readingStatus; | ||
} | ||
|
||
} |
33 changes: 33 additions & 0 deletions
33
src/main/java/com/jisungin/application/talkroom/response/TalkRoomQueryResponse.java
This file contains 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,33 @@ | ||
package com.jisungin.application.talkroom.response; | ||
|
||
import com.querydsl.core.annotations.QueryProjection; | ||
import java.util.ArrayList; | ||
import java.util.List; | ||
import lombok.Builder; | ||
import lombok.Getter; | ||
import lombok.NoArgsConstructor; | ||
|
||
@Getter | ||
@NoArgsConstructor | ||
public class TalkRoomQueryResponse { | ||
|
||
private Long talkRoomId; | ||
private String userName; | ||
private String content; | ||
private String bookImage; | ||
private List<TalkRoomQueryReadingStatus> readingStatuses = new ArrayList<>(); | ||
|
||
@Builder | ||
@QueryProjection | ||
public TalkRoomQueryResponse(Long talkRoomId, String userName, String content, String bookImage) { | ||
this.talkRoomId = talkRoomId; | ||
this.userName = userName; | ||
this.content = content; | ||
this.bookImage = bookImage; | ||
} | ||
|
||
public void addTalkRoomStatus(List<TalkRoomQueryReadingStatus> readingStatuses) { | ||
this.readingStatuses = readingStatuses; | ||
} | ||
|
||
} |
This file contains 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 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,20 @@ | ||
package com.jisungin.config; | ||
|
||
import com.querydsl.jpa.impl.JPAQueryFactory; | ||
import jakarta.persistence.EntityManager; | ||
import jakarta.persistence.PersistenceContext; | ||
import org.springframework.context.annotation.Bean; | ||
import org.springframework.context.annotation.Configuration; | ||
|
||
@Configuration | ||
public class QueryDslConfig { | ||
|
||
@PersistenceContext | ||
public EntityManager em; | ||
|
||
@Bean | ||
public JPAQueryFactory jpaQueryFactory() { | ||
return new JPAQueryFactory(em); | ||
} | ||
|
||
} |
This file contains 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
10 changes: 10 additions & 0 deletions
10
src/main/java/com/jisungin/domain/talkroom/repository/TalkRoomRepositoryCustom.java
This file contains 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,10 @@ | ||
package com.jisungin.domain.talkroom.repository; | ||
|
||
import com.jisungin.application.response.PageResponse; | ||
import com.jisungin.application.talkroom.request.TalkRoomSearchServiceRequest; | ||
|
||
public interface TalkRoomRepositoryCustom { | ||
|
||
PageResponse getTalkRooms(TalkRoomSearchServiceRequest search); | ||
|
||
} |
100 changes: 100 additions & 0 deletions
100
src/main/java/com/jisungin/domain/talkroom/repository/TalkRoomRepositoryImpl.java
This file contains 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,100 @@ | ||
package com.jisungin.domain.talkroom.repository; | ||
|
||
import static com.jisungin.domain.book.QBook.book; | ||
import static com.jisungin.domain.talkroom.QTalkRoom.talkRoom; | ||
import static com.jisungin.domain.talkroom.QTalkRoomRole.talkRoomRole; | ||
import static com.jisungin.domain.user.QUser.user; | ||
|
||
import com.jisungin.application.response.PageResponse; | ||
import com.jisungin.application.talkroom.request.TalkRoomSearchServiceRequest; | ||
import com.jisungin.application.talkroom.response.QTalkRoomQueryReadingStatus; | ||
import com.jisungin.application.talkroom.response.QTalkRoomQueryResponse; | ||
import com.jisungin.application.talkroom.response.TalkRoomQueryReadingStatus; | ||
import com.jisungin.application.talkroom.response.TalkRoomQueryResponse; | ||
import com.querydsl.core.types.OrderSpecifier; | ||
import com.querydsl.jpa.impl.JPAQueryFactory; | ||
import java.util.List; | ||
import java.util.Map; | ||
import java.util.stream.Collectors; | ||
import lombok.RequiredArgsConstructor; | ||
|
||
@RequiredArgsConstructor | ||
public class TalkRoomRepositoryImpl implements TalkRoomRepositoryCustom { | ||
|
||
private final JPAQueryFactory queryFactory; | ||
|
||
@Override | ||
public PageResponse<TalkRoomQueryResponse> getTalkRooms(TalkRoomSearchServiceRequest search) { | ||
|
||
//루트 조회(toOne 코드를 모두 한번에 조회) | ||
List<TalkRoomQueryResponse> findTalkRoom = findTalkRoom(search); | ||
|
||
//TalkRoomRole 컬렉션을 MAP 한방에 조회 | ||
Map<Long, List<TalkRoomQueryReadingStatus>> talkRoomRoleMap = findTalkRoomRoleMap(toTalkRoomIds(findTalkRoom)); | ||
|
||
//루프를 돌면서 컬렉션 추가(추가 쿼리 실행X) | ||
findTalkRoom.forEach(t -> t.addTalkRoomStatus(talkRoomRoleMap.get(t.getTalkRoomId()))); | ||
|
||
long totalCount = getTotalTalkRoomCount(); | ||
|
||
return PageResponse.<TalkRoomQueryResponse>builder() | ||
.queryResponse(findTalkRoom) | ||
.totalCount(totalCount) | ||
.size(search.getSize()) | ||
.build(); | ||
} | ||
|
||
private List<Long> toTalkRoomIds(List<TalkRoomQueryResponse> findTalkRoom) { | ||
return findTalkRoom.stream() | ||
.map(t -> t.getTalkRoomId()) | ||
.collect(Collectors.toList()); | ||
} | ||
|
||
private Map<Long, List<TalkRoomQueryReadingStatus>> findTalkRoomRoleMap(List<Long> talkRoomIds) { | ||
List<TalkRoomQueryReadingStatus> talkRoomRoles = queryFactory.select(new QTalkRoomQueryReadingStatus( | ||
talkRoom.id, | ||
talkRoomRole.readingStatus | ||
)) | ||
.from(talkRoomRole) | ||
.join(talkRoomRole.talkRoom, talkRoom) | ||
.where(talkRoomRole.talkRoom.id.in(talkRoomIds)) | ||
.fetch(); | ||
|
||
return talkRoomRoles.stream() | ||
.collect(Collectors.groupingBy(TalkRoomQueryReadingStatus::getTalkRoomId)); | ||
} | ||
|
||
private long getTotalTalkRoomCount() { | ||
return queryFactory | ||
.select(talkRoom.count()) | ||
.from(talkRoom) | ||
.join(talkRoom.user, user) | ||
.join(talkRoom.book, book) | ||
.fetchOne(); | ||
} | ||
|
||
private List<TalkRoomQueryResponse> findTalkRoom(TalkRoomSearchServiceRequest search) { | ||
return queryFactory.select(new QTalkRoomQueryResponse( | ||
talkRoom.id.as("talkRoomId"), | ||
user.name.as("userName"), | ||
talkRoom.content, | ||
book.url.as("bookImage") | ||
)) | ||
.from(talkRoom) | ||
.join(talkRoom.user, user) | ||
.join(talkRoom.book, book) | ||
.offset(search.getOffset()) | ||
.limit(search.getSize()) | ||
.orderBy(condition(search.getOrder())) | ||
.fetch(); | ||
} | ||
|
||
/** | ||
* 아직 좋아요 기능이 구현 되지 않아 최신순으로만 정렬 | ||
*/ | ||
private OrderSpecifier<?> condition(String order) { | ||
// if (order.equals("recent")) | ||
return talkRoom.id.desc(); | ||
} | ||
|
||
} |
Oops, something went wrong.