@Transactional 롤백,,?
안녕하세요 강사님. 프로젝트 진행중에 간단한 테스트 작업 중 이상한 결과가 나와서 질문드립니다..!
@Transactional
@SpringBootTest
@ActiveProfiles("test")
class ProductListResponseDtoTest {
@Autowired ProductRepository productRepository;
@Test
@DisplayName("주문 상세가 주어졌을 때 ProductListResponseDto 변환")
public void ofWithOrderDetail() {
Product product = Product.builder()
.price(1000L)
.name("빵빵이")
.productNo("123")
.build();
productRepository.save(product);
OrderDetail orderDetail = OrderDetail.builder()
.product(product)
.price(product.getPrice())
.quantity(2L)
.build();
// when
ProductListResponseDto result = ProductListResponseDto.of(orderDetail);
// then
assertThat(result).extracting("productId", "productNo", "name", "price", "quantity")
.contains(1L, "123", "빵빵이", 1000L, 2L);
}
@Test
@DisplayName("상품과 수량이 주어졌을 때 ProductListResponseDto 변환")
public void ofWithProductAndQuantity() {
Long quantity = 2L;
Product product = Product.builder()
.price(1000L)
.name("빵빵이")
.productNo("123")
.build();
productRepository.save(product);
// when
ProductListResponseDto result = ProductListResponseDto.of(product, quantity);
// then
assertThat(result).extracting("productId", "productNo", "name", "price", "quantity")
.contains(1L, "123", "빵빵이", 1000L, 2L);
}
}@Transactional를 통해 각 테스트가 롤백되어 productId가 모두 1L 될 것으로 예상하였습니다.
그런데 기대와 달리 실패를 하였는데요. 첫번째 테스트(ofWithOrderDetail)의 productId의 값이 2L 되었습니다.
insert문과 에러 메세지입니다.
Hibernate:
insert
into
product
(category_id, created_at, deleted_at, discount_rate, is_own, is_subs, name, price, product_no, stock, thumb_img, updated_at, product_id)
values
(?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, default)
2024-01-29T22:28:07.219+09:00 INFO 3636 --- [ main] p6spy : #1706534887219 | took 4ms | statement | connection 3| url jdbc:h2:mem:~/Marketbridge
insert into product (category_id,created_at,deleted_at,discount_rate,is_own,is_subs,name,price,product_no,stock,thumb_img,updated_at,product_id) values (?,?,?,?,?,?,?,?,?,?,?,?,default)
insert into product (category_id,created_at,deleted_at,discount_rate,is_own,is_subs,name,price,product_no,stock,thumb_img,updated_at,product_id) values (NULL,NULL,NULL,NULL,NULL,NULL,'빵빵이',1000,'123',NULL,NULL,NULL,default);
2024-01-29T22:28:07.299+09:00 INFO 3636 --- [ main] p6spy : #1706534887299 | took 0ms | rollback | connection 3| url jdbc:h2:mem:~/Marketbridge
;
Hibernate:
insert
into
product
(category_id, created_at, deleted_at, discount_rate, is_own, is_subs, name, price, product_no, stock, thumb_img, updated_at, product_id)
values
(?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, default)
2024-01-29T22:28:07.309+09:00 INFO 3636 --- [ main] p6spy : #1706534887309 | took 0ms | statement | connection 4| url jdbc:h2:mem:~/Marketbridge
insert into product (category_id,created_at,deleted_at,discount_rate,is_own,is_subs,name,price,product_no,stock,thumb_img,updated_at,product_id) values (?,?,?,?,?,?,?,?,?,?,?,?,default)
insert into product (category_id,created_at,deleted_at,discount_rate,is_own,is_subs,name,price,product_no,stock,thumb_img,updated_at,product_id) values (NULL,NULL,NULL,NULL,NULL,NULL,'빵빵이',1000,'123',NULL,NULL,NULL,default);
2024-01-29T22:28:07.317+09:00 INFO 3636 --- [ main] p6spy : #1706534887317 | took 0ms | rollback | connection 4| url jdbc:h2:mem:~/Marketbridge
;
java.lang.AssertionError: [Extracted: productId, productNo, name, price, quantity]
Expecting ArrayList:
[2L, "123", "빵빵이", 1000L, 2L]
to contain:
[1L, "123", "빵빵이", 1000L, 2L]
but could not find the following element(s):
[1L]
at com.objects.marketbridge.order.service.dto.ProductListResponseDtoTest.ofWithOrderDetail(ProductListResponseDtoTest.java:44)
at java.base/java.lang.reflect.Method.invoke(Method.java:568)
at java.base/java.util.ArrayList.forEach(ArrayList.java:1511)
at java.base/java.util.ArrayList.forEach(ArrayList.java:1511)
of 메서드 입니다.
@Getter
public class ProductListResponseDto {
private Long productId;
private String productNo;
private String name;
private Long price;
private Long quantity;
@Builder
private ProductListResponseDto(Long productId, String productNo, String name, Long price,Long quantity) {
this.productId = productId;
this.productNo = productNo;
this.name = name;
this.price = price;
this.quantity = quantity;
}
public static ProductListResponseDto of(Product product, Long quantity) {
return ProductListResponseDto.builder()
.productId(product.getId())
.productNo(product.getProductNo())
.name(product.getName())
.price(product.getPrice())
.quantity(quantity)
.build();
}
public static ProductListResponseDto of(OrderDetail orderDetail) {
return ProductListResponseDto.builder()
.productId(orderDetail.getProduct().getId())
.productNo(orderDetail.getProduct().getProductNo())
.name(orderDetail.getProduct().getName())
.price(orderDetail.getProduct().getPrice())
.quantity(orderDetail.getQuantity())
.build();
}
}
현재 Product 엔티티의 Id는 @GeneratedValue(strategy = GenerationType.IDENTITY) 로 이루어져 있습니다.
추가적으로 @ActiveProfiles("test")에 해당하는 yml의 일부는 아래와 같습니다.
datasource:
url: jdbc:h2:mem:~/Marketbridge
driver-class-name: org.h2.Driver
username: sa
password:
jpa:
hibernate:
ddl-auto: none
show-sql: true
properties:
hibernate:
format_sql: true
default_batch_fetch_size: 100
defer-datasource-initialization: true
h2:
console:
enabled: true
이런 경우는 처음이라 어디가 잘못됐는지 찾지 못하겠네요 ㅠㅠ
답변 1
1
안녕하세요. 유선목님, 공식 서포터즈 y2gcoder입니다.
@GeneratedValue(strategy = GenerationType.IDENTITY)
를 통해 만드는 auto inrement 값은 트랜잭션 롤백의 영향을 받지 않습니다! 아래의 두 링크를 참고해주십쇼!
https://ymkmoon.github.io/Java-29-Jpa-Primary-Key/
감사합니다.
RepositoryTest의 패키지 위치가 domain인 이유
0
29
2
REQUIRES_NEW 해결 방법에 대해서 질문있습니다!!
0
29
1
update()에 사용하는 setter 질문드립니다.
0
47
1
SQL 중심적 개발의 문제점에 대한 질문
0
72
1
혹시 Containing 을 안쓰신 이유가 있을까요?
0
83
2
[공유] 스프링부트 4.x 버전 mybatis 연동
0
173
1
@repository 어노테이션
0
89
3
ItemService
0
58
1
논리 커밋, 물리 커밋 질문드립니다.
0
54
1
내부 트랜잭션 커밋은 필수인가요?
0
57
1
프록시 커넥션 객체를 반환할 때 생성하는건가요?
0
54
1
Transaction readOnly 성능 개선 (김영한님의 대한 감사인사)
2
178
2
JPQL 대신 네이티브 쿼리를 사용해야 하는 경우
0
77
1
@EventListener(ApplicationReadyEvent.class) 관련
0
88
1
트랜잭션 동기화 매니저와 데이터 소스
0
76
1
DB 관련 강의 개설 계획은 없으신건가요?
0
133
2
물리 트랜잭션 과 논리트랜잭션 용어를 맞게 이해한걸까요
0
94
1
스프링 3 버전 이상 rollbackFor 변경된듯요
1
112
1
트랜잭션 전파 질문.
0
87
1
프로젝트 오픈 에러
0
126
1
외부 트랜잭션에서 isNewTransaction이 false로 나오는거에 대해 질문드립니다
0
83
2
같은 스레드를 사용하면 트랜잭션 동기화 매니저는 같은 커넥션을 반환
0
72
1
h2 인메모리 테스트중 예약어 충돌날 경우 대처방법
0
102
1
커스텀aop와 트랜잭션을 같이 사용할때 우선순위에 관한 질문
0
98
2





