diff --git a/src/main/java/ybe/mini/travelserver/domain/cart/controller/CartController.java b/src/main/java/ybe/mini/travelserver/domain/cart/controller/CartController.java index e235d4e..e0399a6 100644 --- a/src/main/java/ybe/mini/travelserver/domain/cart/controller/CartController.java +++ b/src/main/java/ybe/mini/travelserver/domain/cart/controller/CartController.java @@ -52,7 +52,8 @@ public ResponseDto createCart( public ResponseDto deleteCart( @AuthenticationPrincipal PrincipalDetails principalDetails, @PathVariable Long cartId) { - CartDeleteResponse cartDeleteResponse = cartService.deleteCart(cartId); + CartDeleteResponse cartDeleteResponse = + cartService.deleteCart(principalDetails.getMemberId(), cartId); return new ResponseDto<>(HttpStatus.OK.value(), cartDeleteResponse); } } \ No newline at end of file diff --git a/src/main/java/ybe/mini/travelserver/domain/cart/dto/request/CartCreateRequest.java b/src/main/java/ybe/mini/travelserver/domain/cart/dto/request/CartCreateRequest.java index b868277..7f6c192 100644 --- a/src/main/java/ybe/mini/travelserver/domain/cart/dto/request/CartCreateRequest.java +++ b/src/main/java/ybe/mini/travelserver/domain/cart/dto/request/CartCreateRequest.java @@ -2,7 +2,10 @@ import com.fasterxml.jackson.annotation.JsonFormat; import com.fasterxml.jackson.annotation.JsonIgnoreProperties; +import jakarta.validation.constraints.FutureOrPresent; import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.NotNull; +import jakarta.validation.constraints.Positive; import lombok.Builder; import java.time.LocalDate; @@ -10,26 +13,29 @@ @Builder @JsonIgnoreProperties(ignoreUnknown = true) public record CartCreateRequest( - @NotBlank + + @Positive Long roomTypeId, - @NotBlank + + @FutureOrPresent @JsonFormat(shape = JsonFormat.Shape.STRING, pattern = "yyyy-MM-dd") LocalDate checkIn, - @NotBlank + + @FutureOrPresent @JsonFormat(shape = JsonFormat.Shape.STRING, pattern = "yyyy-MM-dd") LocalDate checkOut, - @NotBlank + + @Positive Integer guestNumber, + + @Positive + Long accommodationId, + @NotBlank - Long accommodationId + String keyword, + @NotBlank + String areaCode ) { -// public static CartCreateRequest fromEntity(Cart cart) { -// return new CartCreateRequest( -// cart.getId(), -// cart.getCheckIn(), -// cart.getCheckOut(), -// cart.getGuestNumber() -// ); -// } + } \ No newline at end of file diff --git a/src/main/java/ybe/mini/travelserver/domain/cart/dto/response/CartCreateResponse.java b/src/main/java/ybe/mini/travelserver/domain/cart/dto/response/CartCreateResponse.java index db0cce5..299a5a2 100644 --- a/src/main/java/ybe/mini/travelserver/domain/cart/dto/response/CartCreateResponse.java +++ b/src/main/java/ybe/mini/travelserver/domain/cart/dto/response/CartCreateResponse.java @@ -1,9 +1,11 @@ package ybe.mini.travelserver.domain.cart.dto.response; import com.fasterxml.jackson.annotation.JsonIgnoreProperties; +import jakarta.validation.constraints.Positive; @JsonIgnoreProperties(ignoreUnknown = true) public record CartCreateResponse ( - Long id + @Positive + Long id ){ } diff --git a/src/main/java/ybe/mini/travelserver/domain/cart/dto/response/CartDeleteResponse.java b/src/main/java/ybe/mini/travelserver/domain/cart/dto/response/CartDeleteResponse.java index 7d06cfd..700e340 100644 --- a/src/main/java/ybe/mini/travelserver/domain/cart/dto/response/CartDeleteResponse.java +++ b/src/main/java/ybe/mini/travelserver/domain/cart/dto/response/CartDeleteResponse.java @@ -1,9 +1,11 @@ package ybe.mini.travelserver.domain.cart.dto.response; import com.fasterxml.jackson.annotation.JsonIgnoreProperties; +import jakarta.validation.constraints.Positive; @JsonIgnoreProperties(ignoreUnknown = true) public record CartDeleteResponse ( + @Positive Long id ){ } \ No newline at end of file diff --git a/src/main/java/ybe/mini/travelserver/domain/cart/dto/response/CartGetResponse.java b/src/main/java/ybe/mini/travelserver/domain/cart/dto/response/CartGetResponse.java index d846963..60f19e7 100644 --- a/src/main/java/ybe/mini/travelserver/domain/cart/dto/response/CartGetResponse.java +++ b/src/main/java/ybe/mini/travelserver/domain/cart/dto/response/CartGetResponse.java @@ -1,6 +1,9 @@ package ybe.mini.travelserver.domain.cart.dto.response; import com.fasterxml.jackson.annotation.JsonIgnoreProperties; +import jakarta.validation.Valid; +import jakarta.validation.constraints.FutureOrPresent; +import jakarta.validation.constraints.Positive; import ybe.mini.travelserver.domain.accommodation.dto.AccommodationGetResponse; import ybe.mini.travelserver.domain.accommodation.entity.Accommodation; import ybe.mini.travelserver.domain.cart.entity.Cart; @@ -11,17 +14,29 @@ @JsonIgnoreProperties(ignoreUnknown = true) public record CartGetResponse ( + @Positive Long id, + + @Positive Integer guestNumber, + + @FutureOrPresent LocalDate checkIn, + + @FutureOrPresent LocalDate checkOut, + + @Valid RoomGetResponse roomGetResponse, + + @Valid AccommodationGetResponse accommodationGetResponse ) { public static CartGetResponse fromEntity( Cart cart, Room room, - Accommodation accommodation) { + Accommodation accommodation + ) { return new CartGetResponse( cart.getId(), cart.getGuestNumber(), diff --git a/src/main/java/ybe/mini/travelserver/domain/cart/exception/CartAleadyExistException.java b/src/main/java/ybe/mini/travelserver/domain/cart/exception/CartAleadyExistException.java new file mode 100644 index 0000000..200d518 --- /dev/null +++ b/src/main/java/ybe/mini/travelserver/domain/cart/exception/CartAleadyExistException.java @@ -0,0 +1,5 @@ +package ybe.mini.travelserver.domain.cart.exception; + +public class CartAleadyExistException extends RuntimeException { + +} diff --git a/src/main/java/ybe/mini/travelserver/domain/cart/exception/CartErrorMessage.java b/src/main/java/ybe/mini/travelserver/domain/cart/exception/CartErrorMessage.java new file mode 100644 index 0000000..092e557 --- /dev/null +++ b/src/main/java/ybe/mini/travelserver/domain/cart/exception/CartErrorMessage.java @@ -0,0 +1,19 @@ +package ybe.mini.travelserver.domain.cart.exception; + +import lombok.AllArgsConstructor; +import lombok.Getter; +import ybe.mini.travelserver.global.exception.ErrorMessage; +import org.springframework.http.HttpStatus; +import static org.springframework.http.HttpStatus.BAD_REQUEST; +@Getter +@AllArgsConstructor +public enum CartErrorMessage implements ErrorMessage { + + CART_INVALID_MEMBER(BAD_REQUEST, "해당 ID가 유효하지 않습니다."), + CART_ALREADY_EXIST(BAD_REQUEST, "해당 정보가 장바구니에 담겨있습니다."), + + CART_NOT_FOUND(BAD_REQUEST, "해당 ID의 장바구니 정보가 없습니다.") + ; + private final HttpStatus status; + private final String message; +} \ No newline at end of file diff --git a/src/main/java/ybe/mini/travelserver/domain/cart/exception/CartExceptionHandler.java b/src/main/java/ybe/mini/travelserver/domain/cart/exception/CartExceptionHandler.java new file mode 100644 index 0000000..ce7604d --- /dev/null +++ b/src/main/java/ybe/mini/travelserver/domain/cart/exception/CartExceptionHandler.java @@ -0,0 +1,34 @@ +package ybe.mini.travelserver.domain.cart.exception; + +import jakarta.servlet.http.HttpServletRequest; +import org.springframework.http.ProblemDetail; +import org.springframework.web.bind.annotation.ExceptionHandler; +import org.springframework.web.bind.annotation.RestControllerAdvice; +import ybe.mini.travelserver.domain.cart.controller.CartController; +import ybe.mini.travelserver.global.exception.ProblemDetailCreator; + +import static ybe.mini.travelserver.domain.cart.exception.CartErrorMessage.*; + +@RestControllerAdvice(basePackageClasses = CartController.class) +public class CartExceptionHandler extends ProblemDetailCreator { + + protected CartExceptionHandler() { + super("장바구니 처리 실패"); + } + + @ExceptionHandler(CartNotFoundException.class) + public ProblemDetail handelCartNotFoundException(HttpServletRequest request) { + return createProblemDetail(CART_NOT_FOUND, request); + } + + @ExceptionHandler(CartInvalidMemberException.class) + public ProblemDetail handelCartInvalidMemberException(HttpServletRequest request) { + return createProblemDetail(CART_INVALID_MEMBER, request); + } + + @ExceptionHandler(CartAleadyExistException.class) + public ProblemDetail handelCartAleadyExistException(HttpServletRequest request) { + return createProblemDetail(CART_ALREADY_EXIST, request); + } + +} \ No newline at end of file diff --git a/src/main/java/ybe/mini/travelserver/domain/cart/exception/CartInvalidMemberException.java b/src/main/java/ybe/mini/travelserver/domain/cart/exception/CartInvalidMemberException.java new file mode 100644 index 0000000..86b63d3 --- /dev/null +++ b/src/main/java/ybe/mini/travelserver/domain/cart/exception/CartInvalidMemberException.java @@ -0,0 +1,4 @@ +package ybe.mini.travelserver.domain.cart.exception; + +public class CartInvalidMemberException extends RuntimeException { +} diff --git a/src/main/java/ybe/mini/travelserver/domain/cart/exception/CartNotFoundException.java b/src/main/java/ybe/mini/travelserver/domain/cart/exception/CartNotFoundException.java new file mode 100644 index 0000000..2f64c73 --- /dev/null +++ b/src/main/java/ybe/mini/travelserver/domain/cart/exception/CartNotFoundException.java @@ -0,0 +1,5 @@ +package ybe.mini.travelserver.domain.cart.exception; + +public class CartNotFoundException extends RuntimeException { + +} \ No newline at end of file diff --git a/src/main/java/ybe/mini/travelserver/domain/cart/service/CartService.java b/src/main/java/ybe/mini/travelserver/domain/cart/service/CartService.java index 26e66d6..fd8ff95 100644 --- a/src/main/java/ybe/mini/travelserver/domain/cart/service/CartService.java +++ b/src/main/java/ybe/mini/travelserver/domain/cart/service/CartService.java @@ -11,8 +11,11 @@ import ybe.mini.travelserver.domain.cart.dto.response.CartDeleteResponse; import ybe.mini.travelserver.domain.cart.dto.response.CartGetResponse; import ybe.mini.travelserver.domain.cart.entity.Cart; +import ybe.mini.travelserver.domain.cart.exception.CartInvalidMemberException; +import ybe.mini.travelserver.domain.cart.exception.CartNotFoundException; import ybe.mini.travelserver.domain.cart.repository.CartRepository; import ybe.mini.travelserver.domain.member.entity.Member; +import ybe.mini.travelserver.domain.member.exception.MemberNotFoundException; import ybe.mini.travelserver.domain.member.repository.MemberRepository; import ybe.mini.travelserver.domain.room.entity.Room; import ybe.mini.travelserver.domain.room.repository.RoomRepository; @@ -34,13 +37,11 @@ public class CartService { @Transactional public CartCreateResponse createCart(Long userId, CartCreateRequest cartCreateRequest) { Member member = getMemberById(userId); - Long accommodtationId = cartCreateRequest.accommodationId(); - Long roomTypeId = cartCreateRequest.roomTypeId(); + createAccommodationById(cartCreateRequest.keyword(), cartCreateRequest.areaCode()); + Room room = createRoomById( + cartCreateRequest.accommodationId(), cartCreateRequest.roomTypeId()); - Accommodation accommodation = createAccommodationById(accommodtationId); - Room room = createRoomById(accommodtationId, roomTypeId); Cart cart = createCart(cartCreateRequest, room, member); - Cart createdCart = cartRepository.save(cart); return new CartCreateResponse(createdCart.getId()); @@ -55,20 +56,24 @@ public List getMyCarts(Long userId) { } @Transactional - public CartDeleteResponse deleteCart(Long cartId) { - - cartRepository.findById(cartId).orElseThrow(RuntimeException::new); - cartRepository.deleteById(cartId); - return new CartDeleteResponse(cartId); + public CartDeleteResponse deleteCart(Long memberId, Long cartId) { + Cart cart = cartRepository.findById(cartId) + .orElseThrow(CartNotFoundException::new); + if (cart.getMember().getId() == memberId) { + cartRepository.deleteById(cartId); + return new CartDeleteResponse(cartId); + } else { + throw new CartInvalidMemberException(); + } } private Member getMemberById(Long id) { return memberRepository.findById(id) - .orElseThrow(RuntimeException::new); + .orElseThrow(MemberNotFoundException::new); } - private Accommodation createAccommodationById(Long accommodationId) { - Accommodation accommodation = tourAPIService.bringAccommodation(accommodationId, "_"); + private Accommodation createAccommodationById(String keyword, String areaCode) { + Accommodation accommodation = tourAPIService.bringAccommodation(keyword, areaCode); return getOrSaveAccommodation(accommodation); } @@ -78,6 +83,10 @@ private Room createRoomById(Long accommodationId, Long roomId) { } private Cart createCart(CartCreateRequest cartCreateRequest, Room room, Member member) { + // TODO : 성수님 roomId 관련 논의 + roomRepository.findById(room.getId()) + .orElseThrow(CartInvalidMemberException::new); + return Cart.builder() .guestNumber(cartCreateRequest.guestNumber()) .room(room)