test(order-service): kafka 전송 테스트 코드, order 테스트 코드 작성
- kafka 전송 테스트 코드 - order 테스트 코드 작성
This commit is contained in:
@@ -83,7 +83,11 @@ operation::prevOrder-get-BindException[snippets='curl-request,http-request,http-
|
|||||||
=== 주문 내역 페이지
|
=== 주문 내역 페이지
|
||||||
operation::api-customer-order-history[snippets='curl-request,http-request,http-response,request-headers,request-parameters,response-fields']
|
operation::api-customer-order-history[snippets='curl-request,http-request,http-response,request-headers,request-parameters,response-fields']
|
||||||
|
|
||||||
|
=== 장바구니 상품 추가
|
||||||
|
operation::add-item-to-basket[snippets='curl-request,http-request,http-response,request-headers,request-body,request-fields']
|
||||||
|
|
||||||
|
=== 장바구니 내역 가져오기
|
||||||
|
operation::fetch-order[snippets='curl-request,http-request,http-response,request-headers,response-fields']
|
||||||
|
|
||||||
|
=== 주문하기
|
||||||
operation::add-item-to-basket[snippets='curl-request,http-request,http-response,request-headers,request-body,request-fields']
|
operation::save-order[snippets='curl-request,http-request,http-response,request-headers']
|
||||||
@@ -1,38 +1,27 @@
|
|||||||
package com.justpickup.orderservice.domain.order.dto;
|
package com.justpickup.orderservice.domain.order.dto;
|
||||||
|
|
||||||
import com.justpickup.orderservice.domain.order.entity.Order;
|
import com.justpickup.orderservice.domain.order.entity.Order;
|
||||||
import com.justpickup.orderservice.domain.order.entity.OrderStatus;
|
|
||||||
import com.justpickup.orderservice.domain.orderItem.dto.OrderItemDto;
|
import com.justpickup.orderservice.domain.orderItem.dto.OrderItemDto;
|
||||||
import com.justpickup.orderservice.domain.orderItem.entity.OrderItem;
|
|
||||||
import com.justpickup.orderservice.domain.orderItemOption.dto.OrderItemOptionDto;
|
import com.justpickup.orderservice.domain.orderItemOption.dto.OrderItemOptionDto;
|
||||||
|
import lombok.AllArgsConstructor;
|
||||||
import lombok.Getter;
|
import lombok.Getter;
|
||||||
import lombok.NoArgsConstructor;
|
import lombok.NoArgsConstructor;
|
||||||
|
|
||||||
import java.time.LocalDateTime;
|
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.stream.Collectors;
|
import java.util.stream.Collectors;
|
||||||
|
|
||||||
@Getter
|
@Getter
|
||||||
@NoArgsConstructor
|
@NoArgsConstructor
|
||||||
|
@AllArgsConstructor
|
||||||
public class FetchOrderDto {
|
public class FetchOrderDto {
|
||||||
private Long id;
|
private Long id;
|
||||||
|
|
||||||
private Long userId;
|
private Long userId;
|
||||||
|
|
||||||
private String userName;
|
|
||||||
|
|
||||||
private Long userCouponId;
|
|
||||||
|
|
||||||
private Long orderPrice;
|
private Long orderPrice;
|
||||||
|
|
||||||
private Long storeId;
|
private Long storeId;
|
||||||
|
|
||||||
private LocalDateTime orderTime;
|
|
||||||
|
|
||||||
private Long usedPoint;
|
|
||||||
|
|
||||||
private OrderStatus orderStatus;
|
|
||||||
|
|
||||||
private List<OrderItemDto> orderItemDtoList;
|
private List<OrderItemDto> orderItemDtoList;
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@@ -0,0 +1,69 @@
|
|||||||
|
package com.justpickup.orderservice.domain.order.service;
|
||||||
|
|
||||||
|
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||||
|
import com.fasterxml.jackson.datatype.jsr310.JavaTimeModule;
|
||||||
|
import com.justpickup.orderservice.domain.order.entity.Order;
|
||||||
|
import com.justpickup.orderservice.domain.order.entity.OrderStatus;
|
||||||
|
import com.justpickup.orderservice.domain.orderItem.dto.OrderItemDto;
|
||||||
|
import lombok.*;
|
||||||
|
import lombok.extern.slf4j.Slf4j;
|
||||||
|
import org.springframework.kafka.core.KafkaTemplate;
|
||||||
|
import org.springframework.stereotype.Service;
|
||||||
|
|
||||||
|
import java.time.LocalDateTime;
|
||||||
|
import java.util.List;
|
||||||
|
|
||||||
|
@Service
|
||||||
|
@Slf4j
|
||||||
|
@RequiredArgsConstructor
|
||||||
|
public class OrderSender {
|
||||||
|
|
||||||
|
private final KafkaTemplate<String, String> kafkaTemplate;
|
||||||
|
|
||||||
|
public void orderPlaced( KafkaSendOrderDto kafkaSendOrderDto) throws Exception{
|
||||||
|
ObjectMapper mapper = new ObjectMapper().registerModule(new JavaTimeModule());
|
||||||
|
String jsonInString = mapper.writeValueAsString(kafkaSendOrderDto);
|
||||||
|
kafkaTemplate.send("orderPlaced", jsonInString);
|
||||||
|
log.info("kafka Producer sent data from the Order microservice: "+ kafkaSendOrderDto);
|
||||||
|
}
|
||||||
|
|
||||||
|
@NoArgsConstructor
|
||||||
|
@Data
|
||||||
|
@AllArgsConstructor
|
||||||
|
@Builder
|
||||||
|
static class KafkaSendOrderDto{
|
||||||
|
private Long id;
|
||||||
|
|
||||||
|
private Long userId;
|
||||||
|
|
||||||
|
private String userName;
|
||||||
|
|
||||||
|
private Long userCouponId;
|
||||||
|
|
||||||
|
private Long orderPrice;
|
||||||
|
|
||||||
|
private Long storeId;
|
||||||
|
|
||||||
|
private LocalDateTime orderTime;
|
||||||
|
|
||||||
|
private Long usedPoint;
|
||||||
|
|
||||||
|
private OrderStatus orderStatus;
|
||||||
|
|
||||||
|
private List<OrderItemDto> orderItemDtoList;
|
||||||
|
|
||||||
|
// == 생성 메소드 == //
|
||||||
|
public static KafkaSendOrderDto createPrimitiveField(Order order) {
|
||||||
|
return KafkaSendOrderDto.builder()
|
||||||
|
.id(order.getId())
|
||||||
|
.userId(order.getUserId())
|
||||||
|
.userCouponId(order.getUserCouponId())
|
||||||
|
.orderPrice(order.getOrderPrice())
|
||||||
|
.orderTime(order.getOrderTime())
|
||||||
|
.storeId(order.getStoreId())
|
||||||
|
.usedPoint(order.getUsedPoint())
|
||||||
|
.orderStatus(order.getOrderStatus())
|
||||||
|
.build();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -1,10 +1,5 @@
|
|||||||
package com.justpickup.orderservice.domain.order.service;
|
package com.justpickup.orderservice.domain.order.service;
|
||||||
|
|
||||||
import com.fasterxml.jackson.core.JsonProcessingException;
|
|
||||||
import com.fasterxml.jackson.databind.ObjectMapper;
|
|
||||||
import com.fasterxml.jackson.databind.annotation.JsonDeserialize;
|
|
||||||
import com.fasterxml.jackson.datatype.jsr310.JavaTimeModule;
|
|
||||||
import com.fasterxml.jackson.datatype.jsr310.deser.LocalDateTimeDeserializer;
|
|
||||||
import com.justpickup.orderservice.domain.order.dto.FetchOrderDto;
|
import com.justpickup.orderservice.domain.order.dto.FetchOrderDto;
|
||||||
import com.justpickup.orderservice.domain.order.dto.OrderDto;
|
import com.justpickup.orderservice.domain.order.dto.OrderDto;
|
||||||
import com.justpickup.orderservice.domain.order.dto.OrderSearchCondition;
|
import com.justpickup.orderservice.domain.order.dto.OrderSearchCondition;
|
||||||
@@ -29,11 +24,9 @@ import org.springframework.data.domain.Page;
|
|||||||
import org.springframework.data.domain.Pageable;
|
import org.springframework.data.domain.Pageable;
|
||||||
import org.springframework.data.domain.SliceImpl;
|
import org.springframework.data.domain.SliceImpl;
|
||||||
import org.springframework.data.support.PageableExecutionUtils;
|
import org.springframework.data.support.PageableExecutionUtils;
|
||||||
import org.springframework.kafka.core.KafkaTemplate;
|
|
||||||
import org.springframework.stereotype.Service;
|
import org.springframework.stereotype.Service;
|
||||||
import org.springframework.transaction.annotation.Transactional;
|
import org.springframework.transaction.annotation.Transactional;
|
||||||
|
|
||||||
import java.time.LocalDateTime;
|
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.Optional;
|
import java.util.Optional;
|
||||||
import java.util.stream.Collectors;
|
import java.util.stream.Collectors;
|
||||||
@@ -50,7 +43,9 @@ public class OrderServiceImpl implements OrderService {
|
|||||||
private final OrderRepositoryCustom orderRepositoryCustom;
|
private final OrderRepositoryCustom orderRepositoryCustom;
|
||||||
private final StoreClient storeClient;
|
private final StoreClient storeClient;
|
||||||
private final UserClient userClient;
|
private final UserClient userClient;
|
||||||
private final KafkaTemplate<String, String> kafkaTemplate;
|
private final OrderSender orderSender;
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public List<OrderDto> findOrderMain(OrderSearchCondition condition, Long storeId) {
|
public List<OrderDto> findOrderMain(OrderSearchCondition condition, Long storeId) {
|
||||||
@@ -154,59 +149,13 @@ public class OrderServiceImpl implements OrderService {
|
|||||||
.orElseThrow(() -> new OrderException("장바구니 정보를 찾을 수 없습니다."))
|
.orElseThrow(() -> new OrderException("장바구니 정보를 찾을 수 없습니다."))
|
||||||
.setOrderStatus(OrderStatus.PLACED);
|
.setOrderStatus(OrderStatus.PLACED);
|
||||||
try{
|
try{
|
||||||
send("orderPlaced",KafkaSendOrderDto.createPrimitiveField(order));
|
orderSender.orderPlaced(OrderSender.KafkaSendOrderDto.createPrimitiveField(order));
|
||||||
}catch (Exception ex){
|
}catch (Exception ex){
|
||||||
throw new OrderException(ex.getMessage());
|
throw new OrderException(ex.getMessage());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
public void send(String topic, KafkaSendOrderDto kafkaSendOrderDto) throws Exception{
|
|
||||||
ObjectMapper mapper = new ObjectMapper().registerModule(new JavaTimeModule());
|
|
||||||
String jsonInString = mapper.writeValueAsString(kafkaSendOrderDto);
|
|
||||||
kafkaTemplate.send(topic, jsonInString);
|
|
||||||
log.info("kafka Producer sent data from the Order microservice: "+ kafkaSendOrderDto);
|
|
||||||
}
|
|
||||||
|
|
||||||
@NoArgsConstructor
|
|
||||||
@Data
|
|
||||||
@AllArgsConstructor
|
|
||||||
@Builder
|
|
||||||
static class KafkaSendOrderDto{
|
|
||||||
private Long id;
|
|
||||||
|
|
||||||
private Long userId;
|
|
||||||
|
|
||||||
private String userName;
|
|
||||||
|
|
||||||
private Long userCouponId;
|
|
||||||
|
|
||||||
private Long orderPrice;
|
|
||||||
|
|
||||||
private Long storeId;
|
|
||||||
|
|
||||||
// @JsonDeserialize(using = LocalDateTimeDeserializer.class)
|
|
||||||
private LocalDateTime orderTime;
|
|
||||||
|
|
||||||
private Long usedPoint;
|
|
||||||
|
|
||||||
private OrderStatus orderStatus;
|
|
||||||
|
|
||||||
private List<OrderItemDto> orderItemDtoList;
|
|
||||||
|
|
||||||
// == 생성 메소드 == //
|
|
||||||
public static KafkaSendOrderDto createPrimitiveField(Order order) {
|
|
||||||
return KafkaSendOrderDto.builder()
|
|
||||||
.id(order.getId())
|
|
||||||
.userId(order.getUserId())
|
|
||||||
.userCouponId(order.getUserCouponId())
|
|
||||||
.orderPrice(order.getOrderPrice())
|
|
||||||
.orderTime(order.getOrderTime())
|
|
||||||
.storeId(order.getStoreId())
|
|
||||||
.usedPoint(order.getUsedPoint())
|
|
||||||
.orderStatus(order.getOrderStatus())
|
|
||||||
.build();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -0,0 +1,105 @@
|
|||||||
|
package com.justpickup.orderservice.domain.order.service;
|
||||||
|
|
||||||
|
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||||
|
import com.fasterxml.jackson.datatype.jsr310.JavaTimeModule;
|
||||||
|
import com.justpickup.orderservice.domain.order.entity.OrderStatus;
|
||||||
|
import com.justpickup.orderservice.domain.orderItem.dto.OrderItemDto;
|
||||||
|
import com.justpickup.orderservice.domain.orderItemOption.dto.OrderItemOptionDto;
|
||||||
|
import org.apache.kafka.clients.consumer.Consumer;
|
||||||
|
import org.apache.kafka.clients.consumer.ConsumerConfig;
|
||||||
|
import org.apache.kafka.clients.consumer.ConsumerRecord;
|
||||||
|
import org.junit.jupiter.api.BeforeEach;
|
||||||
|
import org.junit.jupiter.api.Test;
|
||||||
|
import org.junit.jupiter.api.TestInstance;
|
||||||
|
import org.junit.jupiter.api.extension.ExtendWith;
|
||||||
|
import org.springframework.beans.factory.annotation.Autowired;
|
||||||
|
import org.springframework.kafka.annotation.EnableKafka;
|
||||||
|
import org.springframework.kafka.core.DefaultKafkaConsumerFactory;
|
||||||
|
import org.springframework.kafka.core.DefaultKafkaProducerFactory;
|
||||||
|
import org.springframework.kafka.core.KafkaTemplate;
|
||||||
|
import org.springframework.kafka.support.SendResult;
|
||||||
|
import org.springframework.kafka.test.EmbeddedKafkaBroker;
|
||||||
|
import org.springframework.kafka.test.context.EmbeddedKafka;
|
||||||
|
import org.springframework.kafka.test.utils.KafkaTestUtils;
|
||||||
|
import org.springframework.test.annotation.DirtiesContext;
|
||||||
|
import org.springframework.test.context.junit.jupiter.SpringExtension;
|
||||||
|
import org.springframework.util.concurrent.ListenableFuture;
|
||||||
|
|
||||||
|
import java.time.LocalDateTime;
|
||||||
|
import java.util.Collections;
|
||||||
|
import java.util.HashMap;
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.Map;
|
||||||
|
|
||||||
|
import static org.assertj.core.api.Assertions.assertThat;
|
||||||
|
|
||||||
|
@ExtendWith(SpringExtension.class)
|
||||||
|
@EnableKafka
|
||||||
|
@DirtiesContext
|
||||||
|
@EmbeddedKafka(topics = {"orderPlaced"})
|
||||||
|
@TestInstance(TestInstance.Lifecycle.PER_CLASS)
|
||||||
|
class OrderSenderTest {
|
||||||
|
|
||||||
|
private final String TEST_TOPIC = "orderPlaced";
|
||||||
|
|
||||||
|
private Consumer<Integer, String> consumer;
|
||||||
|
private KafkaTemplate<String, String> producer;
|
||||||
|
|
||||||
|
@Autowired
|
||||||
|
private EmbeddedKafkaBroker embeddedKafkaBroker;
|
||||||
|
|
||||||
|
|
||||||
|
@BeforeEach
|
||||||
|
void setup() {
|
||||||
|
System.out.println("beforeAll");
|
||||||
|
producer = configureProducer();
|
||||||
|
consumer = configureConsumer();
|
||||||
|
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
private Consumer<Integer, String> configureConsumer() {
|
||||||
|
Map<String, Object> consumerProps = KafkaTestUtils.consumerProps("testGroup", "true", embeddedKafkaBroker);
|
||||||
|
consumerProps.put(ConsumerConfig.AUTO_OFFSET_RESET_CONFIG, "earliest");
|
||||||
|
Consumer<Integer, String> consumer = new DefaultKafkaConsumerFactory<Integer, String>(consumerProps)
|
||||||
|
.createConsumer();
|
||||||
|
consumer.subscribe(Collections.singleton(TEST_TOPIC));
|
||||||
|
return consumer;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
private KafkaTemplate<String, String> configureProducer() {
|
||||||
|
Map<String, Object> producerProps = new HashMap<>(KafkaTestUtils.producerProps(embeddedKafkaBroker));
|
||||||
|
return new KafkaTemplate <>( new DefaultKafkaProducerFactory<>(producerProps));
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
@Test
|
||||||
|
void sendOrderPlaced() throws Exception{
|
||||||
|
//given
|
||||||
|
ObjectMapper mapper = new ObjectMapper().registerModule(new JavaTimeModule());
|
||||||
|
OrderSender.KafkaSendOrderDto kafkaSendOrderDto = new OrderSender.KafkaSendOrderDto(
|
||||||
|
1L,2L,"주문아이디",1L,12000L,2L, LocalDateTime.now(),3000L, OrderStatus.PLACED,
|
||||||
|
List.of(
|
||||||
|
OrderItemDto.of(1L,300L,3000L,2L,
|
||||||
|
List.of(new OrderItemOptionDto(2L)
|
||||||
|
,new OrderItemOptionDto(3L))
|
||||||
|
)
|
||||||
|
)
|
||||||
|
);
|
||||||
|
String jsonInString = mapper.writeValueAsString(kafkaSendOrderDto);
|
||||||
|
|
||||||
|
//when
|
||||||
|
ListenableFuture<SendResult<String, String>> orderPlaced = producer.send("orderPlaced", jsonInString);
|
||||||
|
System.out.println(orderPlaced.get().toString());
|
||||||
|
//then
|
||||||
|
|
||||||
|
ConsumerRecord<Integer, String> singleRecord = KafkaTestUtils.getSingleRecord(consumer, TEST_TOPIC);
|
||||||
|
assertThat(singleRecord).isNotNull();
|
||||||
|
assertThat(singleRecord.value()).isEqualTo(jsonInString);
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
}
|
||||||
@@ -176,10 +176,39 @@ class OrderCustomerApiControllerTest {
|
|||||||
@DisplayName("장바구니 정보 조회_성공")
|
@DisplayName("장바구니 정보 조회_성공")
|
||||||
void fetchOrder() throws Exception{
|
void fetchOrder() throws Exception{
|
||||||
//Given
|
//Given
|
||||||
|
FetchOrderDto fetchOrderDto =
|
||||||
|
new FetchOrderDto(2L,2L,12000L,2L
|
||||||
|
,List.of(
|
||||||
|
OrderItemDto.of(1L,300L,3000L,2L,
|
||||||
|
List.of(new OrderItemOptionDto(2L)
|
||||||
|
,new OrderItemOptionDto(3L))
|
||||||
|
)
|
||||||
|
)
|
||||||
|
);
|
||||||
|
|
||||||
|
given(orderService.fetchOrder(2L)).willReturn(fetchOrderDto);
|
||||||
//When
|
//When
|
||||||
|
|
||||||
|
ResultActions actions = mockMvc.perform(get(url + "/orders")
|
||||||
|
.header("user-id", "2")
|
||||||
|
);
|
||||||
|
|
||||||
//Then
|
//Then
|
||||||
|
actions.andExpect(status().isOk())
|
||||||
|
.andDo(print())
|
||||||
|
.andDo(document("fetch-order",
|
||||||
|
requestHeaders(headerWithName("user-id").description("유저 고유번호")),
|
||||||
|
responseFields(
|
||||||
|
fieldWithPath("code").description("결과 코드 SUCCESS/ERROR"),
|
||||||
|
fieldWithPath("message").description("메시지"),
|
||||||
|
fieldWithPath("data.storeId").description("매장 고유번호"),
|
||||||
|
fieldWithPath("data.totalPrice").description("총 합계"),
|
||||||
|
fieldWithPath("data._orderItemDtos[*].itemId").description("상품 고유번호"),
|
||||||
|
fieldWithPath("data._orderItemDtos[*].price").description("상품 가격"),
|
||||||
|
fieldWithPath("data._orderItemDtos[*].count").description("상품 갯수"),
|
||||||
|
fieldWithPath("data._orderItemDtos[*].itemOptionIds[*]").description("아이템 옵션들")
|
||||||
|
)));
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -189,8 +218,15 @@ class OrderCustomerApiControllerTest {
|
|||||||
//Given
|
//Given
|
||||||
|
|
||||||
//When
|
//When
|
||||||
|
ResultActions actions = mockMvc.perform(post(url + "/orders")
|
||||||
|
.header("user-id", "2")
|
||||||
|
);
|
||||||
//Then
|
//Then
|
||||||
|
actions.andExpect(status().isCreated())
|
||||||
|
.andDo(print())
|
||||||
|
.andDo(document("save-order",
|
||||||
|
requestHeaders(headerWithName("user-id").description("유저 고유번호"))
|
||||||
|
));
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user