Reputation: 7557
In a Spring 3 MVC project running on WebSphere Community Edition 2.1, I'm trying to configure my entityManagerFactory. However it seems that I can't override the PersistanceProvider. It defaults to OpenJPA, and even excluded this as a hidden class:
<sys:hidden-classes>
<sys:filter>org.apache.openjpa</sys:filter>
</sys:hidden-classes>
However I get the following error in WebSphere when trying to deploy the application:
javax.persistence.PersistenceException: Invalid or inaccessible provider class: org.apache.openjpa.persistence.PersistenceProviderImpl
Even though I am providing a different provider(HibernatePersistence) in persistance.xml:
<persistence-unit name="com.intl.cigna">
<description>
Persistence unit for the JPA implementation
</description>
<provider>org.hibernate.ejb.HibernatePersistence</provider>
<non-jta-data-source>java:comp/env/jdbc/myJndiDS</non-jta-data-source>
<properties>
<property name="hibernate.dialect" value="org.hibernate.dialect.SQLServer2008Dialect"/>
<property name="hibernate.show_sql" value="true" />
</properties>
</persistence-unit>
Upvotes: 2
Views: 1625
Reputation: 7557
You can override the persistence provider via a ServletContextListener.
First implement a PersistenceProviderResolver
:
public class HibernatePersistenceProviderResolver implements PersistenceProviderResolver {
private static final Logger LOGGER = LoggerFactory.getLogger(HibernatePersistenceProviderResolver.class);
private volatile PersistenceProvider persistenceProvider = new HibernatePersistence();
public List<PersistenceProvider> getPersistenceProviders() {
return Collections.singletonList(persistenceProvider);
}
public void clearCachedProviders() {
persistenceProvider = new HibernatePersistence();
}
public static void register() {
LOGGER.info("Registering HibernatePersistenceProviderResolver");
PersistenceProviderResolverHolder.setPersistenceProviderResolver(new HibernatePersistenceProviderResolver());
}
}
Then create an implemetation of a ServletContextListener
and 'register' the ProviderResolver:
public class HibernateContextListener implements ServletContextListener{
public void contextInitialized(ServletContextEvent sce) {
HibernatePersistenceProviderResolver.register();
}
public void contextDestroyed(ServletContextEvent sce) {
// nothing to do here
}
}
And add it as a listener in web.xml:
<listener>
<listener-class>my.context.listener.HibernateContextListener</listener-class>
</listener>
Upvotes: 1
Reputation: 23105
To deploy the new JPA provider as a part of your application:
Ensure persistence.xml <provider>
element points to the new JPA provider's implementation of javax.persistence.spi.PersistenceProvider
.
Build the new JPA persistence code into the application - deploy all necessary jars into the your application EAR / WAR / CLASSPATH.
Copy hibernate3.jar and the required 3rd party libraries available in lib/required Copy lib/jpa/hibernate-jpa-2.0-api-1.0.0.Final.jar to your classpath as well.
Configure the app server class loader order for your application - load the new JPA classes first. If the class loader is not configured properly, the JPA provider that is included with the application server is used by your application instead of the third-party JPA provider.
If you bundled the provider in an EAR file, in application modules that need JPA access, specify the third-party persistence provider binaries in the Manifest.mf class path.
If you bundled the provider in a WAR file, include the necessary provider binaries in the WEB-INF/lib directory of the web application.
To deploy the new JPA provider within a shared library:
Ensure persistence.xml <provider>
element points to the new JPA provider's implementation of javax.persistence.spi.PersistenceProvider
.
Define the persistence provider in a shared library
If the library is accessed by many applications, associate the shared library with the server class loader. Otherwise, associate the shared library with the application class loader.
Configure the class loader order for your application - load the new JPA classes first. If the class loader is not configured properly, the JPA provider that is included with the application server is used by your application instead of the third-party JPA provider.
Websphere 8 JPA provider configuration
Hibernate 3.5 configuration
WAS CE - overriding class load order
WAS CE 2.0 - using frameworks, including Hibernate
Upvotes: 1
Reputation: 4448
you have to add the following properties to your persistence.xml file:
<property
name="hibernate.transaction.factory_class"
value="org.hibernate.transaction.CMTTransactionFactory"
/>
<property
name="hibernate.transaction.manager_lookup_class"
value="org.hibernate.transaction.WebSphereExtendedJTATransactionLookup"
/>
Also have all hibernate .jar libs added to your package lib folder(.war or .ear) and than change the class loading policy for the server to be Parent Last instead of the default Parent First, you can change that using the Domain Manager Console (Dmgr) at:
Servers > $SERVER_NAME > Server Specific Application Settings
Restart your server and this should do the trick.
regards.
Upvotes: 0