From 6d00d9c5e30321668d82477c1fe613117ac5cc13 Mon Sep 17 00:00:00 2001 From: seminchoi Date: Wed, 21 Aug 2024 10:30:44 +0900 Subject: [PATCH 01/13] =?UTF-8?q?feat:=20=EA=B2=B0=EC=A0=9C=20=EC=99=84?= =?UTF-8?q?=EB=A3=8C=20=ED=9B=84=20=EC=9D=B4=EB=B2=A4=ED=8A=B8=20=EB=B0=9C?= =?UTF-8?q?=ED=96=89=ED=95=98=EB=8F=84=EB=A1=9D=20=EA=B8=B0=EB=8A=A5=20?= =?UTF-8?q?=EA=B5=AC=ED=98=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../ticket/controller/TicketController.java | 6 +++--- .../domain/ticket/dto/event/PaymentEvent.java | 10 ++++++++++ .../{ => request}/SeatSelectionRequest.java | 2 +- .../{ => request}/TicketPaymentRequest.java | 2 +- .../dto/{ => response}/TicketElement.java | 2 +- .../ticket/service/ReservationService.java | 4 ++-- .../ReservationTransactionService.java | 19 ++++++++++++++----- .../domain/ticket/service/TicketService.java | 2 +- .../proxy/LettuceReservationServiceProxy.java | 4 ++-- .../OptimisticReservationServiceProxy.java | 4 ++-- .../PessimisticReservationServiceProxy.java | 4 ++-- .../RedissonReservationServiceProxy.java | 4 ++-- .../ticket/service/CacheReservationTest.java | 2 +- .../service/PersistenceReservationTest.java | 4 ++-- 14 files changed, 44 insertions(+), 25 deletions(-) create mode 100644 src/main/java/com/thirdparty/ticketing/domain/ticket/dto/event/PaymentEvent.java rename src/main/java/com/thirdparty/ticketing/domain/ticket/dto/{ => request}/SeatSelectionRequest.java (84%) rename src/main/java/com/thirdparty/ticketing/domain/ticket/dto/{ => request}/TicketPaymentRequest.java (84%) rename src/main/java/com/thirdparty/ticketing/domain/ticket/dto/{ => response}/TicketElement.java (83%) diff --git a/src/main/java/com/thirdparty/ticketing/domain/ticket/controller/TicketController.java b/src/main/java/com/thirdparty/ticketing/domain/ticket/controller/TicketController.java index 9e2878e1..60d10f16 100644 --- a/src/main/java/com/thirdparty/ticketing/domain/ticket/controller/TicketController.java +++ b/src/main/java/com/thirdparty/ticketing/domain/ticket/controller/TicketController.java @@ -9,9 +9,9 @@ import com.thirdparty.ticketing.domain.ItemResult; import com.thirdparty.ticketing.domain.common.LoginMember; -import com.thirdparty.ticketing.domain.ticket.dto.SeatSelectionRequest; -import com.thirdparty.ticketing.domain.ticket.dto.TicketElement; -import com.thirdparty.ticketing.domain.ticket.dto.TicketPaymentRequest; +import com.thirdparty.ticketing.domain.ticket.dto.request.SeatSelectionRequest; +import com.thirdparty.ticketing.domain.ticket.dto.request.TicketPaymentRequest; +import com.thirdparty.ticketing.domain.ticket.dto.response.TicketElement; import com.thirdparty.ticketing.domain.ticket.service.ReservationService; import com.thirdparty.ticketing.domain.ticket.service.TicketService; diff --git a/src/main/java/com/thirdparty/ticketing/domain/ticket/dto/event/PaymentEvent.java b/src/main/java/com/thirdparty/ticketing/domain/ticket/dto/event/PaymentEvent.java new file mode 100644 index 00000000..74a76ce2 --- /dev/null +++ b/src/main/java/com/thirdparty/ticketing/domain/ticket/dto/event/PaymentEvent.java @@ -0,0 +1,10 @@ +package com.thirdparty.ticketing.domain.ticket.dto.event; + +import com.thirdparty.ticketing.domain.common.Event; + +import lombok.Data; + +@Data +public class PaymentEvent implements Event { + private final String email; +} diff --git a/src/main/java/com/thirdparty/ticketing/domain/ticket/dto/SeatSelectionRequest.java b/src/main/java/com/thirdparty/ticketing/domain/ticket/dto/request/SeatSelectionRequest.java similarity index 84% rename from src/main/java/com/thirdparty/ticketing/domain/ticket/dto/SeatSelectionRequest.java rename to src/main/java/com/thirdparty/ticketing/domain/ticket/dto/request/SeatSelectionRequest.java index c4f6e2ce..cc8fe8bc 100644 --- a/src/main/java/com/thirdparty/ticketing/domain/ticket/dto/SeatSelectionRequest.java +++ b/src/main/java/com/thirdparty/ticketing/domain/ticket/dto/request/SeatSelectionRequest.java @@ -1,4 +1,4 @@ -package com.thirdparty.ticketing.domain.ticket.dto; +package com.thirdparty.ticketing.domain.ticket.dto.request; import jakarta.validation.constraints.Min; import jakarta.validation.constraints.NotNull; diff --git a/src/main/java/com/thirdparty/ticketing/domain/ticket/dto/TicketPaymentRequest.java b/src/main/java/com/thirdparty/ticketing/domain/ticket/dto/request/TicketPaymentRequest.java similarity index 84% rename from src/main/java/com/thirdparty/ticketing/domain/ticket/dto/TicketPaymentRequest.java rename to src/main/java/com/thirdparty/ticketing/domain/ticket/dto/request/TicketPaymentRequest.java index b812c0e0..b4dfbdf5 100644 --- a/src/main/java/com/thirdparty/ticketing/domain/ticket/dto/TicketPaymentRequest.java +++ b/src/main/java/com/thirdparty/ticketing/domain/ticket/dto/request/TicketPaymentRequest.java @@ -1,4 +1,4 @@ -package com.thirdparty.ticketing.domain.ticket.dto; +package com.thirdparty.ticketing.domain.ticket.dto.request; import jakarta.validation.constraints.Min; import jakarta.validation.constraints.NotNull; diff --git a/src/main/java/com/thirdparty/ticketing/domain/ticket/dto/TicketElement.java b/src/main/java/com/thirdparty/ticketing/domain/ticket/dto/response/TicketElement.java similarity index 83% rename from src/main/java/com/thirdparty/ticketing/domain/ticket/dto/TicketElement.java rename to src/main/java/com/thirdparty/ticketing/domain/ticket/dto/response/TicketElement.java index 085c03e6..741438ca 100644 --- a/src/main/java/com/thirdparty/ticketing/domain/ticket/dto/TicketElement.java +++ b/src/main/java/com/thirdparty/ticketing/domain/ticket/dto/response/TicketElement.java @@ -1,4 +1,4 @@ -package com.thirdparty.ticketing.domain.ticket.dto; +package com.thirdparty.ticketing.domain.ticket.dto.response; import java.util.UUID; diff --git a/src/main/java/com/thirdparty/ticketing/domain/ticket/service/ReservationService.java b/src/main/java/com/thirdparty/ticketing/domain/ticket/service/ReservationService.java index 3067e4f5..1b9ba7c3 100644 --- a/src/main/java/com/thirdparty/ticketing/domain/ticket/service/ReservationService.java +++ b/src/main/java/com/thirdparty/ticketing/domain/ticket/service/ReservationService.java @@ -1,7 +1,7 @@ package com.thirdparty.ticketing.domain.ticket.service; -import com.thirdparty.ticketing.domain.ticket.dto.SeatSelectionRequest; -import com.thirdparty.ticketing.domain.ticket.dto.TicketPaymentRequest; +import com.thirdparty.ticketing.domain.ticket.dto.request.SeatSelectionRequest; +import com.thirdparty.ticketing.domain.ticket.dto.request.TicketPaymentRequest; public interface ReservationService { void selectSeat(String memberEmail, SeatSelectionRequest seatSelectionRequest); diff --git a/src/main/java/com/thirdparty/ticketing/domain/ticket/service/ReservationTransactionService.java b/src/main/java/com/thirdparty/ticketing/domain/ticket/service/ReservationTransactionService.java index e4eb007b..5f7db413 100644 --- a/src/main/java/com/thirdparty/ticketing/domain/ticket/service/ReservationTransactionService.java +++ b/src/main/java/com/thirdparty/ticketing/domain/ticket/service/ReservationTransactionService.java @@ -3,14 +3,16 @@ import org.springframework.transaction.annotation.Transactional; import com.thirdparty.ticketing.domain.common.ErrorCode; +import com.thirdparty.ticketing.domain.common.EventPublisher; import com.thirdparty.ticketing.domain.common.TicketingException; import com.thirdparty.ticketing.domain.member.Member; import com.thirdparty.ticketing.domain.member.repository.MemberRepository; import com.thirdparty.ticketing.domain.payment.PaymentProcessor; import com.thirdparty.ticketing.domain.payment.dto.PaymentRequest; import com.thirdparty.ticketing.domain.seat.Seat; -import com.thirdparty.ticketing.domain.ticket.dto.SeatSelectionRequest; -import com.thirdparty.ticketing.domain.ticket.dto.TicketPaymentRequest; +import com.thirdparty.ticketing.domain.ticket.dto.event.PaymentEvent; +import com.thirdparty.ticketing.domain.ticket.dto.request.SeatSelectionRequest; +import com.thirdparty.ticketing.domain.ticket.dto.request.TicketPaymentRequest; import com.thirdparty.ticketing.domain.ticket.service.strategy.LockSeatStrategy; import lombok.RequiredArgsConstructor; @@ -22,6 +24,7 @@ public class ReservationTransactionService implements ReservationService { private final MemberRepository memberRepository; private final PaymentProcessor paymentProcessor; private final LockSeatStrategy lockSeatStrategy; + private final EventPublisher eventPublisher; @Override @Transactional @@ -55,12 +58,18 @@ public void reservationTicket(String memberEmail, TicketPaymentRequest ticketPay .findByEmail(memberEmail) .orElseThrow(() -> new TicketingException(ErrorCode.NOT_FOUND_MEMBER)); - seat.markAsPendingPayment(); - paymentProcessor.processPayment(new PaymentRequest()); - seat.markAsPaid(); + processPayment(seat, loginMember); if (seat.isAssignedByMember(loginMember)) { throw new TicketingException(ErrorCode.NOT_SELECTABLE_SEAT); } } + + private void processPayment(Seat seat, Member loginMember) { + seat.markAsPendingPayment(); + paymentProcessor.processPayment(new PaymentRequest()); + seat.markAsPaid(); + PaymentEvent paymentEvent = new PaymentEvent(loginMember.getEmail()); + eventPublisher.publish(paymentEvent); + } } diff --git a/src/main/java/com/thirdparty/ticketing/domain/ticket/service/TicketService.java b/src/main/java/com/thirdparty/ticketing/domain/ticket/service/TicketService.java index 4c5ae0a7..73e46b83 100644 --- a/src/main/java/com/thirdparty/ticketing/domain/ticket/service/TicketService.java +++ b/src/main/java/com/thirdparty/ticketing/domain/ticket/service/TicketService.java @@ -9,7 +9,7 @@ import com.thirdparty.ticketing.domain.common.TicketingException; import com.thirdparty.ticketing.domain.member.Member; import com.thirdparty.ticketing.domain.member.repository.MemberRepository; -import com.thirdparty.ticketing.domain.ticket.dto.TicketElement; +import com.thirdparty.ticketing.domain.ticket.dto.response.TicketElement; import com.thirdparty.ticketing.domain.ticket.repository.TicketRepository; import lombok.RequiredArgsConstructor; diff --git a/src/main/java/com/thirdparty/ticketing/domain/ticket/service/proxy/LettuceReservationServiceProxy.java b/src/main/java/com/thirdparty/ticketing/domain/ticket/service/proxy/LettuceReservationServiceProxy.java index 1e49501b..59582937 100644 --- a/src/main/java/com/thirdparty/ticketing/domain/ticket/service/proxy/LettuceReservationServiceProxy.java +++ b/src/main/java/com/thirdparty/ticketing/domain/ticket/service/proxy/LettuceReservationServiceProxy.java @@ -3,8 +3,8 @@ import com.thirdparty.ticketing.domain.common.ErrorCode; import com.thirdparty.ticketing.domain.common.LettuceRepository; import com.thirdparty.ticketing.domain.common.TicketingException; -import com.thirdparty.ticketing.domain.ticket.dto.SeatSelectionRequest; -import com.thirdparty.ticketing.domain.ticket.dto.TicketPaymentRequest; +import com.thirdparty.ticketing.domain.ticket.dto.request.SeatSelectionRequest; +import com.thirdparty.ticketing.domain.ticket.dto.request.TicketPaymentRequest; import com.thirdparty.ticketing.domain.ticket.service.ReservationTransactionService; import lombok.RequiredArgsConstructor; diff --git a/src/main/java/com/thirdparty/ticketing/domain/ticket/service/proxy/OptimisticReservationServiceProxy.java b/src/main/java/com/thirdparty/ticketing/domain/ticket/service/proxy/OptimisticReservationServiceProxy.java index 0268ac76..af7f245a 100644 --- a/src/main/java/com/thirdparty/ticketing/domain/ticket/service/proxy/OptimisticReservationServiceProxy.java +++ b/src/main/java/com/thirdparty/ticketing/domain/ticket/service/proxy/OptimisticReservationServiceProxy.java @@ -5,8 +5,8 @@ import com.thirdparty.ticketing.domain.common.ErrorCode; import com.thirdparty.ticketing.domain.common.TicketingException; -import com.thirdparty.ticketing.domain.ticket.dto.SeatSelectionRequest; -import com.thirdparty.ticketing.domain.ticket.dto.TicketPaymentRequest; +import com.thirdparty.ticketing.domain.ticket.dto.request.SeatSelectionRequest; +import com.thirdparty.ticketing.domain.ticket.dto.request.TicketPaymentRequest; import com.thirdparty.ticketing.domain.ticket.service.ReservationTransactionService; import lombok.RequiredArgsConstructor; diff --git a/src/main/java/com/thirdparty/ticketing/domain/ticket/service/proxy/PessimisticReservationServiceProxy.java b/src/main/java/com/thirdparty/ticketing/domain/ticket/service/proxy/PessimisticReservationServiceProxy.java index 243ae15f..8d3518d0 100644 --- a/src/main/java/com/thirdparty/ticketing/domain/ticket/service/proxy/PessimisticReservationServiceProxy.java +++ b/src/main/java/com/thirdparty/ticketing/domain/ticket/service/proxy/PessimisticReservationServiceProxy.java @@ -6,8 +6,8 @@ import com.thirdparty.ticketing.domain.common.ErrorCode; import com.thirdparty.ticketing.domain.common.TicketingException; -import com.thirdparty.ticketing.domain.ticket.dto.SeatSelectionRequest; -import com.thirdparty.ticketing.domain.ticket.dto.TicketPaymentRequest; +import com.thirdparty.ticketing.domain.ticket.dto.request.SeatSelectionRequest; +import com.thirdparty.ticketing.domain.ticket.dto.request.TicketPaymentRequest; import com.thirdparty.ticketing.domain.ticket.service.ReservationTransactionService; import lombok.RequiredArgsConstructor; diff --git a/src/main/java/com/thirdparty/ticketing/domain/ticket/service/proxy/RedissonReservationServiceProxy.java b/src/main/java/com/thirdparty/ticketing/domain/ticket/service/proxy/RedissonReservationServiceProxy.java index b1bb4a99..0dfa0c08 100644 --- a/src/main/java/com/thirdparty/ticketing/domain/ticket/service/proxy/RedissonReservationServiceProxy.java +++ b/src/main/java/com/thirdparty/ticketing/domain/ticket/service/proxy/RedissonReservationServiceProxy.java @@ -7,8 +7,8 @@ import com.thirdparty.ticketing.domain.common.ErrorCode; import com.thirdparty.ticketing.domain.common.TicketingException; -import com.thirdparty.ticketing.domain.ticket.dto.SeatSelectionRequest; -import com.thirdparty.ticketing.domain.ticket.dto.TicketPaymentRequest; +import com.thirdparty.ticketing.domain.ticket.dto.request.SeatSelectionRequest; +import com.thirdparty.ticketing.domain.ticket.dto.request.TicketPaymentRequest; import com.thirdparty.ticketing.domain.ticket.service.ReservationTransactionService; import lombok.RequiredArgsConstructor; diff --git a/src/test/java/com/thirdparty/ticketing/domain/ticket/service/CacheReservationTest.java b/src/test/java/com/thirdparty/ticketing/domain/ticket/service/CacheReservationTest.java index 0aa520a8..188f8d21 100644 --- a/src/test/java/com/thirdparty/ticketing/domain/ticket/service/CacheReservationTest.java +++ b/src/test/java/com/thirdparty/ticketing/domain/ticket/service/CacheReservationTest.java @@ -30,7 +30,7 @@ import com.thirdparty.ticketing.domain.seat.SeatStatus; import com.thirdparty.ticketing.domain.seat.repository.SeatGradeRepository; import com.thirdparty.ticketing.domain.seat.repository.SeatRepository; -import com.thirdparty.ticketing.domain.ticket.dto.SeatSelectionRequest; +import com.thirdparty.ticketing.domain.ticket.dto.request.SeatSelectionRequest; import com.thirdparty.ticketing.domain.zone.Zone; import com.thirdparty.ticketing.domain.zone.repository.ZoneRepository; import com.thirdparty.ticketing.support.TestContainerStarter; diff --git a/src/test/java/com/thirdparty/ticketing/domain/ticket/service/PersistenceReservationTest.java b/src/test/java/com/thirdparty/ticketing/domain/ticket/service/PersistenceReservationTest.java index cb7aa724..f184b5f2 100644 --- a/src/test/java/com/thirdparty/ticketing/domain/ticket/service/PersistenceReservationTest.java +++ b/src/test/java/com/thirdparty/ticketing/domain/ticket/service/PersistenceReservationTest.java @@ -26,8 +26,8 @@ import org.springframework.test.context.jdbc.SqlConfig; import com.thirdparty.ticketing.domain.common.TicketingException; -import com.thirdparty.ticketing.domain.ticket.dto.SeatSelectionRequest; -import com.thirdparty.ticketing.domain.ticket.dto.TicketPaymentRequest; +import com.thirdparty.ticketing.domain.ticket.dto.request.SeatSelectionRequest; +import com.thirdparty.ticketing.domain.ticket.dto.request.TicketPaymentRequest; import com.thirdparty.ticketing.support.TestContainerStarter; @SpringBootTest From b96162ad8453986fc7515a4efea6f30d75a7f3eb Mon Sep 17 00:00:00 2001 From: mirageoasis Date: Tue, 20 Aug 2024 20:21:24 +0900 Subject: [PATCH 02/13] =?UTF-8?q?chore:=20prometheus=20=EC=9D=98=EC=A1=B4?= =?UTF-8?q?=EC=84=B1=20=EC=B6=94=EA=B0=80?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- build.gradle | 1 + 1 file changed, 1 insertion(+) diff --git a/build.gradle b/build.gradle index 4208a4c0..ca23869e 100644 --- a/build.gradle +++ b/build.gradle @@ -37,6 +37,7 @@ dependencies { implementation 'org.springframework.boot:spring-boot-starter-web' implementation 'org.springframework.boot:spring-boot-starter-security' implementation 'org.springframework.boot:spring-boot-starter-data-redis' + implementation 'io.micrometer:micrometer-registry-prometheus' // Redisson implementation 'org.redisson:redisson-spring-boot-starter:3.17.6' From 3452c930e89bf65eadb5725ebc2758ec1a35c8c0 Mon Sep 17 00:00:00 2001 From: mirageoasis Date: Tue, 20 Aug 2024 20:21:42 +0900 Subject: [PATCH 03/13] =?UTF-8?q?chore:=20version=20=ED=95=84=EB=93=9C=20?= =?UTF-8?q?=EC=88=98=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- docker/docker-compose.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docker/docker-compose.yml b/docker/docker-compose.yml index d91a162e..3aec8957 100644 --- a/docker/docker-compose.yml +++ b/docker/docker-compose.yml @@ -1,4 +1,4 @@ -/version: '3.8' +version: '3.8' services: mysql: image: mysql:8.0.32 From 9ed2840ac61529767636292bc4c885f1bba91281 Mon Sep 17 00:00:00 2001 From: mirageoasis Date: Tue, 20 Aug 2024 20:42:02 +0900 Subject: [PATCH 04/13] =?UTF-8?q?chore:=20backend-config=20=EC=88=98?= =?UTF-8?q?=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- backend-config | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/backend-config b/backend-config index 4c5331e6..c77fb71d 160000 --- a/backend-config +++ b/backend-config @@ -1 +1 @@ -Subproject commit 4c5331e614055376ff0d1f4a76a78f961858054c +Subproject commit c77fb71d2fdda0ae42928d5f1fd8ee05791756a0 From f19fed2c5caee4354afc2c1cd379b8db592db89b Mon Sep 17 00:00:00 2001 From: lass9436 Date: Wed, 21 Aug 2024 10:45:58 +0900 Subject: [PATCH 05/13] =?UTF-8?q?fix:=20CORS=20=EC=84=A4=EC=A0=95=20?= =?UTF-8?q?=EC=88=98=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../global/config/SecurityConfig.java | 21 +++++++++++-------- 1 file changed, 12 insertions(+), 9 deletions(-) diff --git a/src/main/java/com/thirdparty/ticketing/global/config/SecurityConfig.java b/src/main/java/com/thirdparty/ticketing/global/config/SecurityConfig.java index d32ddfc0..5ee5665a 100644 --- a/src/main/java/com/thirdparty/ticketing/global/config/SecurityConfig.java +++ b/src/main/java/com/thirdparty/ticketing/global/config/SecurityConfig.java @@ -14,8 +14,8 @@ import org.springframework.security.web.SecurityFilterChain; import org.springframework.security.web.authentication.UsernamePasswordAuthenticationFilter; import org.springframework.web.cors.CorsConfiguration; -import org.springframework.web.cors.CorsConfigurationSource; import org.springframework.web.cors.UrlBasedCorsConfigurationSource; +import org.springframework.web.filter.CorsFilter; import com.thirdparty.ticketing.domain.member.MemberRole; import com.thirdparty.ticketing.domain.member.service.JwtProvider; @@ -55,18 +55,21 @@ public SecurityFilterChain filterChain(HttpSecurity http, JwtProvider jwtProvide .addFilterBefore( new AuthenticationFilter(jwtProvider), UsernamePasswordAuthenticationFilter.class) - .cors(cors -> cors.configurationSource(corsConfigurationSource())) .build(); } - private CorsConfigurationSource corsConfigurationSource() { - CorsConfiguration configuration = new CorsConfiguration(); - configuration.setAllowedOrigins(List.of("http://localhost:8080")); - configuration.setAllowedMethods( - List.of("GET", "POST", "PUT", "PATCH", "DELETE", "OPTIONS")); + @Bean + public CorsFilter corsFilter() { + CorsConfiguration config = new CorsConfiguration(); + config.setAllowedOrigins(List.of("http://localhost:3000/")); + config.setAllowedMethods(List.of("GET", "POST", "PUT", "PATCH", "DELETE", "OPTIONS")); + config.setAllowCredentials(true); + config.setAllowedHeaders(List.of("*")); + config.setExposedHeaders(List.of("Authorization")); + config.setMaxAge(3600L); UrlBasedCorsConfigurationSource source = new UrlBasedCorsConfigurationSource(); - source.registerCorsConfiguration("/**", configuration); - return source; + source.registerCorsConfiguration("/**", config); + return new CorsFilter(source); } @Bean From a620e4fce84631d7200516c17f8b17d5f9db7395 Mon Sep 17 00:00:00 2001 From: mirageoasis Date: Tue, 20 Aug 2024 21:15:03 +0900 Subject: [PATCH 06/13] =?UTF-8?q?chore:=20=EB=A1=9C=EC=BB=AC=20=ED=99=98?= =?UTF-8?q?=EA=B2=BD=20=EC=84=A4=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- backend-config | 2 +- docker/docker-compose.yml | 2 +- scripts/local-end.sh | 10 ++++++++++ 3 files changed, 12 insertions(+), 2 deletions(-) create mode 100644 scripts/local-end.sh diff --git a/backend-config b/backend-config index c77fb71d..20885cc2 160000 --- a/backend-config +++ b/backend-config @@ -1 +1 @@ -Subproject commit c77fb71d2fdda0ae42928d5f1fd8ee05791756a0 +Subproject commit 20885cc25e27bd86f571509e4d256b17f90bf88d diff --git a/docker/docker-compose.yml b/docker/docker-compose.yml index 3aec8957..30525d6c 100644 --- a/docker/docker-compose.yml +++ b/docker/docker-compose.yml @@ -6,7 +6,7 @@ services: container_name: mysql environment: MYSQL_ROOT_PASSWORD: root - MYSQL_DATABASE: demo + MYSQL_DATABASE: ticketing ports: - "3306:3306" restart: always diff --git a/scripts/local-end.sh b/scripts/local-end.sh new file mode 100644 index 00000000..66904bd6 --- /dev/null +++ b/scripts/local-end.sh @@ -0,0 +1,10 @@ +#!/bin/bash + +# 현재 스크립트의 디렉토리로 이동 +cd "$(dirname "$0")" + +# Docker Compose 파일이 있는 디렉토리로 이동 +cd ../docker + +# Docker Compose를 사용하여 서비스 종료 +docker-compose -f docker-compose.yml down \ No newline at end of file From 71e6e588d530b108ac87285177225918d33f9287 Mon Sep 17 00:00:00 2001 From: mirageoasis Date: Wed, 21 Aug 2024 10:24:48 +0900 Subject: [PATCH 07/13] =?UTF-8?q?chore:=20=ED=85=8C=EC=8A=A4=ED=8A=B8=20wo?= =?UTF-8?q?rkflow=20=EC=84=A4=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .github/workflows/test.yml | 51 +++++++++++++++++++++++++++++++++++--- 1 file changed, 48 insertions(+), 3 deletions(-) diff --git a/.github/workflows/test.yml b/.github/workflows/test.yml index 66bc167e..1f8f7945 100644 --- a/.github/workflows/test.yml +++ b/.github/workflows/test.yml @@ -1,10 +1,34 @@ -name: unit test on push +name: test on push on: [ pull_request ] jobs: deploy: - name: unit test + name: test runs-on: ubuntu-latest + services: + mysql: + image: mysql:8.0.32 + ports: + - 3306:3306 + env: + MYSQL_ROOT_PASSWORD: root + MYSQL_DATABASE: ticketing + options: >- + --health-cmd "mysqladmin ping -u root -proot" + --health-interval 10s + --health-timeout 5s + --health-retries 5 + + redis: + image: redis:7.0.11 + ports: + - 6379:6379 + options: >- + --health-cmd "redis-cli ping" + --health-interval 10s + --health-timeout 5s + --health-retries 5 + steps: - name: checkout uses: actions/checkout@v3 @@ -18,7 +42,28 @@ jobs: distribution: 'temurin' java-version: '17' + - name: Set /etc/hosts for MySQL and Redis + run: | + echo "127.0.0.1 mysql" | sudo tee -a /etc/hosts + echo "127.0.0.1 redis" | sudo tee -a /etc/hosts + + - name: Wait for MySQL to be ready + run: | + until mysqladmin ping -h mysql -u root -proot --silent; do + echo 'waiting for mysql...' + sleep 5 + done + + - name: Wait for Redis to be ready + run: | + until nc -zv redis 6379; do + echo 'waiting for redis...' + sleep 5 + done + + - name: Build with Gradle run: | chmod +x ./gradlew - ./gradlew --info test + ./gradlew copyYml + ./gradlew test From f5be0cba1733d432b4a20ed1f72c477f009e9dc5 Mon Sep 17 00:00:00 2001 From: mirageoasis Date: Wed, 21 Aug 2024 11:21:27 +0900 Subject: [PATCH 08/13] =?UTF-8?q?chore:=20copyYml=20=EC=88=98=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- build.gradle | 9 +-------- 1 file changed, 1 insertion(+), 8 deletions(-) diff --git a/build.gradle b/build.gradle index ca23869e..455af41a 100644 --- a/build.gradle +++ b/build.gradle @@ -61,6 +61,7 @@ dependencies { testImplementation 'org.springframework.restdocs:spring-restdocs-mockmvc' asciidoctorExt 'org.springframework.restdocs:spring-restdocs-asciidoctor' testImplementation "org.testcontainers:testcontainers:1.20.1" + testImplementation 'org.testcontainers:mysql:1.20.1' testImplementation 'org.testcontainers:junit-jupiter:1.20.1' } @@ -110,14 +111,6 @@ tasks.register('copyYml') { } into("src/main/resources") } - - copy { - duplicatesStrategy = dupStr - from(src) { - include(fileExt) - } - into("src/test/resources") - } } build { From 09cfeadb6eb210f7096f5b7f114e84abc3d219df Mon Sep 17 00:00:00 2001 From: mirageoasis Date: Wed, 21 Aug 2024 11:21:50 +0900 Subject: [PATCH 09/13] =?UTF-8?q?chore:=20test=20=EC=95=84=EB=9E=98?= =?UTF-8?q?=EC=97=90=20=EC=9E=88=EB=8A=94=20yml=20=ED=8C=8C=EC=9D=BC=20?= =?UTF-8?q?=EC=9D=B8=EC=8B=9D=20=EB=90=98=EA=B2=8C=20=EB=B3=80=EA=B2=BD?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .gitignore | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.gitignore b/.gitignore index d3a1b168..272d24af 100644 --- a/.gitignore +++ b/.gitignore @@ -17,7 +17,7 @@ bin/ !**/src/main/**/bin/ !**/src/test/**/bin/ # src 아래 yml파일 잠금 -**/src/**/*.yml +**/src/main/**/*.yml backend-config/*.yml ### IntelliJ IDEA ### From b57498b25f5f21e3deb25a2fbd494fee597c3bf8 Mon Sep 17 00:00:00 2001 From: mirageoasis Date: Wed, 21 Aug 2024 11:23:37 +0900 Subject: [PATCH 10/13] =?UTF-8?q?chore:=20=ED=85=8C=EC=8A=A4=ED=8A=B8=20?= =?UTF-8?q?=EC=BB=A8=ED=85=8C=EC=9D=B4=EB=84=88=20=EC=88=98=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../support/TestContainerStarter.java | 25 ++++++++++++++++++- src/test/resources/application.yml | 18 +++++++++++++ 2 files changed, 42 insertions(+), 1 deletion(-) create mode 100644 src/test/resources/application.yml diff --git a/src/test/java/com/thirdparty/ticketing/support/TestContainerStarter.java b/src/test/java/com/thirdparty/ticketing/support/TestContainerStarter.java index d71aff86..a36927d5 100644 --- a/src/test/java/com/thirdparty/ticketing/support/TestContainerStarter.java +++ b/src/test/java/com/thirdparty/ticketing/support/TestContainerStarter.java @@ -3,6 +3,7 @@ import org.springframework.test.context.DynamicPropertyRegistry; import org.springframework.test.context.DynamicPropertySource; import org.testcontainers.containers.GenericContainer; +import org.testcontainers.containers.MySQLContainer; import org.testcontainers.junit.jupiter.Testcontainers; @Testcontainers @@ -12,14 +13,36 @@ public class TestContainerStarter { private static final int REDIS_PORT = 6379; private static final GenericContainer REDIS; + private static final String MYSQL_IMAGE = "mysql:8.0.32"; + private static final int MYSQL_PORT = 3306; + private static final MySQLContainer MYSQL; + static { REDIS = new GenericContainer<>(REDIS_IMAGE).withExposedPorts(REDIS_PORT).withReuse(true); REDIS.start(); + + MYSQL = + new MySQLContainer<>(MYSQL_IMAGE) + .withExposedPorts(MYSQL_PORT) + .withUsername("root") + .withPassword("root") + .withDatabaseName("ticketing") + .withReuse(false); + MYSQL.start(); } @DynamicPropertySource - private static void registerRedisProperties(DynamicPropertyRegistry registry) { + private static void registerProperties(DynamicPropertyRegistry registry) { registry.add("spring.data.redis.host", REDIS::getHost); registry.add("spring.data.redis.port", () -> REDIS.getMappedPort(REDIS_PORT).toString()); + + String mysqlUrl = + String.format( + "jdbc:mysql://%s:%s/ticketing", + MYSQL.getHost(), MYSQL.getMappedPort(MYSQL_PORT)); + + registry.add("spring.datasource.url", () -> mysqlUrl); + registry.add("spring.datasource.username", () -> "root"); + registry.add("spring.datasource.password", () -> "root"); } } diff --git a/src/test/resources/application.yml b/src/test/resources/application.yml new file mode 100644 index 00000000..012371a2 --- /dev/null +++ b/src/test/resources/application.yml @@ -0,0 +1,18 @@ +spring: + data: + redis: + host: localhost + port: 6379 + datasource: + url: jdbc:mysql://localhost:3306/ticketing + username: root + password: root + driver-class-name: com.mysql.cj.jdbc.Driver + jpa: + hibernate: + ddl-auto: create-drop + +jwt: + issuer: test + expiry-seconds: 1800 + secret: thisisjusttestaccesssecretsodontworry \ No newline at end of file From a551498212834c292158e4d5404fb6fe0cd73736 Mon Sep 17 00:00:00 2001 From: mirageoasis Date: Wed, 21 Aug 2024 11:24:02 +0900 Subject: [PATCH 11/13] =?UTF-8?q?chore:=20workflow=20=EB=A1=A4=EB=B0=B1?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .github/workflows/test.yml | 51 +++----------------------------------- 1 file changed, 3 insertions(+), 48 deletions(-) diff --git a/.github/workflows/test.yml b/.github/workflows/test.yml index 1f8f7945..66bc167e 100644 --- a/.github/workflows/test.yml +++ b/.github/workflows/test.yml @@ -1,34 +1,10 @@ -name: test on push +name: unit test on push on: [ pull_request ] jobs: deploy: - name: test + name: unit test runs-on: ubuntu-latest - services: - mysql: - image: mysql:8.0.32 - ports: - - 3306:3306 - env: - MYSQL_ROOT_PASSWORD: root - MYSQL_DATABASE: ticketing - options: >- - --health-cmd "mysqladmin ping -u root -proot" - --health-interval 10s - --health-timeout 5s - --health-retries 5 - - redis: - image: redis:7.0.11 - ports: - - 6379:6379 - options: >- - --health-cmd "redis-cli ping" - --health-interval 10s - --health-timeout 5s - --health-retries 5 - steps: - name: checkout uses: actions/checkout@v3 @@ -42,28 +18,7 @@ jobs: distribution: 'temurin' java-version: '17' - - name: Set /etc/hosts for MySQL and Redis - run: | - echo "127.0.0.1 mysql" | sudo tee -a /etc/hosts - echo "127.0.0.1 redis" | sudo tee -a /etc/hosts - - - name: Wait for MySQL to be ready - run: | - until mysqladmin ping -h mysql -u root -proot --silent; do - echo 'waiting for mysql...' - sleep 5 - done - - - name: Wait for Redis to be ready - run: | - until nc -zv redis 6379; do - echo 'waiting for redis...' - sleep 5 - done - - - name: Build with Gradle run: | chmod +x ./gradlew - ./gradlew copyYml - ./gradlew test + ./gradlew --info test From 7bb620d494989e34ea91ba3b6978c367118e12ba Mon Sep 17 00:00:00 2001 From: mirageoasis Date: Wed, 21 Aug 2024 11:24:48 +0900 Subject: [PATCH 12/13] =?UTF-8?q?chore:=20=EC=83=88=EB=A1=9C=EC=9A=B4=20ym?= =?UTF-8?q?l=20=EC=A0=81=EC=9A=A9?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- backend-config | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/backend-config b/backend-config index 20885cc2..1937897c 160000 --- a/backend-config +++ b/backend-config @@ -1 +1 @@ -Subproject commit 20885cc25e27bd86f571509e4d256b17f90bf88d +Subproject commit 1937897ca5f9355d72fecfc7064e5140b6e3b010 From acd432a2adcb03b63161f6e381e6d22d95340cf4 Mon Sep 17 00:00:00 2001 From: seminchoi Date: Wed, 21 Aug 2024 12:45:33 +0900 Subject: [PATCH 13/13] =?UTF-8?q?fix:=20=EC=BB=B4=ED=8C=8C=EC=9D=BC=20?= =?UTF-8?q?=EC=98=A4=EB=A5=98=20=EC=88=98=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../config/ReservationServiceContainer.java | 16 ++++++++++------ 1 file changed, 10 insertions(+), 6 deletions(-) diff --git a/src/main/java/com/thirdparty/ticketing/global/config/ReservationServiceContainer.java b/src/main/java/com/thirdparty/ticketing/global/config/ReservationServiceContainer.java index aa667118..eaab2e2d 100644 --- a/src/main/java/com/thirdparty/ticketing/global/config/ReservationServiceContainer.java +++ b/src/main/java/com/thirdparty/ticketing/global/config/ReservationServiceContainer.java @@ -5,6 +5,7 @@ import org.springframework.context.annotation.Configuration; import org.springframework.context.annotation.Primary; +import com.thirdparty.ticketing.domain.common.EventPublisher; import com.thirdparty.ticketing.domain.common.LettuceRepository; import com.thirdparty.ticketing.domain.member.repository.MemberRepository; import com.thirdparty.ticketing.domain.payment.PaymentProcessor; @@ -51,29 +52,32 @@ ReservationService pessimisticReservationServiceProxy( public ReservationTransactionService cacheReservationTransactionService( PaymentProcessor paymentProcessor, MemberRepository memberRepository, - SeatRepository seatRepository) { + SeatRepository seatRepository, + EventPublisher eventPublisher) { LockSeatStrategy lockSeatStrategy = new NaiveSeatStrategy(seatRepository); return new ReservationTransactionService( - memberRepository, paymentProcessor, lockSeatStrategy); + memberRepository, paymentProcessor, lockSeatStrategy, eventPublisher); } @Bean public ReservationTransactionService persistenceOptimisticReservationService( PaymentProcessor paymentProcessor, MemberRepository memberRepository, - SeatRepository seatRepository) { + SeatRepository seatRepository, + EventPublisher eventPublisher) { LockSeatStrategy lockSeatStrategy = new OptimisticLockSeatStrategy(seatRepository); return new ReservationTransactionService( - memberRepository, paymentProcessor, lockSeatStrategy); + memberRepository, paymentProcessor, lockSeatStrategy, eventPublisher); } @Bean public ReservationTransactionService persistencePessimisticReservationService( PaymentProcessor paymentProcessor, MemberRepository memberRepository, - SeatRepository seatRepository) { + SeatRepository seatRepository, + EventPublisher eventPublisher) { LockSeatStrategy lockSeatStrategy = new PessimisticLockSeatStrategy(seatRepository); return new ReservationTransactionService( - memberRepository, paymentProcessor, lockSeatStrategy); + memberRepository, paymentProcessor, lockSeatStrategy, eventPublisher); } }