일단 기본적으로 다른 서비스와 통신하는 것은 없다.
전부 Order에 제공되는 service인 것 같다.
제공되는 API
또한 Zipkin이 있는 걸로 봐서 분산 추적 및 모니터링을 수행하는 것 같다.
QueryDSL 기능을 사용하는 거 같은데 처음보는 기능이다.
Qclass 라는 걸 봤다.
import static com.spring_cloud.eureka.client.product.core.QProduct.product;
@Bean
JPAQueryFactory jpaQueryFactory(EntityManager em){
return new JPAQueryFactory(em);
}QueryResults<Product> results = queryFactory
.selectFrom(product)
.where(
nameContains(searchDto.getName()),
descriptionContains(searchDto.getDescription()),
priceBetween(searchDto.getMinPrice(), searchDto.getMaxPrice()),
quantityBetween(searchDto.getMinQuantity(), searchDto.getMaxQuantity())
)
.orderBy(orders.toArray(new OrderSpecifier[0]))
.offset(pageable.getOffset())
.limit(pageable.getPageSize())
.fetchResults();
queryFactory에서 selectFrom()으로 테이블을 정한다.
where절에 조건을 기술하고
product.price.between 이런 식으로 처리하는 거도 보이고private BooleanExpression nameContains(String name) {
return name != null ? product.name.containsIgnoreCase(name) : null;
}orderBy로 order by 절에 대해 기술한다.
offset과 limit로 paging 처리에 대한 내용을 기술한다.
fetchResults로 QueryResults 결과를 가져온다.
그리고 QueryResults의 인스턴스를 가공해서 원하는 결과를 만들어주면 된다.
마지막으로 Service에서는 그냥 JpaRepository를 주입받게 해놓고 Jpa의 기능과 QueryDsl의 기능을 모두 쓰는 것도 확인했다.
JpaRepository와 ProductRepositoryCustom를 impl한 ProductRepository
ProductRepositoryCustom은 ProductRepositoryImpl가 가졌음 하는 기능을 넣고 ProductRepository 인스턴스에서도 수행이 가능하도록 다중 구현을 때려버림ProductRepositoryCustom을 implement한 ProductRepositoryImpl
public class ProductService {
private final ProductRepository productRepository;
@Transactional
public ProductResponseDto createProduct(ProductRequestDto requestDto, String userId) {
Product product = Product.createProduct(requestDto, userId);
Product savedProduct = productRepository.save(product);
return toResponseDto(savedProduct);
}
public Page<ProductResponseDto> getProducts(ProductSearchDto searchDto, Pageable pageable) {
return productRepository.searchProducts(searchDto, pageable);
}
기능은 다음과 같은 것 같다
기본적으로 관계형 데이터베이스에는 컬렉션을 저장할 수 없다.
따라서 컬렉션을 저장하기 위해서는 별도의 테이블을 만들어서 컬렉션을 저장해야 한다.
이때 사용할 수 있는 것이 @ElementCollection과 @CollectionTable이다.
@ElementCollection
컬렉션 객체임을 JPA가 알 수 있게 하게 한다.
엔티티가 아닌 값 타입, 임베디드 타입에 대한 테이블을 생성하고 1대다 관계로 다룬다.
@CollectionTable
값 타입 컬렉션을 매핑할 테이블에 대한 역할을 지정하는 데 사용한다.
테이블의 이름과 조인정보를 적어줘야 한다.
대략적으로 이러한 흐름을 갖고 있다.
조금 더 설명이 필요한 것 같아 지피티한테 물어봤다.
지피티 said
1️⃣ 클라이언트(브라우저 등) → A 서비스
2️⃣ A 서비스 로직 처리 후
@FeignClient 가 @GetMapping("/something") 같은 B의 API를 호출하려고 함.3️⃣ A 서비스 내부의 LoadBalancer 동작
@FeignClient(name = "b-service"))을 보고 A 서비스의 Spring Cloud LoadBalancer가 Eureka(서비스 레지스트리) 에서 B의 실제 인스턴스 목록을 조회.4️⃣ B 서비스 처리
5️⃣ HTTP 응답 반환
다른 사람의 블로그도 들어가보면서 공부해봐야겠다.
완료 얼추 했음…