Oracle 이 XA 를 위한 구성이 되어있지 않을 경우 다음과 같은 오류가 발생할 수 있다.

error
WARN[12-11-09 16:09:38]-Error in recovery (com.atomikos.logging.Slf4jLogger.logWarning(Slf4jLogger.java:24))
javax.transaction.xa.XAException
    at oracle.jdbc.xa.OracleXAResource.recover(OracleXAResource.java:709)
    at com.atomikos.datasource.xa.XATransactionalResource.recover(XATransactionalResource.java:579)
    at com.atomikos.datasource.xa.XATransactionalResource.endRecovery(XATransactionalResource.java:669)
    at com.atomikos.icatch.imp.TransactionServiceImp.recover(TransactionServiceImp.java:604)
    at com.atomikos.datasource.xa.XATransactionalResource.setRecoveryService(XATransactionalResource.java:495)
    at com.atomikos.icatch.system.Configuration.installRecoveryService(Configuration.java:252)
    at com.atomikos.icatch.standalone.UserTransactionServiceImp.init(UserTransactionServiceImp.java:269)
    at com.atomikos.icatch.config.UserTransactionServiceImp.init(UserTransactionServiceImp.java:405)
    at com.atomikos.icatch.config.UserTransactionServiceImp.init(UserTransactionServiceImp.java:569)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
    at java.lang.reflect.Method.invoke(Method.java:597)
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.invokeCustomInitMethod(AbstractAutowireCapableBeanFactory.java:1546)
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.invokeInitMethods(AbstractAutowireCapableBeanFactory.java:1487)
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.initializeBean(AbstractAutowireCapableBeanFactory.java:1419)
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:518)
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:455)
    at org.springframework.beans.factory.support.AbstractBeanFactory$1.getObject(AbstractBeanFactory.java:293)
    at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:222)
    at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:290)
    at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:192)
    at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:283)
    at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:192)
    at org.springframework.beans.factory.support.DefaultListableBeanFactory.preInstantiateSingletons(DefaultListableBeanFactory.java:585)
    at org.springframework.context.support.AbstractApplicationContext.finishBeanFactoryInitialization(AbstractApplicationContext.java:895)
    at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:425)
    at org.springframework.test.AbstractSingleSpringContextTests.createApplicationContext(AbstractSingleSpringContextTests.java:216)
    at org.springframework.test.AbstractSingleSpringContextTests.loadContextLocations(AbstractSingleSpringContextTests.java:192)
    at org.springframework.test.AbstractSingleSpringContextTests.loadContext(AbstractSingleSpringContextTests.java:172)
    at org.springframework.test.AbstractSpringContextTests.getContext(AbstractSpringContextTests.java:133)
    at org.springframework.test.AbstractSingleSpringContextTests.setUp(AbstractSingleSpringContextTests.java:101)
    at junit.framework.TestCase.runBare(TestCase.java:132)
    at org.springframework.test.ConditionalTestCase.runBare(ConditionalTestCase.java:79)
    at junit.framework.TestResult$1.protect(TestResult.java:110)
    at junit.framework.TestResult.runProtected(TestResult.java:128)
    at junit.framework.TestResult.run(TestResult.java:113)
    at junit.framework.TestCase.run(TestCase.java:124)
    at junit.framework.TestSuite.runTest(TestSuite.java:243)
    at junit.framework.TestSuite.run(TestSuite.java:238)
    at org.junit.internal.runners.JUnit38ClassRunner.run(JUnit38ClassRunner.java:83)
    at org.eclipse.jdt.internal.junit4.runner.JUnit4TestReference.run(JUnit4TestReference.java:49)
    at org.eclipse.jdt.internal.junit.runner.TestExecution.run(TestExecution.java:38)
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:467)
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:683)
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.run(RemoteTestRunner.java:390)
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.main(RemoteTestRunner.java:197)
 WARN[12-11-09 16:09:38]-ERROR IN RECOVERY (com.atomikos.logging.Slf4jLogger.logWarning(Slf4jLogger.java:24))
