[6회차] Spring Batch 스터디: 후기 및 추가 학습 내용

6회차는 Spring Batch의 JpaItemReaderWriter에 대해 공부했습니다.

 

스터디 진행 전 교안을 공부하며 정리한 내용은 이곳에서 볼 수 있습니다.

 

[6회차] JpaPagingItemReader로 DB내용을 읽고, JpaItemWriter로 DB에 쓰기

아래 글은 한국 스프링 사용자 모임(KSUG)에서 진행된 스프링 배치 스터디 내용을 정리한 게시글입니다.DEVOCEAN에 연재 중인 KIDO님의 글을 참고하여 실습한 내용을 기록했습니다. 원본: [SpringBatch

yeseul-dev.tistory.com

 

1. JPA를 사용한 Batch 처리 중 예외와 데이터 무결성 문제

Spring Batch와 JPA를 활용한 Batch 처리에서 다음과 같은 문제들이 발생할 수 있습니다.

  1. 예외 발생 시 데이터 무결성 문제
    • Chunk 단위로 데이터를 처리할 때, 예외가 발생하면 해당 Chunk 내 일부 데이터만 반영될 수 있습니다. 이로 인해 데이터 무결성이 깨질 가능성이 있습니다.
    • JPA의 자동 플러시로 인해, 트랜잭션 롤백 후에도 예상치 못한 데이터 상태 변화가 발생할 수 있습니다.
  2. JpaPagingItemReader와 영속성 컨텍스트 문제
    • JpaPagingItemReader는 데이터를 읽을 때 엔티티를 영속성 컨텍스트에 포함시킵니다.
    • 이로 인해 프로세서 단계에서 엔티티가 변경되면, 트랜잭션 종료 시 변경 사항이 의도치 않게 DB에 반영될 가능성이 있습니다.

해결 방법

1. Chunk 크기 조정 및 트랜잭션 관리

  • Chunk 크기를 적절히 줄여 예외 발생 시 영향을 최소화합니다.
  • Chunk 단위로 트랜잭션을 설정하여 커밋 및 플러시 타이밍을 명확히 관리합니다. 이를 통해 데이터 처리 효율성과 안정성을 확보할 수 있습니다.

2. JPA 트랜잭션 경계 설정

  • Spring Batch와 JPA의 트랜잭션 경계를 명확히 설정합니다.
  • Chunk마다 트랜잭션이 커밋되므로, Chunk 크기에 따라 커밋 타이밍이 달라질 수 있음을 인지하고 이를 설계에 반영합니다.

3. Flush 및 롤백 전략 강화

  • Chunk 처리 단계에서 예외 발생 시, EntityManager.clear()를 호출해 영속성 컨텍스트를 초기화하여 변경 사항을 무효화합니다.
  • 트랜잭션 경계를 명확히 정의하여 데이터 무결성을 유지합니다.

4. JpaPagingItemReader 문제 해결 방안

  • DTO 변환하기
    • 데이터를 읽은 직후 DTO로 변환해 영속성 컨텍스트에서 제외합니다.
    • 불필요한 데이터베이스 반영을 방지합니다.
  • 읽기 전용 설정하기
    • 데이터를 읽기 전용으로 설정해 엔티티가 수정되지 않도록 제한합니다.
  • EntityManager.clear() 사용하기
    • 프로세스 단계 후 EntityManager.clear()를 호출해 DB와의 동기화를 방지합니다.

5. 재처리 로직 추가

  • 실패한 데이터를 별도의 테이블이나 로그에 저장하여 이후 재처리를 수행합니다.
  • 이 과정을 통해 데이터 정합성을 유지할 수 있습니다.

2. 실습 경험 공유

  • 엑셀로 에러 데이터 저장하기
    • 실패한 데이터를 엑셀 파일로 저장하는 로직을 구현
    • 저장된 데이터를 백업 테이블로 마이그레이션하는 작업까지 구현한 사례 공유

3. 후기

이번 스터디에서는 JPA와 Spring Batch를 결합해 데이터를 읽고 쓰는 작업을 진행하며, 영속성 컨텍스트와 트랜잭션 경계의 중요성을 배울 수 있었습니다.

마침 JPA 책을 읽고 있던 터라 내용이 비교적 쉽게 이해되었고, 학습하는 데 도움이 되었습니다.

 

스터디가 끝난 후 면접 준비를 위한 모의 면접을 봐주신다고 하셔서 긴장한 나머지 학습 내용이 머리에 많이 남지 않은 것 같습니다.

면접 준비로 인해 정리 시기가 늦어졌지만, 앞으로 더 공부하며 부족한 부분을 보완해야겠습니다.

 

틀린 내용이 있다면 댓글 부탁드립니다.

읽어주셔서 감사합니다!