Developing JPA applications with Oracle WLS
Developing JPA applications with Oracle WLS is not different from other Java EE 6 compliant application servers. The only difference consists in the persistence provider, which is different from the other application server’s providers discussed in this book.
Oracle TopLink is the default persistence provider in WebLogic Server 12c. It is a comprehensive standards-based object-persistence and object-transformation framework that provides APIs, schemas and run-time services for the persistence layer of an application.
The core component of TopLink is the EclipseLink project’s produced libraries and utilities. EclipseLink is the open source implementation of the development framework and the runtime provided in TopLink.
Here’s a sample persistence.xml which references a datasource named “jdbc/OracleDS”:
<persistence xmlns=”http://java.sun.com/xml/ns/persistence” version=”2.0″>
<persistence-unit name=”persistenceUnit”>
<provider>org.eclipse.persistence.jpa.PersistenceProvider</provider>
<jta-data-source>jdbc/OracleDS</jta-data-source>
<class>com.model.Property</class>
</persistence-unit>
</persistence>
Configuring EclipseLink’s shared cache
By default, EclipseLink uses a shared object cache to cache objects read from the database, in order to avoid repeated database access. This is pretty like the Hibernate second level cache feature. One important difference with Hibernate JPA Provider (discussed in the JBoss EAP Part) is that support for second level cache in EclipseLink is turned on by default; thus entities which are read are L2 cached. When using Hibernate, on the other hand, just the first level cache is enabled by default.
One more difference is that EclipseLink caches actual entities in L2, while Hibernate caches just the entity id and the state in L2.
You can disable the L2 default behavior in several ways, for example by adding in your persistence.xml the following property:
<property name=”eclipselink.cache.shared.default” value=”false”/>
Or use the JPA 2.0 persistence unit element in your persistence.xml:
<shared-cache-mode>ENABLE_SELECTIVE</shared-cache-mode>
This will require tagging your Entities with Cacheable = false in order to disable caching:
@Entity
@Cacheable(false)
public class Bean { …
}
Referencing resources in the JNDI tree
One of the key issues when porting Java EE applications between different application servers is the different JNDI naming policy used. This is a frequent issue when your applications reference Java EE resources (such as data sources, JMS objects, etc) by its JNDI name. For example, the following code introduces a portability issue, since it hardcodes the JNDI name of a resource in it:
public class TestEJB {
@Resource(mappedName=”jdbc/MyDataSource”)
private DataSource datasource;
}
One way to reduce the impact on portability, is introducing the resource name as an alias for the JNDI name which will be declared in XML deployment descriptors. In our case, here’s how to improve the above example EJB:
public class TestEJB {
@Resource(name=”MyDataSource”)
private DataSource datasource;
}
Then, in your ejb-jar.xml, you can declare the actual JNDI binding to your data source as follows:
<ejb-jar>
<display-name>SampleJNDI</display-name>
<enterprise-beans>
<session>
<ejb-name>TestEJB</ejb-name>
<resource-ref>
<res-ref-name>MyDataSource</res-ref-name>
<lookup-name>jdbc/MyDataSource</lookup-name>
</resource-ref>
</session>
</enterprise-beans>
</ejb-jar>
This way, you can port your applications between different application servers by simply changing the ejb-jar.xml.
So far we did some improvements in portability; yet it remains the annoyance that you have to modify your deliverables when porting them to another application server. Luckily, it’s possible to use WLS custom XML descriptors (in our case weblogic-ejb-jar.xml) in order to “shade” the references contained in ejb-jar.xml. Here’s how we can do it:
<wls:weblogic-ejb-jar>
<wls:weblogic-enterprise-bean>
<wls:ejb-name>TestEJB</wls:ejb-name>
<wls:stateless-session-descriptor></wls:stateless-session-descriptor>
<wls:resource-description>
<wls:res-ref-name>MyDataSource</wls:res-ref-name>
<wls:jndi-name>jdbc/MyDataSource</wls:jndi-name>
</wls:resource-description>
</wls:weblogic-enterprise-bean>
</wls:weblogic-ejb-jar>
This way, you can pack your applications with a custom descriptor which will kick-in just in case you are deploying on WLS.
Can we improve even more our portability? For example, let’s say you don’t want to add at all a reference to your actual resource JNDI name in your application archive. This can be, for example, the case if you are moving your application from a development stage to a production stage, where it’s not granted that you have the same environment (just to mention one option: the database).
The answer is: use deployment plans which are a peculiar feature of WLS that let you override all or part of the application server deployment descriptors (in our case weblogic-ejb-jar.xml). Deployment plans are discussed in detail in Chapter 8, in the recipe “Creating Deployment plans” which includes a follow-up to our example.
Dumping the JNDI tree
Getting to know the JNDI naming of your resources is essential when you are developing applications. A dump of the JNDI tree can be obtained through the Admin console. Login to console and select the server name you want to inspect from the left hand side.
Under the Configuration > General tab, click on View JNDI tree in order to dump the JNDI tree of the server: