====== Hibernate Test ======
* [[http://blog.schauderhaft.de/2011/03/13/testing-databases-with-junit-and-hibernate-part-1-one-to-rule-them/|Testing Databases with JUnit and Hibernate Part 1: One to Rule them]]
* [[http://blog.schauderhaft.de/2011/03/20/testing-databases-with-junit-and-hibernate-part-2-the-mother-of-all-things/|Testing Databases with JUnit and Hibernate Part 2: The Mother of All Things]]
* [[http://blog.schauderhaft.de/2011/03/27/testing-databases-with-junit-and-hibernate-part-3-cleaning-up-and-further-ideas/|Testing Databases with JUnit and Hibernate Part 3: Cleaning up and Further Ideas]]
===== Hibernate Test Case Template =====
* Hibernate Issue Reporting 등을 할 때 테스트 케이스를 만들어서 제공해야 한다.
* [[http://in.relation.to/2015/06/26/hibernate-test-case-templates/|Hibernate Test Case Templates]]
* [[https://github.com/hibernate/hibernate-test-case-templates|hibernate-test-case-templates github]]
* 자기가 테스트하고자하는 버전의 Template을 다운로드하여 자신만의 프로젝트에 복사해 넣고 이미 만들어져 있는 테스트 케이스 파일을 수정해서 해본다.
* ''org.hibernate:hibernate-testing:${version.org.hibernate}'' 에 의존성을 가지고서 ''ORMUnitTestCase''를 참조하여 수정해서 만들면 좋다.
* [[https://github.com/hibernate/hibernate-orm/wiki/Hibernate-JUnit-Infastructure|Hibernate JUnit Infrastructure]]
===== hibernate-testing 사용시 Jboss Logging 문제 =====
hibernate-testing 사용시 아래와 같이 jboss logging에 문제가 생길 수 있다.
java.lang.NoSuchMethodError: org.jboss.logging.Logger.getMessageLogger(Ljava/lang/Class;Ljava/lang/String;)Ljava/lang/Object;
이 이유는 hibernate-testing이 의존하고 있는 ''jboss-common-core'' -> ''org.jboss.logging:jboss-logging-spi''가 ''jboss-logging''과 동일한 패키지의 ''Logger'' 클래스를 구현하고 있어서 두 라이브러리간 충돌이 발생하기 때문이다.
''org.jboss.logging:jboss-logging-spi'' exclude 처리한다.
testCompile(group: 'org.hibernate', name: 'hibernate-testing', version: hibernateVersion) {
exclude group: 'org.jboss.logging', module: 'jboss-logging-spi'
}
===== Hibernate 4.2 미만 Spock Spec 기본 뼈대 =====
/**
* Hibernate/JPA testing specification.
*/
abstract class AbstractHibernateSessionSpec extends Specification {
Configuration configuration
SessionFactory sf
Session session
void setup() {
configuration = new Configuration();
configuration.addAnnotatedClass(Article)
configuration.setProperty("hibernate.show_sql", "false")
configuration.setProperty("hibernate.format_sql", "true")
configuration.setProperty("hibernate.dialect", "org.hibernate.dialect.H2Dialect")
configuration.setProperty("hibernate.connection.driver_class", "org.h2.Driver")
configuration.setProperty("hibernate.connection.url", "jdbc:h2:mem:testdb;DB_CLOSE_DELAY=-1")
configuration.setProperty("hibernate.connection.username", "sa")
configuration.setProperty("hibernate.hbm2ddl.auto", "create-drop")
// hibernate 4.2.x 미만 의 ServiceRegistryBuilder 설정.
// 4.x 끼리도 버전마다 조금씩 달라질 수 있다.
def srBuilder = new ServiceRegistryBuilder().applySettings(configuration.getProperties())
def serviceRegistry = srBuilder.buildServiceRegistry()
sf = configuration.buildSessionFactory(serviceRegistry);
session = sf.openSession()
}
void cleanup() {
session.close()
sf.close()
}
}
// 테스트시 직접 Connection을 맺어 쿼리를 실행하고 검사하고 싶을 경우
session.doWork({ Connection con ->
groovy.sql.Sql sql = new groovy.sql.Sql(con)
// work with Sql object
} as Work)
===== Hibernate 5.2 / Java 8 Test with lambda =====
* [[http://in.relation.to/2016/09/15/integration-tests-and-java-8-lambdas/|How to simplify JPA and Hibernate integration testing using Java 8 lambdas]]
* ''hibernate-testing'' 의존성을 걸고 다음과 같이 테스트하면 ''EntityManager''나 ''Session'' 의 Life Cycle을 자동으로 관리하면서 테스트 할 수 있다.
import static org.hibernate.testing.transaction.TransactionUtil.*;
doInJPA( this::entityManagerFactory, entityManager -> {
entityManager.persist( item );
assertTrue( entityManager.contains( item ) );
} );
// or
doInHibernate( this::sessionFactory, session -> {
session.persist( item );
assertTrue( session.contains( item ) );
} );