Transaction Management

Hibernate에서 지원하는 Transaction 관리 방법에는 크게 JDBC, JTA, CMT 세 가지가 있다. 본 페이지에서는 일반적으로 가장 많이 사용하는 JDBC, JTA 기반의 Transaction 관리 방법에 대해서 설명하겠다.

JDBC - HibernateTransactionManager

HibernateTransactionManager는 DataSource를 사용하여 Local Transaction과 Hibernate Session을 관리한다. 따라서 HibernateTransactionManager는 LocalSessionFactory Bean에 의존성을 가지고 있으므로 반드시 LocalSessionFactory와 함께 사용되어야 한다.
  • Configuration
  • 다음은 Spring Framework의 org.springframework.orm.hibernate3.HibernateTransactionManager를 이용하여 Hibernate 기반에서 Transaction을 관리하기 위한 context-transaction.xml 파일의 일부이다.
    <bean id="transactionManager"
    	class="org.springframework.orm.hibernate3.HibernateTransactionManager">
    	<property name="sessionFactory" ref="sessionFactory" />
    </bean>
    
    Spring의 TransactionManager 설정 방법에 대해서는 본 매뉴얼 >> Tech. Service >> Transaction 을 참고한다.

  • Test Case
  • 다음은 org.springframework.orm.hibernate3.HibernateTransactionManager를 이용하여 Transaction 관리 기능을 테스트하기 위한 HibernateJDBCTransactionManagerTest.java 의 일부이다.
    public class HibernateJDBCTransactionManager extends
    	AbstractTransactionalDataSourceSpringContextTests {
    
    <!--중략 -->
    
    /**
     * [Flow #-1] Positive Case : HibernateTransactionManager Rollback을 이용하여,
     * 초기화 데이터의 입력 작업을 취소시킨 후, 데이터가 제대로 Rollback되었는지 검증한다.
     * 
     * @throws Exception
     *             throws exception which is from hibernate
     */
    	public void testRollback() throws Exception {
    		// 1. insert init data
    		Session session = sessionFactory.getCurrentSession();
    		SetUpInitData.initializeData(session);
    	
    		// 2. rollback transaction
    		isRollback();
    		endTransaction();
    	
    		// 3. begin a new transaction
    		startNewTransaction();
    	
    		// 4. check if insertion is rollbacked
    		Movie movie = (Movie) sessionFactory.getCurrentSession().get(
    				Movie.class, "MV-00001");
    		assertNull("fail to rollback init data.", movie);
    	}
    
    	/**
    	 * [Flow #-2] Positive Case : HibernateTransactionManager Commit을 이용하여, 초기화
    	 * 데이터의 입력 작업을 DB에 반영시킨 후, 데이터가 제대로 Commit되었는지 검증한다.
    	 * 
    	 * @throws Exception
    	 *             throws exception which is from hibernate
    	 */
    	public void testCommit() throws Exception {
    		// 1. insert init data
    		Session session = sessionFactory.getCurrentSession();
    		SetUpInitData.initializeData(session);
    
    		// 2. commit transaction
    		setComplete();
    		endTransaction();
    
    		// 3. begin a new transaction
    		startNewTransaction();
    
    		// 4. check if insertion is successful
    		Movie movie = (Movie) sessionFactory.getCurrentSession().get(
    				Movie.class, "MV-00001");
    		assertNotNull("fail to add a movie.", movie);
    	}
    }

JTA - JTATransactionManager

JTATransactionManager 서비스는 JTA를 사용한 Global Transaction 관리 부분을 추상화하여 해당 서비스가 JTA,JNDI 등에 종속적이지 않게 구현 가능 하도록 도와준다.
  • Configuration
  • 아래는 JTATransactionManager의 속성을 정의한 context-transaction.xml 파일의 일부이다.
    <bean id="transactionManager"
    	class="org.springframework.transaction.jta.WebLogicJtaTransactionManager"/>
    위에서 볼 수 있듯이 Hibernate 기반에서 JTA Transaction 관리는 SpringJDBC를 사용 할 때와 다르지 않다. 상세한 속성 정의 방법에 대해서는 JTA Transaction Service 를 참고한다.

  • Test Case
  • 다음은 WebLogicJtaTransactionManager를 이용해 Transaction 관리 기능을 테스트 하는 HibernateJTATransactionManagerTest.java 의 일부이다.
    public class HibernateJTATransactionManager extends
    		AbstractTransactionalDataSourceSpringContextTests {
    	
    <!-- 중략 -->
    
    	/**
    	 * [Flow #-1] Positive Case : WebLogicJtaTransactionManager Rollback을 이용하여,
    	 * 초기화 데이터의 입력 작업을 취소시킨 후, 데이터가 제대로 Rollback되었는지 검증한다.
    	 * 
    	 * @throws Exception
    	 *             throws exception which is from hibernate
    	 */
    	public void testRollback() throws Exception {
    		// 1. insert init data
    		Session session = sessionFactory.getCurrentSession();
    		SetUpInitData.initializeData(session);
    
    		// 2. rollback transaction
    		isRollback();
    		endTransaction();
    
    		// 3. begin a new transaction
    		startNewTransaction();
    
    		// 4. check if insertion is rollbacked
    		Movie movie = (Movie) sessionFactory.getCurrentSession().get(
    				Movie.class, "MV-00001");
    		assertNull("fail to rollback init data.", movie);
    	}
    
    	/**
    	 * [Flow #-2] Positive Case : WebLogicJtaTransactionManager Commit을 이용하여,
    	 * 초기화 데이터의 입력 작업을 DB에 반영시킨 후, 데이터가 제대로 Commit되었는지 검증한다.
    	 * 
    	 * @throws Exception
    	 *             throws exception which is from hibernate
    	 */
    	public void testCommit() throws Exception {
    		// 1. insert init data
    		Session session = sessionFactory.getCurrentSession();
    		SetUpInitData.initializeData(session);
    
    		// 2. commit transaction
    		setComplete();
    		endTransaction();
    
    		// 3. begin a new transaction
    		startNewTransaction();
    
    		// 4. check if insertion is successful
    		Movie movie = (Movie) sessionFactory.getCurrentSession().get(
    				Movie.class, "MV-00001");
    		assertNotNull("fail to add a movie.", movie);
    	}
    }

Resources

  • 다운로드
  • 샘플 테스트 코드를 포함하고 있는 anyframe-hibernatetest-src.zip 파일을 다운받은 후, 테스트 환경 설정 을 참조하여 위에서 제시한 예제 코드 (src/test/java 폴더의 anyframe.core.hibernate.transaction 패키지에 속한 *Test.java)를 실행해 볼 수 있다.
    Name
    Download
    anyframe-hibernatetest-src.zip
    Download