com.atomikos.datasource.ResourceException: Error in recovery
    at com.atomikos.datasource.xa.XATransactionalResource.recover(XATransactionalResource.java:590)
    at com.atomikos.datasource.xa.XATransactionalResource.endRecovery(XATransactionalResource.java:669)
    at com.atomikos.icatch.imp.TransactionServiceImp.recover(TransactionServiceImp.java:604)
    at com.atomikos.datasource.xa.XATransactionalResource.setRecoveryService(XATransactionalResource.java:495)
    at com.atomikos.icatch.system.Configuration.installRecoveryService(Configuration.java:252)
    at com.atomikos.icatch.standalone.UserTransactionServiceImp.init(UserTransactionServiceImp.java:269)
    at com.atomikos.icatch.config.UserTransactionServiceImp.init(UserTransactionServiceImp.java:405)
    at com.atomikos.icatch.config.UserTransactionServiceImp.init(UserTransactionServiceImp.java:569)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
    at java.lang.reflect.Method.invoke(Method.java:597)
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.invokeCustomInitMethod(AbstractAutowireCapableBeanFactory.java:1546)
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.invokeInitMethods(AbstractAutowireCapableBeanFactory.java:1487)
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.initializeBean(AbstractAutowireCapableBeanFactory.java:1419)
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:518)
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:455)
    at org.springframework.beans.factory.support.AbstractBeanFactory$1.getObject(AbstractBeanFactory.java:293)
    at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:222)
    at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:290)
    at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:192)
    at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:283)
    at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:192)
    at org.springframework.beans.factory.support.DefaultListableBeanFactory.preInstantiateSingletons(DefaultListableBeanFactory.java:585)
    at org.springframework.context.support.AbstractApplicationContext.finishBeanFactoryInitialization(AbstractApplicationContext.java:895)
    at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:425)
    at org.springframework.test.AbstractSingleSpringContextTests.createApplicationContext(AbstractSingleSpringContextTests.java:216)
    at org.springframework.test.AbstractSingleSpringContextTests.loadContextLocations(AbstractSingleSpringContextTests.java:192)
    at org.springframework.test.AbstractSingleSpringContextTests.loadContext(AbstractSingleSpringContextTests.java:172)
    at org.springframework.test.AbstractSpringContextTests.getContext(AbstractSpringContextTests.java:133)
    at org.springframework.test.AbstractSingleSpringContextTests.setUp(AbstractSingleSpringContextTests.java:101)
    at junit.framework.TestCase.runBare(TestCase.java:132)
    at org.springframework.test.ConditionalTestCase.runBare(ConditionalTestCase.java:79)
    at junit.framework.TestResult$1.protect(TestResult.java:110)
    at junit.framework.TestResult.runProtected(TestResult.java:128)
    at junit.framework.TestResult.run(TestResult.java:113)
    at junit.framework.TestCase.run(TestCase.java:124)
    at junit.framework.TestSuite.runTest(TestSuite.java:243)
    at junit.framework.TestSuite.run(TestSuite.java:238)
    at org.junit.internal.runners.JUnit38ClassRunner.run(JUnit38ClassRunner.java:83)
    at org.eclipse.jdt.internal.junit4.runner.JUnit4TestReference.run(JUnit4TestReference.java:49)
    at org.eclipse.jdt.internal.junit.runner.TestExecution.run(TestExecution.java:38)
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:467)
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:683)
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.run(RemoteTestRunner.java:390)
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.main(RemoteTestRunner.java:197)

또한 오라클 최신 드라이버를 항상 사용할 것을 권장한다. (오라클 9에 접속할 때도 마찬가지)

pom.xml
<dependency>
    <groupId>com.oracle</groupId>
    <artifactId>ojdbc6</artifactId>
    <version>11.2.0.3</version>
</dependency>
...
<repositories>
    <repository>
      <id>codelds</id>
    </repository>
  </repositories>

 

그리고 XA 를 위한 오라클 설정은 다음과 같다.

grant.sql
grant select on sys.dba_pending_transactions to <user name>;
grant select on sys.pending_trans$ to <user name>;
grant select on sys.dba_2pc_pending to <user name>;
grant execute on sys.dbms_system to <user name>;

 

참조 문서

웹로직 12c 에 아파치 dbcp 로 데이터 소스를 구성할 경우, 서버 자체가 응답이 없는(무한 대기 상태에 빠지는) 현상이 발생한다. 결국, 자체적인 데이터 소스를 구성하지 않고, 웹로직의 데이터 소스를 구성해 jndi 로 룩업하여 해결하였다. 아파치 dbcp 를 사용하기 위해서 다른 설정을 해야할 것인지, 아니면 그냥 버그인지는 모르겠으나 일단 좀 더 아름다운 구성이 맞을거 같아서 버그 리포팅은 안하기로 했다.


여튼, 이거 하느라고 하루를 날려버린 것도 있고, 웹로직에 오라클이 아닌 타 벤더의 JDBC 데이터 소스를 등록할 경우, 시간을 허비할 지 모르는 개발자들을 위해 블로깅을 해본다.


이 문서에서는 MS 사의 SQL Server 용 JDBC 등록하는 것에 대하여 작성할 것이다. 

본 문서에 사용된 환경 변수에 대한 패스 정보는 다음과 같다.


 변수

설명

예제 경로 
 WL_HOME  웹로직이 설치된 홈 디렉토리  C:\Oracle\Middleware\wlserver_12.1
 WLS_HOME  홈 디렉토리 하위 Server 디렉토리  C:\Oracle\Middleware\wlserver_12.1\serve

작업 절차는 크게 다음과 같다.

  • JDBC 드라이버를 클래스 패스에 등록한다.
  • 관리콘솔에서 데이터 소스를 등록한다.

참조 : http://docs.oracle.com/cd/E24329_01/web.1211/e24367/jdbc_datasources.htm#g1218593


