더티 체킹 (Dirty Checking): 두 판 사이의 차이
기술노트
(컴퓨터 과학 용어 정리 - 더티 체킹 (Dirty Checking) 추가) |
편집 요약 없음 |
||
3번째 줄: | 3번째 줄: | ||
<br> | <br> | ||
[[File:https://cdn.inflearn.com/public/courses/324474/course_cover/58c8632c-7a6e-4c76-9893-d7fffa32faf2/kyh_JPA_Spring2%20%E1%84%87%E1%85%A9%E1%86%A8%E1%84%89%E1%85%A1%206.png|center|600px]] | |||
<br> | <br> | ||
트랜잭션 안에서 Entity의 변경이 일어났을 때 | |||
트랜잭션 안에서 Entity의 변경이 일어났을 때 | 변경한 내용을 자동으로 DB에 반영하는 것을 "더티 체킹(Dirty Checking)"이라고 한다. | ||
변경한 내용을 자동으로 DB에 반영하는 | |||
ORM 구현체나 JPA를 사용할 때 자주 언급되는 이 기능은 변경 감지(change detection)를 기반으로 한다. | |||
=== 예시: 주문 취소 기능 === | |||
<syntaxhighlight> | <syntaxhighlight lang="java"> | ||
@Transactional | @Transactional | ||
public void cancelOrder(Long orderId) { | public void cancelOrder(Long orderId) { | ||
//주문 엔티티 조회 | // 주문 엔티티 조회 | ||
Order order = orderRepository.findOne(orderId); | Order order = orderRepository.findOne(orderId); | ||
//주문 취소 | // 주문 취소 | ||
order.cancel(); | order.cancel(); | ||
} | } | ||
</syntaxhighlight> | </syntaxhighlight> | ||
위 코드는 주문 ID로 주문을 조회하고, 주문을 취소하는 메소드이다. | |||
<code>update</code> 쿼리를 명시적으로 작성하지 않았음에도 불구하고, 데이터베이스에는 변경된 상태가 반영된다. | |||
이는 다음과 같은 흐름으로 동작한다: | |||
* 트랜잭션 시작 | * 트랜잭션 시작 | ||
* | * Entity 조회 | ||
* | * Entity 내부 상태 변경 | ||
* 트랜잭션 커밋 | * 트랜잭션 커밋 시점에 변경 사항 감지 및 자동 update | ||
이 모든 흐름을 가능케 하는 것이 바로 더티 체킹이다. | |||
=== 더티 체킹 작동 방식 === | |||
더티 체킹은 JPA가 트랜잭션 커밋 직전에 수행하는 다음 절차로 작동한다: | |||
# Entity 조회 시점에 스냅샷(snapshot) 생성 | |||
# 트랜잭션 커밋 시 현재 상태와 스냅샷 비교 | |||
# 변경이 감지되면 update 쿼리 생성 및 전송 | |||
<syntaxhighlight lang="text"> | |||
Dirty : 상태의 변화가 생김 | |||
Checking : 검사 | |||
</syntaxhighlight> | |||
즉, 변경된 필드를 자동으로 감지하여, update 쿼리를 생성해주는 기능이다. | |||
=== 대상 === | |||
준영속, | 더티 체킹은 "영속성 컨텍스트"가 관리하는 Entity에만 적용된다. | ||
준영속(detached) 혹은 비영속(transient) 상태의 객체는 변경을 감지하지 못하므로, 데이터베이스에도 반영되지 않는다. | |||
=== 성능 고려: @DynamicUpdate === | |||
기본적으로 | 기본적으로 JPA는 Entity의 모든 필드를 대상으로 update 쿼리를 생성한다. | ||
필드 수가 많을 경우 이는 성능에 비효율적일 수 있다. | |||
이때 <code>@DynamicUpdate</code> 애노테이션을 사용하면 실제 변경된 필드만 update 쿼리로 반영되도록 설정할 수 있다. | |||
<syntaxhighlight> | <syntaxhighlight lang="java"> | ||
@Getter | @Getter | ||
@NoArgsConstructor | @NoArgsConstructor | ||
84번째 줄: | 75번째 줄: | ||
private Long id; | private Long id; | ||
private String product; | private String product; | ||
// 기타 필드 | |||
} | |||
</syntaxhighlight> | </syntaxhighlight> | ||
=== 요약 === | |||
< | * 더티 체킹은 JPA가 영속성 컨텍스트 안에서 Entity의 변경을 감지하고 DB에 자동 반영하는 기능이다. | ||
* 명시적 쿼리 작성 없이도 update가 가능하다. | |||
* 트랜잭션 커밋 시점에만 반영된다. | |||
* <code>@DynamicUpdate</code>를 통해 성능 최적화 가능하다. | |||
== | == 참고 자료 == | ||
* [ | * [https://velog.io/@jiny/JPA-%EB%8D%94%ED%8B%B0-%EC%B2%B4%ED%82%B9Dirty-Checking-%EC%9D%B4%EB%9E%80 JPA 더티 체킹 정리 by jiny] | ||
* [ | * [https://jojoldu.tistory.com/415 JPA Dirty Checking 개념 정리 by jojoldu] |
2025년 5월 6일 (화) 04:30 판
[Spring Data JPA] 더티 체킹 (Dirty Checking)
트랜잭션 안에서 Entity의 변경이 일어났을 때 변경한 내용을 자동으로 DB에 반영하는 것을 "더티 체킹(Dirty Checking)"이라고 한다.
ORM 구현체나 JPA를 사용할 때 자주 언급되는 이 기능은 변경 감지(change detection)를 기반으로 한다.
예시: 주문 취소 기능
@Transactional
public void cancelOrder(Long orderId) {
// 주문 엔티티 조회
Order order = orderRepository.findOne(orderId);
// 주문 취소
order.cancel();
}
위 코드는 주문 ID로 주문을 조회하고, 주문을 취소하는 메소드이다.
update
쿼리를 명시적으로 작성하지 않았음에도 불구하고, 데이터베이스에는 변경된 상태가 반영된다.
이는 다음과 같은 흐름으로 동작한다:
- 트랜잭션 시작
- Entity 조회
- Entity 내부 상태 변경
- 트랜잭션 커밋 시점에 변경 사항 감지 및 자동 update
이 모든 흐름을 가능케 하는 것이 바로 더티 체킹이다.
더티 체킹 작동 방식
더티 체킹은 JPA가 트랜잭션 커밋 직전에 수행하는 다음 절차로 작동한다:
- Entity 조회 시점에 스냅샷(snapshot) 생성
- 트랜잭션 커밋 시 현재 상태와 스냅샷 비교
- 변경이 감지되면 update 쿼리 생성 및 전송
Dirty : 상태의 변화가 생김
Checking : 검사
즉, 변경된 필드를 자동으로 감지하여, update 쿼리를 생성해주는 기능이다.
대상
더티 체킹은 "영속성 컨텍스트"가 관리하는 Entity에만 적용된다. 준영속(detached) 혹은 비영속(transient) 상태의 객체는 변경을 감지하지 못하므로, 데이터베이스에도 반영되지 않는다.
성능 고려: @DynamicUpdate
기본적으로 JPA는 Entity의 모든 필드를 대상으로 update 쿼리를 생성한다. 필드 수가 많을 경우 이는 성능에 비효율적일 수 있다.
이때 @DynamicUpdate
애노테이션을 사용하면 실제 변경된 필드만 update 쿼리로 반영되도록 설정할 수 있다.
@Getter
@NoArgsConstructor
@Entity
@DynamicUpdate
public class Order {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private Long id;
private String product;
// 기타 필드
}
요약
- 더티 체킹은 JPA가 영속성 컨텍스트 안에서 Entity의 변경을 감지하고 DB에 자동 반영하는 기능이다.
- 명시적 쿼리 작성 없이도 update가 가능하다.
- 트랜잭션 커밋 시점에만 반영된다.
@DynamicUpdate
를 통해 성능 최적화 가능하다.