Skip to content
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

Refactor/#397 experience #417

Open
wants to merge 4 commits into
base: develop
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -3,8 +3,7 @@
import static com.jeju.nanaland.global.exception.SuccessCode.EXPERIENCE_DETAIL_SUCCESS;
import static com.jeju.nanaland.global.exception.SuccessCode.EXPERIENCE_LIST_SUCCESS;

import com.jeju.nanaland.domain.experience.dto.ExperienceResponse.ExperienceDetailDto;
import com.jeju.nanaland.domain.experience.dto.ExperienceResponse.ExperienceThumbnailDto;
import com.jeju.nanaland.domain.experience.dto.ExperienceResponse;
import com.jeju.nanaland.domain.experience.entity.enums.ExperienceType;
import com.jeju.nanaland.domain.experience.entity.enums.ExperienceTypeKeyword;
import com.jeju.nanaland.domain.experience.service.ExperienceService;
Expand Down Expand Up @@ -41,18 +40,18 @@ public class ExperienceController {
@ApiResponse(responseCode = "500", description = "μ„œλ²„μΈ‘ μ—λŸ¬", content = @Content)
})
@GetMapping("/list")
public BaseResponse<ExperienceThumbnailDto> getExperienceList(
public BaseResponse<ExperienceResponse.PreviewPageDto> getExperienceList(
@AuthMember MemberInfoDto memberInfoDto,
@RequestParam ExperienceType experienceType,
@RequestParam(defaultValue = "") List<ExperienceTypeKeyword> keywordFilterList,
@RequestParam(defaultValue = "") List<String> addressFilterList,
@RequestParam(defaultValue = "0") int page,
@RequestParam(defaultValue = "12") int size) {

ExperienceThumbnailDto thumbnailDto = experienceService.getExperienceList(memberInfoDto,
experienceType, keywordFilterList, addressFilterList, page, size);
ExperienceResponse.PreviewPageDto previewPageDto = experienceService.getExperiencePreviews(
memberInfoDto, experienceType, keywordFilterList, addressFilterList, page, size);

return BaseResponse.success(EXPERIENCE_LIST_SUCCESS, thumbnailDto);
return BaseResponse.success(EXPERIENCE_LIST_SUCCESS, previewPageDto);
}

@Operation(summary = "μ΄μƒ‰μ²΄ν—˜ 상세 정보 쑰회", description = "μ΄μƒ‰μ²΄ν—˜ 상세 정보 쑰회")
Expand All @@ -64,13 +63,13 @@ public BaseResponse<ExperienceThumbnailDto> getExperienceList(
@ApiResponse(responseCode = "500", description = "μ„œλ²„μΈ‘ μ—λŸ¬", content = @Content)
})
@GetMapping("/{id}")
public BaseResponse<ExperienceDetailDto> getExperienceDetail(
public BaseResponse<ExperienceResponse.DetailDto> getExperienceDetail(
@AuthMember MemberInfoDto memberInfoDto,
@PathVariable Long id,
@RequestParam(defaultValue = "false") boolean isSearch) {

ExperienceDetailDto experienceDetail = experienceService.getExperienceDetail(memberInfoDto,
ExperienceResponse.DetailDto detailDto = experienceService.getExperienceDetail(memberInfoDto,
id, isSearch);
return BaseResponse.success(EXPERIENCE_DETAIL_SUCCESS, experienceDetail);
return BaseResponse.success(EXPERIENCE_DETAIL_SUCCESS, detailDto);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -14,22 +14,22 @@ public class ExperienceResponse {

@Data
@Builder
@Schema(description = "μ΄μƒ‰μ²΄ν—˜ κ²Œμ‹œλ¬Ό νŽ˜μ΄μ§• 정보")
public static class ExperienceThumbnailDto {
@Schema(name = "ExperienceThumbnailDto", description = "μ΄μƒ‰μ²΄ν—˜ κ²Œμ‹œλ¬Ό νŽ˜μ΄μ§• 정보")
public static class PreviewPageDto {

@Schema(description = "μ΄μƒ‰μ²΄ν—˜ 전체 κ²Œμ‹œλ¬Ό 수")
private Long totalElements;

@Schema(description = "μ΄μƒ‰μ²΄ν—˜ κ²Œμ‹œλ¬Ό κ²°κ³Ό 리슀트")
private List<ExperienceThumbnail> data;
private List<PreviewDto> data;
}

@Data
@Setter
@Builder
@AllArgsConstructor
@Schema(description = "μ΄μƒ‰μ²΄ν—˜ κ²Œμ‹œλ¬Ό 정보")
public static class ExperienceThumbnail {
@Schema(name = "ExperienceThumbnail", description = "μ΄μƒ‰μ²΄ν—˜ κ²Œμ‹œλ¬Ό 정보")
public static class PreviewDto {

@Schema(description = "μ΄μƒ‰μ²΄ν—˜ κ²Œμ‹œλ¬Ό id")
private Long id;
Expand All @@ -53,7 +53,7 @@ public static class ExperienceThumbnail {
private boolean isFavorite;

@QueryProjection
public ExperienceThumbnail(Long id, String originUrl, String thumbnailUrl, String title,
public PreviewDto(Long id, String originUrl, String thumbnailUrl, String title,
String addressTag) {
this.id = id;
this.firstImage = new ImageFileDto(originUrl, thumbnailUrl);
Expand All @@ -64,8 +64,8 @@ public ExperienceThumbnail(Long id, String originUrl, String thumbnailUrl, Strin

@Data
@Builder
@Schema(description = "μ΄μƒ‰μ²΄ν—˜ 상세 정보")
public static class ExperienceDetailDto {
@Schema(name = "ExperienceDetailDto", description = "μ΄μƒ‰μ²΄ν—˜ 상세 정보")
public static class DetailDto {

@Schema(description = "μ΄μƒ‰μ²΄ν—˜ κ²Œμ‹œλ¬Ό id")
private Long id;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
import com.jeju.nanaland.domain.common.data.Language;
import com.jeju.nanaland.domain.common.dto.PostPreviewDto;
import com.jeju.nanaland.domain.experience.dto.ExperienceCompositeDto;
import com.jeju.nanaland.domain.experience.dto.ExperienceResponse.ExperienceThumbnail;
import com.jeju.nanaland.domain.experience.dto.ExperienceResponse;
import com.jeju.nanaland.domain.experience.entity.enums.ExperienceType;
import com.jeju.nanaland.domain.experience.entity.enums.ExperienceTypeKeyword;
import com.jeju.nanaland.domain.review.dto.ReviewResponse.SearchPostForReviewDto;
Expand All @@ -14,13 +14,14 @@

public interface ExperienceRepositoryCustom {

ExperienceCompositeDto findCompositeDtoById(Long id, Language language);
ExperienceCompositeDto findExperienceCompositeDto(Long id, Language language);

Page<ExperienceCompositeDto> searchCompositeDtoByKeyword(String Keyword, Language language,
Pageable pageable);

Page<ExperienceThumbnail> findExperienceThumbnails(Language language,
ExperienceType experienceType, List<ExperienceTypeKeyword> keywordFilterList,
Page<ExperienceResponse.PreviewDto> findAllExperiencePreviewDtoOrderByPriorityDescAndCreatedAtDesc(
Language language, ExperienceType experienceType,
List<ExperienceTypeKeyword> keywordFilterList,
List<String> addressFilterList, Pageable pageable);

Set<ExperienceTypeKeyword> getExperienceTypeKeywordSet(Long postId);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -11,9 +11,9 @@
import com.jeju.nanaland.domain.common.dto.PostPreviewDto;
import com.jeju.nanaland.domain.common.dto.QPostPreviewDto;
import com.jeju.nanaland.domain.experience.dto.ExperienceCompositeDto;
import com.jeju.nanaland.domain.experience.dto.ExperienceResponse.ExperienceThumbnail;
import com.jeju.nanaland.domain.experience.dto.ExperienceResponse;
import com.jeju.nanaland.domain.experience.dto.QExperienceCompositeDto;
import com.jeju.nanaland.domain.experience.dto.QExperienceResponse_ExperienceThumbnail;
import com.jeju.nanaland.domain.experience.dto.QExperienceResponse_PreviewDto;
import com.jeju.nanaland.domain.experience.entity.enums.ExperienceType;
import com.jeju.nanaland.domain.experience.entity.enums.ExperienceTypeKeyword;
import com.jeju.nanaland.domain.review.dto.QReviewResponse_SearchPostForReviewDto;
Expand All @@ -39,7 +39,7 @@ public class ExperienceRepositoryImpl implements ExperienceRepositoryCustom {
private final JPAQueryFactory queryFactory;

@Override
public ExperienceCompositeDto findCompositeDtoById(Long id, Language language) {
public ExperienceCompositeDto findExperienceCompositeDto(Long id, Language language) {
return queryFactory
.select(new QExperienceCompositeDto(
experience.id,
Expand All @@ -61,7 +61,10 @@ public ExperienceCompositeDto findCompositeDtoById(Long id, Language language) {
.from(experience)
.leftJoin(experience.firstImageFile, imageFile)
.leftJoin(experience.experienceTrans, experienceTrans)
.where(experience.id.eq(id).and(experienceTrans.language.eq(language)))
.where(
experience.id.eq(id),
experienceTrans.language.eq(language)
)
.fetchOne();
}

Expand Down Expand Up @@ -93,10 +96,12 @@ public Page<ExperienceCompositeDto> searchCompositeDtoByKeyword(String keyword,
.leftJoin(experience.firstImageFile, imageFile)
.leftJoin(experience.experienceTrans, experienceTrans)
.on(experienceTrans.language.eq(language))
.where(experienceTrans.title.contains(keyword)
.or(experienceTrans.addressTag.contains(keyword))
.or(experienceTrans.content.contains(keyword))
.or(experience.id.in(idListContainAllHashtags)))
.where(
experienceTrans.title.contains(keyword)
.or(experienceTrans.addressTag.contains(keyword))
.or(experienceTrans.content.contains(keyword))
.or(experience.id.in(idListContainAllHashtags))
)
.orderBy(experienceTrans.createdAt.desc())
.offset(pageable.getOffset())
.limit(pageable.getPageSize())
Expand All @@ -108,21 +113,24 @@ public Page<ExperienceCompositeDto> searchCompositeDtoByKeyword(String keyword,
.leftJoin(experience.firstImageFile, imageFile)
.leftJoin(experience.experienceTrans, experienceTrans)
.on(experienceTrans.language.eq(language))
.where(experienceTrans.title.contains(keyword)
.or(experienceTrans.addressTag.contains(keyword))
.or(experienceTrans.content.contains(keyword))
.or(experience.id.in(idListContainAllHashtags)));
.where(
experienceTrans.title.contains(keyword)
.or(experienceTrans.addressTag.contains(keyword))
.or(experienceTrans.content.contains(keyword))
.or(experience.id.in(idListContainAllHashtags))
);

return PageableExecutionUtils.getPage(resultDto, pageable, countQuery::fetchOne);
}

@Override
public Page<ExperienceThumbnail> findExperienceThumbnails(Language language,
ExperienceType experienceType, List<ExperienceTypeKeyword> keywordFilterList,
public Page<ExperienceResponse.PreviewDto> findAllExperiencePreviewDtoOrderByPriorityDescAndCreatedAtDesc(
Language language, ExperienceType experienceType,
List<ExperienceTypeKeyword> keywordFilterList,
List<String> addressFilterList, Pageable pageable) {

List<ExperienceThumbnail> resultDto = queryFactory
.selectDistinct(new QExperienceResponse_ExperienceThumbnail(
List<ExperienceResponse.PreviewDto> resultDto = queryFactory
.selectDistinct(new QExperienceResponse_PreviewDto(
experience.id,
imageFile.originUrl,
imageFile.thumbnailUrl,
Expand All @@ -134,12 +142,16 @@ public Page<ExperienceThumbnail> findExperienceThumbnails(Language language,
.innerJoin(experience.experienceTrans, experienceTrans)
.innerJoin(experienceKeyword)
.on(experienceKeyword.experience.id.eq(experience.id))
.where(experienceTrans.language.eq(language)
.and(experience.experienceType.eq(experienceType)) // μ΄μƒ‰μ²΄ν—˜ νƒ€μž…(μ•‘ν‹°λΉ„ν‹°/λ¬Έν™”μ˜ˆμˆ )
.and(addressTagCondition(addressFilterList)) // 지역필터
.and(keywordCondition(keywordFilterList))) // ν‚€μ›Œλ“œ ν•„ν„°
.orderBy(experience.priority.desc(), // μš°μ„ μˆœμœ„ μ •λ ¬
experience.createdAt.desc()) // μ΅œμ‹ μˆœ μ •λ ¬
.where(
experienceTrans.language.eq(language),
experience.experienceType.eq(experienceType), // μ΄μƒ‰μ²΄ν—˜ νƒ€μž…(μ•‘ν‹°λΉ„ν‹°/λ¬Έν™”μ˜ˆμˆ )
addressTagCondition(addressFilterList), // 지역필터
keywordCondition(keywordFilterList) // ν‚€μ›Œλ“œ ν•„ν„°
)
.orderBy(
experience.priority.desc(), // μš°μ„ μˆœμœ„ μ •λ ¬
experience.createdAt.desc() // μ΅œμ‹ μˆœ μ •λ ¬
)
.offset(pageable.getOffset())
.limit(pageable.getPageSize())
.fetch();
Expand All @@ -151,10 +163,12 @@ public Page<ExperienceThumbnail> findExperienceThumbnails(Language language,
.innerJoin(experience.experienceTrans, experienceTrans)
.innerJoin(experienceKeyword)
.on(experienceKeyword.experience.id.eq(experience.id))
.where(experienceTrans.language.eq(language)
.and(experience.experienceType.eq(experienceType))
.and(addressTagCondition(addressFilterList))
.and(keywordCondition(keywordFilterList)));
.where(
experienceTrans.language.eq(language),
experience.experienceType.eq(experienceType),
addressTagCondition(addressFilterList),
keywordCondition(keywordFilterList)
);

return PageableExecutionUtils.getPage(resultDto, pageable, countQuery::fetchOne);
}
Expand Down Expand Up @@ -214,12 +228,13 @@ private List<Long> getIdListContainAllHashtags(String keyword, Language language
.select(experience.id)
.from(experience)
.leftJoin(hashtag)
.on(hashtag.post.id.eq(experience.id)
.and(hashtag.category.eq(Category.EXPERIENCE))
.and(hashtag.language.eq(language)))
.on(hashtag.post.id.eq(experience.id),
hashtag.category.eq(Category.EXPERIENCE),
hashtag.language.eq(language)
)
.where(hashtag.keyword.content.in(splitKeyword(keyword)))
.groupBy(experience.id)
.having(experience.id.count().eq(splitKeyword(keyword).stream().count()))
.having(experience.id.count().eq((long) splitKeyword(keyword).size()))
.fetch();
}

Expand All @@ -234,18 +249,11 @@ private List<String> splitKeyword(String keyword) {
}

private BooleanExpression addressTagCondition(List<String> addressFilterList) {
if (addressFilterList.isEmpty()) {
return null;
} else {
return experienceTrans.addressTag.in(addressFilterList);
}
return addressFilterList.isEmpty() ? null : experienceTrans.addressTag.in(addressFilterList);
}

private BooleanExpression keywordCondition(List<ExperienceTypeKeyword> keywordFilterList) {
if (keywordFilterList.isEmpty()) {
return null;
} else {
return experienceKeyword.experienceTypeKeyword.in(keywordFilterList);
}
return keywordFilterList.isEmpty() ? null
: experienceKeyword.experienceTypeKeyword.in(keywordFilterList);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -11,9 +11,7 @@
import com.jeju.nanaland.domain.common.repository.ImageFileRepository;
import com.jeju.nanaland.domain.common.service.PostService;
import com.jeju.nanaland.domain.experience.dto.ExperienceCompositeDto;
import com.jeju.nanaland.domain.experience.dto.ExperienceResponse.ExperienceDetailDto;
import com.jeju.nanaland.domain.experience.dto.ExperienceResponse.ExperienceThumbnail;
import com.jeju.nanaland.domain.experience.dto.ExperienceResponse.ExperienceThumbnailDto;
import com.jeju.nanaland.domain.experience.dto.ExperienceResponse;
import com.jeju.nanaland.domain.experience.entity.enums.ExperienceType;
import com.jeju.nanaland.domain.experience.entity.enums.ExperienceTypeKeyword;
import com.jeju.nanaland.domain.experience.repository.ExperienceRepository;
Expand Down Expand Up @@ -79,42 +77,63 @@ public PostPreviewDto getPostPreviewDto(Long postId, Category category, Language
return postPreviewDto;
}

// μ΄μƒ‰μ²΄ν—˜ 리슀트 쑰회
public ExperienceThumbnailDto getExperienceList(MemberInfoDto memberInfoDto,
/**
* μ΄μƒ‰μ²΄ν—˜ 리슀트 쑰회
*
* @param memberInfoDto νšŒμ› 정보
* @param experienceType μ΄μƒ‰μ²΄ν—˜ νƒ€μž… (ACTIVITY, CULTURE_AND_ARTS)
* @param keywordFilterList ν‚€μ›Œλ“œ ν•„ν„° (LAND_LEISURE, WATER_LEISURE, AIR_LEISURE, MARINE_EXPERIENCE,
* RURAL_EXPERIENCE, HEALING_THERAPY, HISTORY, EXHIBITION, WORKSHOP,
* ART_MUSEUM, MUSEUM, PARK, PERFORMANCE, RELIGIOUS_FACILITY,
* THEME_PARK)
* @param addressFilterList 지역 ν•„ν„°
* @param page νŽ˜μ΄μ§€
* @param size νŽ˜μ΄μ§€ 크기
* @return ExperienceResponse.PreviewPageDto
*/
public ExperienceResponse.PreviewPageDto getExperiencePreviews(MemberInfoDto memberInfoDto,
ExperienceType experienceType, List<ExperienceTypeKeyword> keywordFilterList,
List<String> addressFilterList, int page, int size) {

Language language = memberInfoDto.getLanguage();
Pageable pageable = PageRequest.of(page, size);

// experienceType(μ•‘ν‹°λΉ„ν‹°, λ¬Έν™”μ˜ˆμˆ )에 λ”°λ₯Έ μ΄μƒ‰μ²΄ν—˜ 쑰회
Page<ExperienceThumbnail> experienceThumbnailPage = experienceRepository.findExperienceThumbnails(
language, experienceType, keywordFilterList, addressFilterList, pageable);
Page<ExperienceResponse.PreviewDto> experiencePreviewPage =
experienceRepository.findAllExperiencePreviewDtoOrderByPriorityDescAndCreatedAtDesc(
language, experienceType, keywordFilterList, addressFilterList, pageable);

// μ’‹μ•„μš” μ—¬λΆ€
List<Long> favoriteIds = memberFavoriteService.getFavoritePostIdsWithMember(
memberInfoDto.getMember());
List<ExperienceThumbnail> data = experienceThumbnailPage.getContent();
List<ExperienceResponse.PreviewDto> data = experiencePreviewPage.getContent();

// μ’‹μ•„μš” μ—¬λΆ€, 리뷰 평균 μΆ”κ°€
for (ExperienceThumbnail experienceThumbnail : data) {
Long postId = experienceThumbnail.getId();
experienceThumbnail.setFavorite(favoriteIds.contains(postId));
experienceThumbnail.setRatingAvg(reviewRepository.findTotalRatingAvg(EXPERIENCE, postId));
for (ExperienceResponse.PreviewDto previewDto : data) {
Long postId = previewDto.getId();
previewDto.setFavorite(favoriteIds.contains(postId));
previewDto.setRatingAvg(reviewRepository.findTotalRatingAvg(EXPERIENCE, postId));
}

return ExperienceThumbnailDto.builder()
.totalElements(experienceThumbnailPage.getTotalElements())
return ExperienceResponse.PreviewPageDto.builder()
.totalElements(experiencePreviewPage.getTotalElements())
.data(data)
.build();
}

// μ΄μƒ‰μ²΄ν—˜ 상세 정보 쑰회
public ExperienceDetailDto getExperienceDetail(MemberInfoDto memberInfoDto, Long postId,
/**
* μ΄μƒ‰μ²΄ν—˜ 상세정보 쑰회
*
* @param memberInfoDto νšŒμ› 정보
* @param postId κ²Œμ‹œλ¬Ό id
* @param isSearch 검색을 톡해 λ“€μ–΄μ™”λŠ”μ§€ μ—¬λΆ€
* @return ExperienceResponse.DetailDto
*/
public ExperienceResponse.DetailDto getExperienceDetail(MemberInfoDto memberInfoDto, Long postId,
boolean isSearch) {

Language language = memberInfoDto.getLanguage();
ExperienceCompositeDto experienceCompositeDto = experienceRepository.findCompositeDtoById(
ExperienceCompositeDto experienceCompositeDto = experienceRepository.findExperienceCompositeDto(
postId, language);

// ν•΄λ‹Ή id의 ν¬μŠ€νŠΈκ°€ μ—†λŠ” 경우 404 μ—λŸ¬
Expand Down Expand Up @@ -144,7 +163,7 @@ public ExperienceDetailDto getExperienceDetail(MemberInfoDto memberInfoDto, Long
experienceTypeKeyword.getValueByLocale(language)
).toList();

return ExperienceDetailDto.builder()
return ExperienceResponse.DetailDto.builder()
.id(experienceCompositeDto.getId())
.title(experienceCompositeDto.getTitle())
.intro(experienceCompositeDto.getIntro())
Expand Down
Loading