Skip to content

Commit

Permalink
Merge branch 'develop' into refactor/product-room-cart
Browse files Browse the repository at this point in the history
  • Loading branch information
wocjf0513 authored Dec 15, 2023
2 parents fb4b2d5 + 3bbd461 commit 92f06c8
Show file tree
Hide file tree
Showing 39 changed files with 392 additions and 275 deletions.
2 changes: 1 addition & 1 deletion src/docs/asciidoc/cart/cart-api.adoc
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ ifndef::snippets[]
:snippets: build/generated-snippets
endif::[]

= Member REST API Docs
= Cart REST API Docs
:doctype: book
:icons: font
:source-highlighter: highlightjs
Expand Down
12 changes: 11 additions & 1 deletion src/docs/asciidoc/index.adoc
Original file line number Diff line number Diff line change
Expand Up @@ -11,10 +11,20 @@

=== link:member/member-api.html[회원 API, window=blank]

=== link:product/product-api.html[상품 API, window=blank]
=== link:product/product-api.html[숙소 API, window=blank]

=== link:room/room-api.html[객실 API, window=blank]

=== link:cart/cart-api.html[장바구니 API, window=blank]

=== link:reservationproduct/reservation-product-api.html[예약 상품 API, window=blank]

=== link:reservation/reservation-api.html[예약 API, window=blank]

=== link:star/star-api.html[별점 API, window=blank]

=== link:favorite/favorite-api.html[즐겨찾기 API, window=blank]


== API Common Response

Expand Down
2 changes: 1 addition & 1 deletion src/docs/asciidoc/product/product-api.adoc
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ ifndef::snippets[]
:snippets: build/generated-snippets
endif::[]

= Member REST API Docs
= Product REST API Docs
:doctype: book
:icons: font
:source-highlighter: highlightjs
Expand Down
25 changes: 25 additions & 0 deletions src/docs/asciidoc/room/room-api.adoc
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
ifndef::snippets[]
:snippets: build/generated-snippets
endif::[]

= Room REST API Docs
:doctype: book
:icons: font
:source-highlighter: highlightjs
:toc: left
:toclevels: 2

[[Get-Rooms-With-Product-Info]]
== 숙박 정보를 포함한 객실 정보 리스트 조회

숙박 정보를 포함한 객실 정보 리스트 조회 API 입니다. (주문 페이지에서 필요한 조회)

=== HttpRequest

include::{snippets}/room-rest-controller-docs-test/get-rooms-with-product-info/http-request.adoc[]
include::{snippets}/room-rest-controller-docs-test/get-rooms-with-product-info/query-parameters.adoc[]

=== HttpResponse

include::{snippets}/room-rest-controller-docs-test/get-rooms-with-product-info/http-response.adoc[]
include::{snippets}/room-rest-controller-docs-test/get-rooms-with-product-info/response-fields.adoc[]
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
package com.fc.shimpyo_be.domain.reservation.constant;

import lombok.AccessLevel;
import lombok.NoArgsConstructor;

