Right now I'm migrating some applications from JBoss 4 to JBoss 5.1.0, most of them I was able to migrate without a lot of headaches, by just fixing the packaging and library locations inside an EAR.
However I've stumbled on a particular application which is a WAR and uses TopLink essentials, since TopLink essentials bundles javax.persistence inside the jar, some problems arise when trying to deploy it in JBoss AS 5, because of the bundled JPA specification. So I did a little research and found out that TopLink Essentials has been discontinued, and has been replaced by EclipseLink. There's a simple migration guide, which I've followed, and was able to sucessfully deploy my war.
Unfortunately there's a problem, when trying to run the application I'm receiveing the following stack trace:
17:43:03,420 ERROR [STDERR] javax.persistence.PersistenceException: No Persistence provider for EntityManager named autenticador 17:43:03,420 ERROR [STDERR] at javax.persistence.Persistence.createEntityManagerFactory(Persistence.java:56) 17:43:03,420 ERROR [STDERR] at xx.yyy.zzzz.autenticador.persistencia.facade.AutenFacade.getEntityManager(AutenFacade.java:42) 17:43:03,420 ERROR [STDERR] at xx.yyy.zzzz.autenticador.persistencia.facade.AutenFacade.queryUsuariofindByLogin(AutenFacade.java:68) 17:43:03,420 ERROR [STDERR] at xx.yyy.zzzz.autenticador.negocio.appService.AutenAS.getUsuario(AutenAS.java:27) 17:43:03,420 ERROR [STDERR] at xx.yyy.zzzz.autenticador.servlet.AutenticadorAction.processaRequisicao(AutenticadorAction.java:68) 17:43:03,421 ERROR [STDERR] at xx.yyy.zzzz.autenticador.servlet.AutenticadorAction.doGet(AutenticadorAction.java:198) 17:43:03,421 ERROR [STDERR] at javax.servlet.http.HttpServlet.service(HttpServlet.java:617) 17:43:03,421 ERROR [STDERR] at javax.servlet.http.HttpServlet.service(HttpServlet.java:717) 17:43:03,421 ERROR [STDERR] at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:290) 17:43:03,421 ERROR [STDERR] at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206) 17:43:03,421 ERROR [STDERR] at org.jboss.web.tomcat.filters.ReplyHeaderFilter.doFilter(ReplyHeaderFilter.java:96) 17:43:03,421 ERROR [STDERR] at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:235) 17:43:03,421 ERROR [STDERR] at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206) 17:43:03,421 ERROR [STDERR] at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:235) 17:43:03,421 ERROR [STDERR] at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:191) 17:43:03,421 ERROR [STDERR] at org.jboss.web.tomcat.security.SecurityAssociationValve.invoke(SecurityAssociationValve.java:183) 17:43:03,421 ERROR [STDERR] at org.jboss.web.tomcat.security.JaccContextValve.invoke(JaccContextValve.java:95) 17:43:03,421 ERROR [STDERR] at org.jboss.web.tomcat.security.SecurityContextEstablishmentValve.process(SecurityContextEstablishmentValve.java:126) 17:43:03,421 ERROR [STDERR] at org.jboss.web.tomcat.security.SecurityContextEstablishmentValve.invoke(SecurityContextEstablishmentValve.java:70) 17:43:03,421 ERROR [STDERR] at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:127) 17:43:03,421 ERROR [STDERR] at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:102) 17:43:03,421 ERROR [STDERR] at org.jboss.web.tomcat.service.jca.CachedConnectionValve.invoke(CachedConnectionValve.java:158) 17:43:03,421 ERROR [STDERR] at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:109) 17:43:03,421 ERROR [STDERR] at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:330) 17:43:03,421 ERROR [STDERR] at org.apache.coyote.http11.Http11Processor.process(Http11Processor.java:829) 17:43:03,422 ERROR [STDERR] at org.apache.coyote.http11.Http11Protocol$Http11ConnectionHandler.process(Http11Protocol.java:598) 17:43:03,422 ERROR [STDERR] at org.apache.tomcat.util.net.JIoEndpoint$Worker.run(JIoEndpoint.java:447) 17:43:03,422 ERROR [STDERR] at java.lang.Thread.run(Thread.java:619)
Most of the posts in blogs and forums I've found on this issue, point to the possibility of missing jar files from the classpath, but I don't think it's the case, or at least it seems unlikely since I've rechecked the usual places. I've even tried removing the javax.persistence packages from the old toplink essentials jar, deployed it, and got stuck at the same place.
I'm not sure if this is due to conflicts with the underlying hibernate implementation, but I doubt since the persistence.xml has the provider specified, as you can see below:
<?xml version="1.0" encoding="UTF-8"?> <persistence xmlns="http://java.sun.com/xml/ns/persistence" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/persistence persistence_1_0.xsd" version="1.0"> <persistence-unit name="autenticador" transaction-type="RESOURCE_LOCAL"> <provider>org.eclipse.persistence.jpa.PersistenceProvider</provider> <non-jta-data-source>java:/autenticadorDS</non-jta-data-source> <class>xx.yyy.zzzz.autenticador.persistencia.entity.Aplicativo</class> <properties> <property name="eclipselink.session.customizer" value="xx.yyy.zzzz.autenticador.util.JPAToplinkSessionCustomizationUtil"/> <property name="eclipselink.target-database" value="Oracle"/> <property name="eclipselink.logging.level" value="ALL"/> <property name="eclipselink.cache.type.default" value="NONE"/> <!-- JBoss 5 --> <property name="eclipselink.weaving" value="false"/> <property name="eclipselink.target-server" value="JBoss"/> </properties> </persistence-unit> </persistence>
As you can see I'm using JPA outside of the container with no transactions, the data-source is configured as a no-tx-datasource, since I only want to read from this particular resource.
The only thing that comes to mind, is the possibility of having problems with the eclipselink.session.customizer property, since the class was made to work with TopLink essentials, and probably references implementations only available in that package, since the package names changed when it was aggregated into EclipseLink, but the error message doesn't indicate it at all.
As far as library version goes, I'm using eclipseLink-2.1.1, and it is inside the WEB-INF/lib dir of this particular war file, it's jboss-web.xml has classloading isolation configured as follows:
<jboss-web> <class-loading java2ClassLoadingCompliance="false"> <loader-repository> jboss.autenticador:archive=autenticador.war <loader-repository-config> java2ParentDelegation=false </loader-repository-config> </loader-repository> </class-loading> </jboss-web>
With this setting it should load the WEB-INF/lib jars first, and then the ones in the server and common/lib folders, in that order.
I'm a little lost as to why this is happening, and I was hoping for some healthy discussion which might lead to a possible solution.
Ok, so I've investigated a little further and found some other things.
First I tried using an older version of eclipseLink, version 1.1.4, I don't know but I thought that maybe eclipseLink 2.x.x releases are JPA 2.0, so I thought I could give that a try.
So now, instead of the whole no persistence provider, I get the error because of the SessionCustomizer, which at first I thought was odd.
Form what I read about TopLink's SessionCustomizer, it is normally used when running applications outside of a container, so I thought about commenting the line out of the persistence.xml, but it seems that even commenting out the line, still throws a NoClassDefFoundError: oracle/toplink/essentials/tools/sessionconfiguration/SessionCustomizer on my persistence unit, a little odd.
I'll try cleaning up the caches for it, sadly it's a matter of changing imports since, from what the documentation says, is that mainly package names have been renamed.
I'll post updates if I have any!
Well, the bottom line is, when deploying a legacy Toplink-essentials or Glassfish V2 application in your JBoss AS 5, you need to switch from TopLink-Essentials to EclipseLink, and follow their guide. But one thing is important you will need the version 1.x.x of eclipseLink, otherwise you might get the error in my original post.
Hope this helps someone in the future.
As far as my migration goes, since it is using a custom SessionCustomizer, I can't just switch it off, I'll need to see if I can upgrade the source code in order to achieve compatibility.