Quartz 사용 시 트랜잭션 관리에 주의해야 하는 이유

Spring의 트랜잭션(@Transactional)은 AOP(Aspect-Oriented Programming)를 기반으로 동작한다.

즉, Spring은 @Transactional 프록시 객체를 생성해서 메서드 전/후에 트랜잭션을 시작하고 커밋하거나 롤백한다.

Quartz Job은 Spring 컨텍스트 바깥의 ThreadPool에서 새로 만든 스레드를 통해 Job을 수행한다. 따라서, Spring Bean으로 등록되지 않은 Job은 트랜잭션 관리가 불가능하다.


트랜잭션 관리 방법

1. Quartz Job 클래스를 Spring Bean으로 등록(SpringBeanJobFactory)

@Bean
public SchedulerFactoryBean schedulerFactoryBean(DataSource dataSource, ApplicationContext applicationContext) {
    SchedulerFactoryBean factory = new SchedulerFactoryBean();

    // 트랜잭션 데이터소스 설정
    factory.setDataSource(dataSource);

    // Spring JobFactory 설정
    SpringBeanJobFactory jobFactory = new SpringBeanJobFactory();
    jobFactory.setApplicationContext(applicationContext);
    factory.setJobFactory(jobFactory);

    return factory;
}

2. 수동 트랜잭션

TransactionTemplate이나 PlatformTansactionManaer를 통해 수동으로 트랜잭션을 관리한다.

@Autowired
private PlatformTransactionManager transactionManager;

public void executeJob() {
    TransactionTemplate transactionTemplate = new TransactionTemplate(transactionManager);
    transactionTemplate.executeWithoutResult(status -> {
        // 트랜잭션 내에서 수행할 로직
        accountRepository.updateSomething();
    });
}