- hibernate 버전: 5.0.12-FINAL


스프링 배치 잡 작업 중 뜬금없이 하이버네이트의 EntityEntryContext 클래스의 reentrantSafeEntityEntries() 메서드에서 ArrayIndexOutOfBoundsException이 발생했다.


java.lang.ArrayIndexOutOfBoundsException: 6673

at org.hibernate.engine.internal.EntityEntryContext.reentrantSafeEntityEntries(EntityEntryContext.java:319)

at org.hibernate.engine.internal.StatefulPersistenceContext.reentrantSafeEntityEntries(StatefulPersistenceContext.java:1128)

at org.hibernate.engine.internal.AbstractFlushingEventListener.prepareEntityFlushes(AbstractFlushingEventListener.java:136)

...


검색하다가 hibernate 커뮤니티의 JIRA에서 동일한 이슈[각주:1]를 발견할 수 있었는데 해당 이슈 보고자도 멀티스레드 환경에서 엔티티를 저장하는 과정에서 가끔 발생했다고 한다.

커멘트의 마지막 부분에 관련 이슈[각주:2]와 함께 이슈를 클로즈한다고 하여 따라가보니 5.1 버전에 픽스되었다고 하여 일단은 버전업을 해보는 것으로 해결.

  1. https://hibernate.atlassian.net/browse/HHH-8880 [본문으로]
  2. https://hibernate.atlassian.net/browse/HHH-10795 [본문으로]

하이버네이트 튜토리얼을 보며 따라하고 있는데 SessionFactory 빈을 생성하는 과정에서 예외가 발생하면서 아래와 같은 스택을 뿌리며 생성에 실패한다.


Caused by: java.util.MissingFormatArgumentException: Format specifier '%s'

at java.util.Formatter.format(Formatter.java:2519) ~[na:1.8.0_25]

at java.util.Formatter.format(Formatter.java:2455) ~[na:1.8.0_25]

at java.lang.String.format(String.java:2927) ~[na:1.8.0_25]

at org.jboss.logging.Slf4jLocationAwareLogger.doLogf(Slf4jLocationAwareLogger.java:81) ~[jboss-logging-3.1.3.GA.jar:3.1.3.GA]

at org.jboss.logging.Logger.debugf(Logger.java:553) ~[jboss-logging-3.1.3.GA.jar:3.1.3.GA]

at org.hibernate.annotations.common.util.StandardClassLoaderDelegateImpl.classForName(StandardClassLoaderDelegateImpl.java:53) ~[hibernate-commons-annotations-4.0.4.Final.jar:4.0.4.Final]

at org.hibernate.cfg.annotations.SimpleValueBinder.fillSimpleValue(SimpleValueBinder.java:491) ~[hibernate-core-4.3.5.Final.jar:4.3.5.Final]

at org.hibernate.cfg.SetSimpleValueTypeSecondPass.doSecondPass(SetSimpleValueTypeSecondPass.java:42) ~[hibernate-core-4.3.5.Final.jar:4.3.5.Final]

at org.hibernate.cfg.Configuration.processSecondPassesOfType(Configuration.java:1470) ~[hibernate-core-4.3.5.Final.jar:4.3.5.Final]

at org.hibernate.cfg.Configuration.secondPassCompile(Configuration.java:1418) ~[hibernate-core-4.3.5.Final.jar:4.3.5.Final]

at org.hibernate.cfg.Configuration.buildSessionFactory(Configuration.java:1844) ~[hibernate-core-4.3.5.Final.jar:4.3.5.Final]

at org.hibernate.cfg.Configuration.buildSessionFactory(Configuration.java:1928) ~[hibernate-core-4.3.5.Final.jar:4.3.5.Final]

at org.springframework.orm.hibernate4.LocalSessionFactoryBuilder.buildSessionFactory(LocalSessionFactoryBuilder.java:372) ~[spring-orm-4.1.6.RELEASE.jar:4.1.6.RELEASE]

at org.springframework.orm.hibernate4.LocalSessionFactoryBean.buildSessionFactory(LocalSessionFactoryBean.java:454) ~[spring-orm-4.1.6.RELEASE.jar:4.1.6.RELEASE]

at org.springframework.orm.hibernate4.LocalSessionFactoryBean.afterPropertiesSet(LocalSessionFactoryBean.java:439) ~[spring-orm-4.1.6.RELEASE.jar:4.1.6.RELEASE]

at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.invokeInitMethods(AbstractAutowireCapableBeanFactory.java:1633) ~[spring-beans-4.1.6.RELEASE.jar:4.1.6.RELEASE]

at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.initializeBean(AbstractAutowireCapableBeanFactory.java:1570) ~[spring-beans-4.1.6.RELEASE.jar:4.1.6.RELEASE]

... 43 common frames omitted





구글링으로 예외와 관련한 것들을 찾아보다가, 비슷한 유형이 나타나지 않길래 라이브러리 내에서 어떤 부분이 문제인지를 확인하려고 org.hibernate.annotations.common.util.StandardClassLoaderDelegateImpl 클래스를 따라가보니 아래 부분에서 예외가 발생했다.


catch ( Throwable ignore ) {

log.debugf( "Unable to locate Class [%s] using TCCL, falling back to HCANN ClassLoader" );

}


빨간색으로 표기한 %s에 전달되어야 할 문자열을 전달하지 않아서 발생하는 예외였다. 실수는 할 수 있지만.. 유틸리티성 클래스라 테스트 커버리지에 포함되지 않아서인지 릴리즈에 버젓이 나 버그요 어디 한번 실행해 보시지 하는 태도라니.


이는 하이버네이트 ORM 4.3.5.Final 버전에서 발생하며, 이 후 버전에서는 고쳐진 듯 하다. (4.3.10.Final 버전으로 확인하니 예외가 발생하지 않는다.)


사실 상용 프레임워크나 소프트웨어는 거의 사용하지 않고 오픈 소스를 주로 이용하다보니, 검증없이 신뢰하기 마련인데, 이번 계기로 모든 것에 의심을 가지자는 태도를 다시 갖춰야겠다.

+ Recent posts