1. JDBC 드라이버 클래스 패스에 등록


오라클에 접속할 경우에는 이미 라이브러리가 클래스 패스에 존재하므로, 이 부분은 지나쳐도 된다.


웹로직에서는 데이터소스를 등록할 경우, 유명한 벤더들의 DBMS 에 대한 설정은 이미 제공되고 있다. 하지만, 오라클 외 타 벤더들에 대한 JDBC 에 대한 설정만 제공하지, 드라이버를 클래스패스에 두고 있지는 않다.


즉, 웹로직 관리콘솔에서 등록한다고 해서 무조건 돌아갈 거 다라는 것은 아니다라는 것이다. 잘 만들어진 GUI 에 현혹 되면 안된다.


그러나, 웹로직에서는 클래스 패스에 해당 드라이버를 넣어주고 있지는 않지만, 참조용으로 제공은 하고 있다. 


해당 드라이버들은 WL_HOME\server\lib 에서 찾을 수 있으며, 파일명은 다음과 같다.

  • For DB2: wldb2.jar
  • For Informix: wlinformix.jar
  • For MS SQL Server: wlsqlserver.jar
  • For Sybase: wlsybase.jar

참조 : http://docs.oracle.com/cd/E24329_01/web.1211/e24376/dd.htm#JDBCP153



해당 파일을 찾았으면, 클래스 패스에 등록을 해야하는데 다음 2가지 위치에서 택일을 한다.


  • 모든 도메인에 해당 드라이버를 적용하고 싶을 경우, WL_HOME/common/bin 하위에 commEnv.cmd/sh 파일을 편집하여 WEBLOGIC_CLASSPATH 환경변수에 jar 파일 위치를 추가한다.
  • 특정한 웹로직 서버 도메인에 해당 드라이버를 적용하고 싶을 경우, 도메인디렉토리/bin 하위에 setDomainEnv.cmd/sh 파일을 편집하여 PRE_CLASSPATH 환경변수에 jar 파일 위치를 추가한다.

다음은 SQL Server 용 jar 를 특정 도메인 환경에 적용한 경우이다.


[setDomainEnv.cmd]

set POST_CLASSPATH=%POST_CLASSPATH%;%WLS_HOME%\lib\wlsqlserver.jar


참조 : http://docs.oracle.com/cd/E24329_01/web.1211/e24487/weblogicserver.htm#i1023430


설정이 모두 되었으면 서버를 재시작한다.

 


2. 관리 콘솔에서 데이터 등록


콘솔에서 등록은 위보다 더 쉽다. 나오는대로 잘 선택하면 해주면 된다.


관리 콘솔에 로그인 한 후 '서비스/데이터소스' 를 선택한 후 '추가' 버튼을 클릭한다.


jndi 에서 조회할 이름과 데이터소스명을 입력하고 데이터베이스 유형을 선택한다.


본 문서에서는 slothinkdb 명으로 MS SQL Server 를 선택했다.




데이터베이스 드라이버는 'Microsoft's MS SQL Server Driver (type4 XA) Versions:2005 and later' 를 선택한다.  




트랜잭션 옵션을 선택한다. MS SQL 은 별다른 트랜잭션 옵션이 없다. '다음' 을 클릭한다.



DB 정보를 입력하고 '다음' 을 클릭한다.



화면 하단 아래에서 '구성 테스트' 를 클릭하여 접속이 옳바르게 되는지 확인 한 후 '다음' 을 클릭한다.



배포할 서버를 선택한 후 '완료' 를 클릭한다.



이제 모든 설정이 완료되었으며, 배포된 서버에 있는 어플리케이션은 JNDI 룩업을 통해 해당 데이터소스를 사용할 수 있다.


* Tested. Oracle Weblogic 12c, MS SQL Server 2008 R2


hibernate3:hbm2doc 를 실행하던 중

[org.hibernate.connection.DriverManagerConnectionProvider]
problem closing pooled connection java.sql.SQLException: Io exception: Socket closed


와 같은 오류가 났다.

하이버네이트 JIRA(http://opensource.atlassian.com/projects/hibernate/browse/HBX-948) 에 의하면 오라클 서버 버젼과 jdbc 버젼이 다를 경우에 저런 메세지가 떨어진다고 한다.


나의 경우는 오라클 11g 버젼을 사용하고 있었는데, 예전 버젼을 사용하고 있어서 그랬다.

<dependency>
<groupId>com.oracle</groupId>
<artifactId>ojdbc14</artifactId>
<version>10.2.0.3.0</version>
</dependency>


다음의 최신 버젼을 사용하면 문제가 해결된다.
다음 버젼은 JDK 1.5 이상에서만 동작하며, JDBC 3.0 과 Oracle 9, 10, 그리고 11 을 지원한다. 올레!

<dependency>
<groupId>com.oracle</groupId>
<artifactId>ojdbc5</artifactId>
<version>11.1.0.7.0</version>
</dependency>

+ Recent posts