XA Transaction & Two phase commit
qwerty2 Apr 20, 2009 1:39 PMHello !
I have two datasources MySql 5.1 and Postgres 8.0 and I'm trying to implement a standard bank example with XA Transaction and 2 phase commit. Unfortunately, I have a problem that I can't resolve.
Please help me !
This is my configurations:
persistance.xml
<persistence-unit name="mybank"> <provider>org.hibernate.ejb.HibernatePersistence</provider> <jta-data-source>java:/mysqlXADatasource</jta-data-source> <properties> <property name="hibernate.dialect" value="org.hibernate.dialect.MySQLDialect"/> <property name="hibernate.hbm2ddl.auto" value="update"/> <property name="hibernate.show_sql" value="true"/> <property name="hibernate.format_sql" value="true"/> <property name="jboss.entity.manager.factory.jndi.name" value="java:/mybankEntityManagerFactory"/> </properties> </persistence-unit> <persistence-unit name="pgbank"> <provider>org.hibernate.ejb.HibernatePersistence</provider> <jta-data-source>java:/pgbankDatasource</jta-data-source> <properties> <property name="hibernate.dialect" value="org.hibernate.dialect.PostgreSQLDialect"/> <property name="hibernate.hbm2ddl.auto" value="update"/> <property name="hibernate.show_sql" value="true"/> <property name="hibernate.format_sql" value="true"/> <property name="jboss.entity.manager.factory.jndi.name" value="java:/pgbankEntityManagerFactory"/> </properties> </persistence-unit>
seamxa-ds.xml
<datasources> <xa-datasource> <jndi-name>mysqlXADatasource</jndi-name> <xa-datasource-class>com.mysql.jdbc.jdbc2.optional.MysqlXADataSource</xa-datasource-class> <xa-datasource-property name="ServerName">localhost</xa-datasource-property> <xa-datasource-property name="PortNumber">3306</xa-datasource-property> <xa-datasource-property name="DatabaseName">mybank</xa-datasource-property> <xa-datasource-property name="User">root</xa-datasource-property> <xa-datasource-property name="Password">mysql</xa-datasource-property> <track-connection-by-tx></track-connection-by-tx> </xa-datasource> <xa-datasource> <jndi-name>pgbankDatasource</jndi-name> <xa-datasource-class>org.postgresql.xa.PGXADataSource</xa-datasource-class> <xa-datasource-property name="ServerName">localhost</xa-datasource-property> <xa-datasource-property name="PortNumber">5432</xa-datasource-property> <xa-datasource-property name="DatabaseName">pgbank</xa-datasource-property> <xa-datasource-property name="User">postgres</xa-datasource-property> <xa-datasource-property name="Password">postgres</xa-datasource-property> <track-connection-by-tx></track-connection-by-tx> </xa-datasource> </datasources>
components.xml
<core:init debug="@debug@" jndi-pattern="@jndiPattern@"/> <core:manager concurrent-request-timeout="500" conversation-timeout="120000" conversation-id-parameter="cid" parent-conversation-id-parameter="pid"/> <persistence:managed-persistence-context name="entityManager" auto-create="true" persistence-unit-jndi-name="java:/seamxaEntityManagerFactory"/> <drools:rule-base name="securityRules"> <drools:rule-files> <value>/security.drl</value> </drools:rule-files> </drools:rule-base> <security:rule-based-permission-resolver security-rules="#{securityRules}"/> <security:identity authenticate-method="#{authenticator.authenticate}" remember-me="true"/> <event type="org.jboss.seam.security.notLoggedIn"> <action execute="#{redirect.captureCurrentView}"/> </event> <event type="org.jboss.seam.security.loginSuccessful"> <action execute="#{redirect.returnToCapturedView}"/> </event> <mail:mail-session host="localhost" port="2525" username="test" password="test" />
Test.java
@Stateless @Name("testy") @Transactional public class Test implements TestI { @PersistenceContext(unitName="pgbank") private EntityManager entityManager; @PersistenceContext(unitName="mybank") private EntityManager em; @Transactional(TransactionPropagationType.REQUIRED) public void start() { int error = 0; em.createQuery("update Account a set balance = 33000 where id = 1").executeUpdate(); if (error != 0) throw new EJBException("ERROR !!"); entityManager.createQuery("update Account a set balance = 33000 where id = 1").executeUpdate(); } }
JBoss 4.2.3 Log
13:21:46,625 INFO [STDOUT] Hibernate: update account set balance=33000 where id=1 13:21:46,656 INFO [STDOUT] Hibernate: update account set balance=33000 where id=1 13:21:46,781 WARN [loggerI18N] [com.arjuna.ats.internal.jta.resources.arjunacore.preparefailed] [com.arjuna.ats.internal.jta.resources.arjunacore.preparefailed] XAResourceRecord.prepare - prepare failed with exception XAException.XAER_RMERR 13:21:46,781 WARN [arjLoggerI18N] [com.arjuna.ats.arjuna.coordinator.BasicAction_50] - Prepare phase of action a01040f:1162:49ec5a80:37 received heuristic decision: TwoPhaseOutcome.HEURISTIC_HAZARD 13:21:46,781 WARN [arjLoggerI18N] [com.arjuna.ats.arjuna.coordinator.BasicAction_36] - BasicAction.End() - prepare phase of action-id a01040f:1162:49ec5a80:37 failed. 13:21:46,781 WARN [arjLoggerI18N] [com.arjuna.ats.arjuna.coordinator.BasicAction_37] - Received heuristic: TwoPhaseOutcome.HEURISTIC_HAZARD . 13:21:46,781 WARN [arjLoggerI18N] [com.arjuna.ats.arjuna.coordinator.BasicAction_38] - Action Aborting 13:21:46,812 WARN [SeamPhaseListener] uncaught exception, passing to exception handler java.lang.IllegalStateException: Could not commit transaction at org.jboss.seam.jsf.SeamPhaseListener.commitOrRollback(SeamPhaseListener.java:626) at org.jboss.seam.jsf.SeamPhaseListener.commitOrRollback(SeamPhaseListener.java:605) at org.jboss.seam.jsf.SeamPhaseListener.handleTransactionsAfterPhase(SeamPhaseListener.java:343) at org.jboss.seam.jsf.SeamPhaseListener.afterServletPhase(SeamPhaseListener.java:243) at org.jboss.seam.jsf.SeamPhaseListener.afterPhase(SeamPhaseListener.java:194) at com.sun.faces.lifecycle.Phase.handleAfterPhase(Phase.java:175) at com.sun.faces.lifecycle.Phase.doPhase(Phase.java:114) at com.sun.faces.lifecycle.LifecycleImpl.render(LifecycleImpl.java:139) at javax.faces.webapp.FacesServlet.service(FacesServlet.java:266) at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:290) at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206) at org.jboss.seam.servlet.SeamFilter$FilterChainImpl.doFilter(SeamFilter.java:83) at org.jboss.seam.web.IdentityFilter.doFilter(IdentityFilter.java:38) at org.jboss.seam.servlet.SeamFilter$FilterChainImpl.doFilter(SeamFilter.java:69) at org.jboss.seam.web.MultipartFilter.doFilter(MultipartFilter.java:90) at org.jboss.seam.servlet.SeamFilter$FilterChainImpl.doFilter(SeamFilter.java:69) at org.jboss.seam.web.ExceptionFilter.doFilter(ExceptionFilter.java:64) at org.jboss.seam.servlet.SeamFilter$FilterChainImpl.doFilter(SeamFilter.java:69) at org.jboss.seam.web.RedirectFilter.doFilter(RedirectFilter.java:45) at org.jboss.seam.servlet.SeamFilter$FilterChainImpl.doFilter(SeamFilter.java:69) at org.ajax4jsf.webapp.BaseXMLFilter.doXmlFilter(BaseXMLFilter.java:150) at org.ajax4jsf.webapp.BaseFilter.handleRequest(BaseFilter.java:267) at org.ajax4jsf.webapp.BaseFilter.processUploadsAndHandleRequest(BaseFilter.java:379) at org.ajax4jsf.webapp.BaseFilter.doFilter(BaseFilter.java:506) at org.jboss.seam.web.Ajax4jsfFilter.doFilter(Ajax4jsfFilter.java:56) at org.jboss.seam.servlet.SeamFilter$FilterChainImpl.doFilter(SeamFilter.java:69) at org.jboss.seam.web.LoggingFilter.doFilter(LoggingFilter.java:58) at org.jboss.seam.servlet.SeamFilter$FilterChainImpl.doFilter(SeamFilter.java:69) at org.jboss.seam.debug.hot.HotDeployFilter.doFilter(HotDeployFilter.java:44) at org.jboss.seam.servlet.SeamFilter$FilterChainImpl.doFilter(SeamFilter.java:69) at org.jboss.seam.servlet.SeamFilter.doFilter(SeamFilter.java:158) at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:235) at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206) at org.jboss.web.tomcat.filters.ReplyHeaderFilter.doFilter(ReplyHeaderFilter.java:96) at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:235) at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206) at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:230) at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:175) at org.jboss.web.tomcat.security.SecurityAssociationValve.invoke(SecurityAssociationValve.java:182) at org.apache.catalina.authenticator.AuthenticatorBase.invoke(AuthenticatorBase.java:432) at org.jboss.web.tomcat.security.JaccContextValve.invoke(JaccContextValve.java:84) at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:127) at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:102) at org.jboss.web.tomcat.service.jca.CachedConnectionValve.invoke(CachedConnectionValve.java:157) at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:109) at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:262) at org.apache.coyote.http11.Http11Processor.process(Http11Processor.java:844) at org.apache.coyote.http11.Http11Protocol$Http11ConnectionHandler.process(Http11Protocol.java:583) at org.apache.tomcat.util.net.JIoEndpoint$Worker.run(JIoEndpoint.java:446) at java.lang.Thread.run(Unknown Source) Caused by: javax.transaction.HeuristicMixedException at com.arjuna.ats.internal.jta.transaction.arjunacore.TransactionImple.commitAndDisassociate(TransactionImple.java:1397) at com.arjuna.ats.internal.jta.transaction.arjunacore.BaseTransaction.commit(BaseTransaction.java:135) at com.arjuna.ats.jbossatx.BaseTransactionManagerDelegate.commit(BaseTransactionManagerDelegate.java:87) at org.jboss.tm.usertx.client.ServerVMClientUserTransaction.commit(ServerVMClientUserTransaction.java:140) at org.jboss.seam.transaction.UTTransaction.commit(UTTransaction.java:52) at org.jboss.seam.jsf.SeamPhaseListener.commitOrRollback(SeamPhaseListener.java:614) ... 49 more
What's wrong with my code ?