Skip to content

Commit 13e0204

Browse files
authored
[feat] 칵테일 검색/필터 컨트롤러 기능 구현#72
* {feat} : domain * {fix}:Cocktail-Wishlist relation * fix : enums * fix : bug * feat : 조회기능, 조init data * feat : cocktailSearch * feat: get cocktailTest * feat : controller * feat : cocktail controller * fix : Dto naming
1 parent ff6a79a commit 13e0204

File tree

10 files changed

+183
-117
lines changed

10 files changed

+183
-117
lines changed
Lines changed: 40 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -1,31 +1,61 @@
11
package com.back.domain.cocktail.controller;
22

3-
import com.back.domain.cocktail.dto.CocktailDetailDto;
3+
import com.back.domain.cocktail.dto.CocktailDetailResponseDto;
4+
import com.back.domain.cocktail.dto.CocktailSearchRequestDto;
5+
import com.back.domain.cocktail.dto.CocktailSearchResponseDto;
6+
import com.back.domain.cocktail.dto.CocktailSummaryResponseDto;
47
import com.back.domain.cocktail.service.CocktailService;
5-
import com.back.domain.user.service.UserService;
68
import com.back.global.rsData.RsData;
79
import io.swagger.v3.oas.annotations.Operation;
810
import lombok.RequiredArgsConstructor;
911
import org.springframework.transaction.annotation.Transactional;
10-
import org.springframework.web.bind.annotation.GetMapping;
11-
import org.springframework.web.bind.annotation.PathVariable;
12-
import org.springframework.web.bind.annotation.RequestMapping;
13-
import org.springframework.web.bind.annotation.RestController;
12+
import org.springframework.web.bind.annotation.*;
13+
14+
import java.util.List;
1415