@NoArgsConstructor(access = AccessLevel.PRIVATE)
public class ReservationValidationConstants {

// regex
public static final String DATE_REGEX = "^\\d{4}-\\d{2}-\\d{2}$";
public static final int RESERVATION_REQ_MIN_SIZE = 1;
public static final int RESERVATION_REQ_MAX_SIZE = 3;
public static final int TOTAL_PRICE_MIN_VALUE = 0;

// validation message
public static final String DATE_PATTERN_MESSAGE = "올바른 날짜 형식이 아닙니다.(yyyy-MM-dd 형식으로 입력하세요.)";
public static final String RESERVATION_REQ_SIZE_MESSAGE = "최소 1개, 최대 3개의 객실 예약이 가능합니다.";
public static final String PAYMETHOD_NOTNULL_MESSAGE = "null 일 수 없습니다. 정해진 결제 수단에서 선택하세요.";
public static final String TOTAL_PRICE_MIN_MESSAGE = "총 결제 금액은 최소 0원 이상이어야 합니다.";
}
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@
import com.fc.shimpyo_be.domain.reservation.dto.request.PreoccupyRoomsRequestDto;
import com.fc.shimpyo_be.domain.reservation.dto.request.ReleaseRoomsRequestDto;
import com.fc.shimpyo_be.domain.reservation.dto.request.SaveReservationRequestDto;
import com.fc.shimpyo_be.domain.reservation.dto.response.ReservationInfoResponseDto;
import com.fc.shimpyo_be.domain.reservation.dto.response.SaveReservationResponseDto;
import com.fc.shimpyo_be.domain.reservation.dto.response.ValidatePreoccupyResultResponseDto;
import com.fc.shimpyo_be.domain.reservation.facade.PreoccupyRoomsLockFacade;
Expand Down Expand Up @@ -31,12 +32,14 @@ public class ReservationRestController {
private final PreoccupyRoomsLockFacade preoccupyRoomsLockFacade;
private final ReservationLockFacade reservationLockFacade;
private final SecurityUtil securityUtil;
private static final int PAGE_SIZE = 10;
private static final int PAGE_NUM = 0;
private static final String PAGE_SORT_BY = "id";

@PostMapping
public ResponseEntity<ResponseDto<SaveReservationResponseDto>> saveReservation(
@Valid @RequestBody SaveReservationRequestDto request
) {
log.debug("[api][POST] /api/reservations");

return ResponseEntity
.status(HttpStatus.CREATED)
Expand All @@ -50,10 +53,9 @@ public ResponseEntity<ResponseDto<SaveReservationResponseDto>> saveReservation(
}

@GetMapping
public ResponseEntity<ResponseDto<Page<?>>> getReservationList(
@PageableDefault(size = 10, page = 0, sort = "id", direction = Sort.Direction.DESC) Pageable pageable
public ResponseEntity<ResponseDto<Page<ReservationInfoResponseDto>>> getReservationList(
@PageableDefault(size = PAGE_SIZE, page = PAGE_NUM, sort = PAGE_SORT_BY, direction = Sort.Direction.DESC) Pageable pageable
) {
log.debug("[api][GET] /api/reservations");

return ResponseEntity
.status(HttpStatus.OK)
Expand All @@ -70,7 +72,6 @@ public ResponseEntity<ResponseDto<Page<?>>> getReservationList(
public ResponseEntity<ResponseDto<ValidatePreoccupyResultResponseDto>> checkAvailableAndPreoccupy(
@Valid @RequestBody PreoccupyRoomsRequestDto request
) {
log.debug("[api][POST] /api/reservations/preoccupy");

return ResponseEntity
.status(HttpStatus.OK)
Expand All @@ -87,7 +88,6 @@ public ResponseEntity<ResponseDto<ValidatePreoccupyResultResponseDto>> checkAvai
public ResponseEntity<ResponseDto<Void>> releaseRooms(
@Valid @RequestBody ReleaseRoomsRequestDto request
) {
log.debug("[api][POST] /api/reservations/release");

reservationService.releaseRooms(securityUtil.getCurrentMemberId(), request);

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,15 +4,17 @@
import jakarta.validation.constraints.Pattern;
import lombok.Builder;

import static com.fc.shimpyo_be.domain.reservation.constant.ReservationValidationConstants.*;

@Builder
public record PreoccupyRoomItemRequestDto(
@NotNull
Long cartId,
@NotNull
Long roomCode,
@Pattern(regexp = "^\\d{4}-\\d{2}-\\d{2}$", message = "올바른 날짜 형식이 아닙니다.(yyyy-MM-dd 형식으로 입력하세요.)")
@Pattern(regexp = DATE_REGEX, message = DATE_PATTERN_MESSAGE)
String startDate,
@Pattern(regexp = "^\\d{4}-\\d{2}-\\d{2}$", message = "올바른 날짜 형식이 아닙니다.(yyyy-MM-dd 형식으로 입력하세요.)")
@Pattern(regexp = DATE_REGEX, message = DATE_PATTERN_MESSAGE)
String endDate
) {
}
Original file line number Diff line number Diff line change
Expand Up @@ -6,11 +6,12 @@

import java.util.List;

import static com.fc.shimpyo_be.domain.reservation.constant.ReservationValidationConstants.*;

@Builder
public record PreoccupyRoomsRequestDto(

@Valid
@Size(min = 1, max = 3, message = "최소 1개, 최대 3개의 객실 예약이 가능합니다.")
@Size(min = RESERVATION_REQ_MIN_SIZE, max = RESERVATION_REQ_MAX_SIZE, message = RESERVATION_REQ_SIZE_MESSAGE)
List<PreoccupyRoomItemRequestDto> rooms
) {
}
Original file line number Diff line number Diff line change
Expand Up @@ -4,13 +4,15 @@
import jakarta.validation.constraints.Pattern;
import lombok.Builder;

import static com.fc.shimpyo_be.domain.reservation.constant.ReservationValidationConstants.*;

@Builder
public record ReleaseRoomItemRequestDto(
@NotNull
Long roomId,
@Pattern(regexp = "^\\d{4}-\\d{2}-\\d{2}$", message = "올바른 날짜 형식이 아닙니다.(yyyy-MM-dd 형식으로 입력하세요.)")
@Pattern(regexp = DATE_REGEX, message = DATE_PATTERN_MESSAGE)
String startDate,
@Pattern(regexp = "^\\d{4}-\\d{2}-\\d{2}$", message = "올바른 날짜 형식이 아닙니다.(yyyy-MM-dd 형식으로 입력하세요.)")
@Pattern(regexp = DATE_REGEX, message = DATE_PATTERN_MESSAGE)
String endDate
) {
}
Original file line number Diff line number Diff line change
Expand Up @@ -6,10 +6,12 @@

import java.util.List;

import static com.fc.shimpyo_be.domain.reservation.constant.ReservationValidationConstants.*;

@Builder
public record ReleaseRoomsRequestDto(
@Valid
@Size(min = 1, max = 3, message = "최소 1개, 최대 3개의 객실 요청 정보가 필요합니다.")
@Size(min = RESERVATION_REQ_MIN_SIZE, max = RESERVATION_REQ_MAX_SIZE, message = RESERVATION_REQ_SIZE_MESSAGE)
List<ReleaseRoomItemRequestDto> rooms
) {
}
Original file line number Diff line number Diff line change
Expand Up @@ -10,14 +10,16 @@

import java.util.List;

import static com.fc.shimpyo_be.domain.reservation.constant.ReservationValidationConstants.*;

@Builder
public record SaveReservationRequestDto(
@Valid
@Size(min = 1, max = 3, message = "최소 1개, 최대 3개의 객실 예약이 가능합니다.")
@Size(min = RESERVATION_REQ_MIN_SIZE, max = RESERVATION_REQ_MAX_SIZE, message = RESERVATION_REQ_SIZE_MESSAGE)
List<ReservationProductRequestDto> reservationProducts,
@NotNull(message = "null 일 수 없습니다. 정해진 결제 수단에서 선택하세요.")
@NotNull(message = PAYMETHOD_NOTNULL_MESSAGE)
PayMethod payMethod,
@Min(value = 0, message = "총 결제 금액은 음수일 수 없습니다.")
@Min(value = TOTAL_PRICE_MIN_VALUE, message = TOTAL_PRICE_MIN_MESSAGE)
Integer totalPrice
) {
}
Original file line number Diff line number Diff line change
Expand Up @@ -39,7 +39,7 @@ public class Reservation extends BaseTimeEntity {
private List<ReservationProduct> reservationProducts = new ArrayList<>();

@Builder
public Reservation(
private Reservation(
Long id,
Member member,
PayMethod payMethod,
Expand Down

This file was deleted.

Original file line number Diff line number Diff line change
Expand Up @@ -38,7 +38,6 @@ public ValidatePreoccupyResultResponseDto checkAvailableAndPreoccupy(Long member
CheckAvailableRoomsResultDto resultDto = preoccupyRoomsService.checkAvailable(memberId, request);

if(!resultDto.isAvailable()) {
log.debug("[{}][check available rooms result] isAvailable = {}, results = {}", currentWorker, false, resultDto.roomResults());
throw new PreoccupyNotAvailableException(
ValidatePreoccupyResultResponseDto.builder()
.isAvailable(false)
Expand All @@ -47,8 +46,6 @@ public ValidatePreoccupyResultResponseDto checkAvailableAndPreoccupy(Long member
);
}

log.debug("[{}][check available rooms result] isAvailable = {}, results = {}", currentWorker, true, resultDto.roomResults());
log.debug("[{}][check available rooms result] preoccupyMap = {}", currentWorker, resultDto.preoccupyMap());
preoccupyRoomsService.preoccupy(resultDto);

return ValidatePreoccupyResultResponseDto.builder()
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,7 @@ public SaveReservationResponseDto saveReservation(Long memberId, SaveReservation
String currentWorker = Thread.currentThread().getName();

try {
boolean isLocked = lock.tryLock(2, 4, TimeUnit.SECONDS);
boolean isLocked = lock.tryLock(3, 5, TimeUnit.SECONDS);

if(!isLocked) {
log.error("[{}] 예약 lock 획득 실패", currentWorker);
Expand All @@ -38,8 +38,6 @@ public SaveReservationResponseDto saveReservation(Long memberId, SaveReservation
ValidateReservationResultDto resultDto = reservationService.validate(memberId, request.reservationProducts());

if(!resultDto.isAvailable()) {
log.debug("[{}][validate rooms result] isAvailable = {}, unavailableIds = {}", currentWorker, false, resultDto.unavailableIds());

throw new ReserveNotAvailableException(
ValidateReservationResultResponseDto.builder()
.isAvailable(false)
Expand All @@ -48,8 +46,6 @@ public SaveReservationResponseDto saveReservation(Long memberId, SaveReservation
);
}

log.debug("[{}][validate rooms result] isAvailable = {}, unavailableIds = {}", currentWorker, true, resultDto.unavailableIds());

return reservationService.saveReservation(memberId, request, resultDto.confirmMap());

} catch (InterruptedException exception) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -60,7 +60,6 @@ public CheckAvailableRoomsResultDto checkAvailable(Long memberId, PreoccupyRooms
String key = String.format(PREOCCUPY_REDIS_KEY_FORMAT, roomId, targetDate);
Object value = opsForValue.get(key);

log.info("roomId: {}, targetDate: {}, value: {}", roomId, targetDate, value);
if(Objects.nonNull(value)) {
dateCheck = false;
preoccupyMap.remove(roomId);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,6 @@
import com.fc.shimpyo_be.domain.cart.service.CartService;
import com.fc.shimpyo_be.domain.member.entity.Member;
import com.fc.shimpyo_be.domain.member.service.MemberService;
import com.fc.shimpyo_be.domain.product.exception.RoomNotFoundException;
import com.fc.shimpyo_be.domain.reservation.dto.ValidateReservationResultDto;
import com.fc.shimpyo_be.domain.reservation.dto.request.ReleaseRoomItemRequestDto;
import com.fc.shimpyo_be.domain.reservation.dto.request.ReleaseRoomsRequestDto;
Expand All @@ -12,12 +11,12 @@
import com.fc.shimpyo_be.domain.reservation.dto.response.SaveReservationResponseDto;
import com.fc.shimpyo_be.domain.reservation.entity.Reservation;
import com.fc.shimpyo_be.domain.reservation.repository.ReservationRepository;
import com.fc.shimpyo_be.domain.reservation.util.ReservationMapper;
import com.fc.shimpyo_be.domain.reservation.util.mapper.ReservationMapper;
import com.fc.shimpyo_be.domain.reservationproduct.dto.request.ReservationProductRequestDto;
import com.fc.shimpyo_be.domain.reservationproduct.entity.ReservationProduct;
import com.fc.shimpyo_be.domain.reservationproduct.repository.ReservationProductRepository;
import com.fc.shimpyo_be.domain.room.entity.Room;
import com.fc.shimpyo_be.domain.room.repository.RoomRepository;
import com.fc.shimpyo_be.domain.room.service.RoomService;
import com.fc.shimpyo_be.global.util.DateTimeUtil;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
Expand All @@ -41,7 +40,7 @@ public class ReservationService {
private final ReservationRepository reservationRepository;
private final ReservationProductRepository reservationProductRepository;
private final MemberService memberService;
private final RoomRepository roomRepository;
private final RoomService roomService;
private final CartService cartService;
private final RedisTemplate<String, Object> redisTemplate;
private static final String REDIS_ROOM_KEY_FORMAT = "roomId:%d:%s";
Expand All @@ -50,7 +49,6 @@ public class ReservationService {
public SaveReservationResponseDto saveReservation(
Long memberId, SaveReservationRequestDto request, Map<Long, List<String>> reservationMap
) {
log.debug("{} ::: {}", getClass().getSimpleName(), "saveReservation");

// 회원 엔티티 조회
Member member = memberService.getMemberById(memberId);
Expand All @@ -59,8 +57,7 @@ public SaveReservationResponseDto saveReservation(
List<ReservationProduct> reservationProducts = new ArrayList<>();
for (ReservationProductRequestDto reservationProductDto : request.reservationProducts()) {

Room room = roomRepository.findById(reservationProductDto.roomId())
.orElseThrow(RoomNotFoundException::new);
Room room = roomService.getRoomById(reservationProductDto.roomId());

// 장바구니 아이템 삭제
if (reservationProductDto.cartId() > 0) {
Expand Down Expand Up @@ -96,7 +93,6 @@ public SaveReservationResponseDto saveReservation(

@Transactional(readOnly = true)
public Page<ReservationInfoResponseDto> getReservationInfoList(Long memberId, Pageable pageable) {
log.debug("{} ::: {}", getClass().getSimpleName(), "getReservationInfoList");

List<Long> reservationIds = reservationRepository.findIdsByMemberId(memberId);

Expand All @@ -106,7 +102,6 @@ public Page<ReservationInfoResponseDto> getReservationInfoList(Long memberId, Pa
}

public ValidateReservationResultDto validate(Long memberId, List<ReservationProductRequestDto> reservationProducts) {
log.debug("{} ::: {}", getClass().getSimpleName(), "validate");

ValueOperations<String, Object> opsForValue = redisTemplate.opsForValue();

Expand Down Expand Up @@ -155,7 +150,6 @@ public ValidateReservationResultDto validate(Long memberId, List<ReservationProd
}

public void releaseRooms(Long memberId, ReleaseRoomsRequestDto request) {
log.debug("{} ::: {}", getClass().getSimpleName(), "releaseRooms");

String memberIdValue = String.valueOf(memberId);
ValueOperations<String, Object> opsForValue = redisTemplate.opsForValue();
Expand All @@ -180,7 +174,6 @@ public void releaseRooms(Long memberId, ReleaseRoomsRequestDto request) {
}

private void confirmReservationProduct(List<String> reservationKeys, String endDate) {
log.debug("{} ::: {}", getClass().getSimpleName(), "confirmReservationProduct");

Date expireDate = convertLocalDateToDate(DateTimeUtil.toLocalDate(endDate));
for (String key : reservationKeys) {
Expand Down
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
package com.fc.shimpyo_be.domain.reservation.util;
package com.fc.shimpyo_be.domain.reservation.util.mapper;

import com.fc.shimpyo_be.domain.product.entity.Product;
import com.fc.shimpyo_be.domain.reservation.dto.response.ReservationInfoResponseDto;
Expand Down
Loading

0 comments on commit 92f06c8

Please sign in to comment.