1516
@RestController
1617
@RequestMapping("api/cocktails")
1718
@RequiredArgsConstructor
1819
public class CocktailController {
1920

2021
private final CocktailService cocktailService;
21-
private final UserService userService;
2222

2323
@GetMapping("/{id}")
2424
@Transactional
2525
@Operation(summary = "칵테일 단건 조회")
26-
public RsData<CocktailDetailDto> getCocktailDetailById(@PathVariable long id) {
26+
public RsData<CocktailDetailDto> getCocktailDetailById(@PathVariable long id){
27+
28+
CocktailDetailResponseDto cocktailDetailResponseDto = cocktailService.getCocktailDetailById(id);
29+
return RsData.successOf(cocktailDetailResponseDto);
30+
}
31+
32+
// @param lastId 마지막으로 가져온 칵테일 ID (첫 요청 시 null 가능)
33+
// @param size 가져올 데이터 개수 (기본값 DEFAULT_SIZE)
34+
// @return RsData 형태의 칵테일 요약 정보 리스트
35+
@GetMapping
36+
@Transactional
37+
@Operation(summary = "칵테일 다건 조회")
38+
public RsData<List<CocktailSummaryResponseDto>> getCocktails(
39+
@RequestParam(value = "lastId", required = false) Long lastId,
40+
@RequestParam(value = "size", required = false) Integer size
41+
) {
42+
List<CocktailSummaryResponseDto> cocktails = cocktailService.getCocktails(lastId, size);
43+
return RsData.successOf(cocktails);
44+
}
45+
46+
47+
// 칵테일 검색 및 필터링
48+
// POST 방식으로 JSON body를 통해 검색 조건 전달
49+
50+
@PostMapping("/search")
51+
@Operation(summary = "칵테일 검색 및 필터링")
52+
public RsData<List<CocktailSearchResponseDto>> searchAndFilter(
53+
@RequestBody CocktailSearchRequestDto cocktailSearchRequestDto
54+
) {
55+
// 서비스 호출
56+
List<CocktailSearchResponseDto> searchResults = cocktailService.searchAndFilter(cocktailSearchRequestDto);
2757

28-
CocktailDetailDto cocktailDetailDto = cocktailService.getCocktailDetailById(id);
29-
return RsData.successOf(cocktailDetailDto);
58+
// RsData로 통일된 응답 반환
59+
return RsData.successOf(searchResults);
3060
}
3161
}

src/main/java/com/back/domain/cocktail/dto/CocktailDetailDto.java

Lines changed: 0 additions & 32 deletions
This file was deleted.
Lines changed: 52 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,52 @@
1+
package com.back.domain.cocktail.dto;
2+
3+
import com.back.domain.cocktail.entity.Cocktail;
4+
import com.back.domain.cocktail.enums.AlcoholBaseType;
5+
import com.back.domain.cocktail.enums.AlcoholStrength;
6+
import com.back.domain.cocktail.enums.CocktailType;
7+
import lombok.Getter;
8+
import lombok.NoArgsConstructor;
9+
10+
@Getter
11+
@NoArgsConstructor
12+
public class CocktailDetailResponseDto {
13+
private Long cocktailId;
14+
private String cocktailName;
15+
private AlcoholStrength alcoholStrength;
16+
private CocktailType cocktailType;
17+
private AlcoholBaseType alcoholBaseType;
18+
private String cocktailImgUrl;
19+
private String cocktailStory;
20+
private String ingredient;
21+
private String recipe;
22+
23+
public CocktailDetailResponseDto(
24+
long cocktailId, String cocktailName,
25+
AlcoholStrength alcoholStrength, CocktailType cocktailType,
26+
AlcoholBaseType alcoholBaseType, String cocktailImgUrl,
27+
String cocktailStory, String ingredient,
28+
String recipe
29+
) {
30+
this.cocktailId = cocktailId;
31+
this.cocktailName = cocktailName;
32+
this.alcoholStrength = alcoholStrength;
33+
this.cocktailType = cocktailType;
34+
this.alcoholBaseType = alcoholBaseType;
35+
this.cocktailImgUrl = cocktailImgUrl;
36+
this.cocktailStory = cocktailStory;
37+
this.ingredient = ingredient;
38+
this.recipe = recipe;
39+
}
40+
41+
public CocktailDetailResponseDto(Cocktail cocktail) {
42+
this.cocktailId = cocktail.getCocktailId();
43+
this.cocktailName = cocktail.getCocktailName();
44+
this.alcoholStrength = cocktail.getAlcoholStrength();
45+
this.cocktailType = cocktail.getCocktailType();
46+
this.alcoholBaseType = cocktail.getAlcoholBaseType();
47+
this.cocktailImgUrl = cocktail.getCocktailImgUrl();
48+
this.cocktailStory = cocktail.getCocktailStory();
49+
this.ingredient = cocktail.getIngredient();
50+
this.recipe = cocktail.getRecipe();
51+
}
52+
}

src/main/java/com/back/domain/cocktail/dto/CocktailRequestDto.java

Lines changed: 0 additions & 29 deletions
This file was deleted.

src/main/java/com/back/domain/cocktail/dto/CocktailFilterRequestDto.java renamed to src/main/java/com/back/domain/cocktail/dto/CocktailSearchRequestDto.java

Lines changed: 13 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,8 @@
33
import com.back.domain.cocktail.enums.AlcoholBaseType;
44
import com.back.domain.cocktail.enums.AlcoholStrength;
55
import com.back.domain.cocktail.enums.CocktailType;
6+
import jakarta.validation.constraints.Max;
7+
import jakarta.validation.constraints.Min;
68
import lombok.Getter;
79
import lombok.NoArgsConstructor;
810
import lombok.Setter;
@@ -12,7 +14,7 @@
1214
@Getter
1315
@Setter
1416
@NoArgsConstructor
15-
public class CocktailFilterRequestDto {
17+
public class CocktailSearchRequestDto {
1618

1719
private String keyword; // 검색 키워드
1820

@@ -23,15 +25,20 @@ public class CocktailFilterRequestDto {
2325
private List<AlcoholBaseType> alcoholBaseTypes;
2426

2527
// 페이징/정렬 추가하고 싶으면 여기 옵션 추가
28+
@Min(0)
2629
private Integer page; // 0-based 페이지 번호
30+
@Max(100)
2731
private Integer size; // 페이지 사이즈
2832

2933
// 생성자
30-
public CocktailFilterRequestDto(String keyword,
31-
List<AlcoholStrength> alcoholStrengths,
32-
List<CocktailType> cocktailTypes,
33-
List<AlcoholBaseType> alcoholBaseTypes,
34-
Integer page, Integer size) {
34+
public CocktailSearchRequestDto(
35+
String keyword,
36+
List<AlcoholStrength> alcoholStrengths,
37+
List<CocktailType> cocktailTypes,
38+
List<AlcoholBaseType> alcoholBaseTypes,
39+
Integer page,
40+
Integer size
41+
) {
3542
this.keyword = keyword;
3643
this.alcoholStrengths = alcoholStrengths;
3744
this.cocktailTypes = cocktailTypes;

src/main/java/com/back/domain/cocktail/dto/CocktailResponseDto.java renamed to src/main/java/com/back/domain/cocktail/dto/CocktailSearchResponseDto.java

Lines changed: 6 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -12,24 +12,21 @@
1212
@Getter
1313
@Setter
1414
@NoArgsConstructor
15-
public class CocktailResponseDto {
15+
public class CocktailSearchResponseDto {
1616

1717
private long cocktailId;
1818
private String cocktailName;
1919
private AlcoholStrength alcoholStrength;
20-
private String cocktailStory;
2120
private CocktailType cocktailType;
2221
private AlcoholBaseType alcoholBaseType;
23-
private String ingredient;
24-
private String recipe;
2522
private String cocktailImgUrl;
23+
private String cocktailStory;
2624
private LocalDateTime createdAt;
27-
private LocalDateTime updatedAt;
2825

29-
public CocktailResponseDto(long cocktailId, String cocktailName,
30-
AlcoholStrength alcoholStrength, CocktailType cocktailType,
31-
AlcoholBaseType alcoholBaseType, String cocktailImgUrl,
32-
String cocktailStory, LocalDateTime createdAt) {
26+
public CocktailSearchResponseDto(long cocktailId, String cocktailName,
27+
AlcoholStrength alcoholStrength, CocktailType cocktailType,
28+
AlcoholBaseType alcoholBaseType, String cocktailImgUrl,
29+
String cocktailStory, LocalDateTime createdAt) {
3330
this.cocktailId = cocktailId;
3431
this.cocktailName = cocktailName;
3532
this.alcoholStrength = alcoholStrength;

src/main/java/com/back/domain/cocktail/dto/CocktailSummaryDto.java renamed to src/main/java/com/back/domain/cocktail/dto/CocktailSummaryResponseDto.java

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3,12 +3,12 @@
33
import lombok.Getter;
44

55
@Getter
6-
public class CocktailSummaryDto {
6+
public class CocktailSummaryResponseDto {
77
private Long cocktailId;
88
private String cocktailName;
99
private String cocktailImgUrl;
1010

11-
public CocktailSummaryDto(Long id, String name, String imageUrl) {
11+
public CocktailSummaryResponseDto(Long id, String name, String imageUrl) {
1212
this.cocktailId = id;
1313
this.cocktailName = name;
1414
this.cocktailImgUrl = imageUrl;

src/main/java/com/back/domain/cocktail/service/CocktailService.java

Lines changed: 24 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,9 @@
11
package com.back.domain.cocktail.service;
22

3-
import com.back.domain.cocktail.dto.CocktailDetailDto;
4-
import com.back.domain.cocktail.dto.CocktailFilterRequestDto;
5-
import com.back.domain.cocktail.dto.CocktailResponseDto;
6-
import com.back.domain.cocktail.dto.CocktailSummaryDto;
3+
import com.back.domain.cocktail.dto.CocktailDetailResponseDto;
4+
import com.back.domain.cocktail.dto.CocktailSearchRequestDto;
5+
import com.back.domain.cocktail.dto.CocktailSearchResponseDto;
6+
import com.back.domain.cocktail.dto.CocktailSummaryResponseDto;
77
import com.back.domain.cocktail.entity.Cocktail;
88
import com.back.domain.cocktail.enums.AlcoholBaseType;
99
import com.back.domain.cocktail.enums.AlcoholStrength;
@@ -31,13 +31,14 @@ public class CocktailService {
3131

3232
@Transactional(readOnly = true)
3333
public Cocktail getCocktailById(Long id) {
34+
3435
return cocktailRepository.findById(id)
3536
.orElseThrow(() -> new IllegalArgumentException("User not found. id=" + id));
36-
}
37+
}
3738

3839
// 칵테일 무한스크롤 조회
3940
@Transactional(readOnly = true)
40-
public List<CocktailSummaryDto> getCocktails (Long lastId, Integer size)
41+
public List<CocktailSummaryResponseDto> getCocktails (Long lastId, Integer size)
4142
{ // 무한스크롤 조회, 클라이언트 쪽에서 lastId와 size 정보를 받음.(스크롤 이벤트)
4243
int fetchSize = (size != null) ? size : DEFAULT_SIZE;
4344

@@ -50,7 +51,7 @@ public List<CocktailSummaryDto> getCocktails (Long lastId, Integer size)
5051
cocktails = cocktailRepository.findByCocktailIdLessThanOrderByCocktailIdDesc(lastId, PageRequest.of(0, fetchSize));
5152
}
5253
return cocktails.stream()
53-
.map(c -> new CocktailSummaryDto(c.getCocktailId(), c.getCocktailName(), c.getCocktailImgUrl()))
54+
.map(c -> new CocktailSummaryResponseDto(c.getCocktailId(), c.getCocktailName(), c.getCocktailImgUrl()))
5455
.collect(Collectors.toList());
5556
}
5657

@@ -69,42 +70,42 @@ public List<Cocktail> cocktailSearch (String keyword){
6970

7071
// 칵테일 검색,필터기능
7172
@Transactional(readOnly = true)
72-
public List<CocktailResponseDto> searchAndFilter (CocktailFilterRequestDto cocktailFilterRequestDto){
73+
public List<CocktailSearchResponseDto> searchAndFilter (CocktailSearchRequestDto cocktailSearchRequestDto){
7374
// 기본값 페이지/사이즈 정하기(PAGE 기본값 0, 사이즈 10)
74-
int page = cocktailFilterRequestDto.getPage() != null && cocktailFilterRequestDto.getPage() >= 0
75-
? cocktailFilterRequestDto.getPage() : 0;
75+
int page = cocktailSearchRequestDto.getPage() != null && cocktailSearchRequestDto.getPage() >= 0
76+
? cocktailSearchRequestDto.getPage() : 0;
7677

77-
int size = cocktailFilterRequestDto.getSize() != null && cocktailFilterRequestDto.getSize() > 0
78-
? cocktailFilterRequestDto.getSize() : DEFAULT_SIZE;
78+
int size = cocktailSearchRequestDto.getSize() != null && cocktailSearchRequestDto.getSize() > 0
79+
? cocktailSearchRequestDto.getSize() : DEFAULT_SIZE;
7980

8081
// searchWithFilters에서 조회한 결과값을 pageResult에 저장.
8182
Pageable pageable = PageRequest.of(page, size);
8283

8384
// 빈 리스트(null 또는 [])는 null로 변환
84-
List<AlcoholStrength> strengths = CollectionUtils.isEmpty(cocktailFilterRequestDto.getAlcoholStrengths())
85+
List<AlcoholStrength> strengths = CollectionUtils.isEmpty(cocktailSearchRequestDto.getAlcoholStrengths())
8586
? null
86-
: cocktailFilterRequestDto.getAlcoholStrengths();
87+
: cocktailSearchRequestDto.getAlcoholStrengths();
8788

88-
List<CocktailType> types = CollectionUtils.isEmpty(cocktailFilterRequestDto.getCocktailTypes())
89+
List<CocktailType> types = CollectionUtils.isEmpty(cocktailSearchRequestDto.getCocktailTypes())
8990
? null
90-
: cocktailFilterRequestDto.getCocktailTypes();
91+
: cocktailSearchRequestDto.getCocktailTypes();
9192

92-
List<AlcoholBaseType> bases = CollectionUtils.isEmpty(cocktailFilterRequestDto.getAlcoholBaseTypes())
93+
List<AlcoholBaseType> bases = CollectionUtils.isEmpty(cocktailSearchRequestDto.getAlcoholBaseTypes())
9394
? null
94-
: cocktailFilterRequestDto.getAlcoholBaseTypes();
95+
: cocktailSearchRequestDto.getAlcoholBaseTypes();
9596

9697
// Repository 호출
9798
Page<Cocktail> pageResult = cocktailRepository.searchWithFilters(
98-
cocktailFilterRequestDto.getKeyword(),
99+
cocktailSearchRequestDto.getKeyword(),
99100
strengths, // List<AlcoholStrength>
100101
types, // List<CocktailType>
101102
bases, // List<AlcoholBaseType>
102103
pageable
103104
);
104105

105106
//Cocktail 엔티티 → CocktailResponseDto 응답 DTO로 바꿔주는 과정
106-
List<CocktailResponseDto> resultDtos = pageResult.stream()
107-
.map(c -> new CocktailResponseDto(
107+
List<CocktailSearchResponseDto> resultDtos = pageResult.stream()
108+
.map(c -> new CocktailSearchResponseDto(
108109
c.getCocktailId(),
109110
c.getCocktailName(),
110111
c.getAlcoholStrength(),
@@ -125,9 +126,9 @@ public List<CocktailResponseDto> searchAndFilter (CocktailFilterRequestDto cockt
125126

126127
// 칵테일 상세조회
127128
@Transactional(readOnly = true)
128-
public CocktailDetailDto getCocktailDetailById (Long cocktailId){
129+
public CocktailDetailResponseDto getCocktailDetailById (Long cocktailId){
129130
Cocktail cocktail = cocktailRepository.findById(cocktailId)
130131
.orElseThrow(() -> new NoSuchElementException("칵테일을 찾을 수 없습니다. id: " + cocktailId));
131-
return new CocktailDetailDto(cocktail);
132+
return new CocktailDetailResponseDto(cocktail);
132133
}
133134
}

0 commit comments

Comments
 (0)