1. The open EntityManager in view pattern
使用Hibernate实现延迟加载时常见的异常:
org.hibernate.LazyInitializationException:
failed to lazily initialize a collection of role:
com.manning.sdmia.dataacces.domain.model.Contact.adresses,
no session or session was closed
With Spring, the lazy loading is tied to its resource management within its data access support.
According to the data access configuration, Spring is responsible for obtaining and releasing the
underlying resources of the JPA implementation. This implies that the scope of the resource
transparently changes. These are the impacts on resources scope in two use cases.
■ No transaction configured —Spring obtains an EntityManager instance before the call of every
JpaTemplate method and releases it after each call. EntityManager instances aren’t gathered and
every call uses a different EntityManager.
■ Transaction applied on service methods —Spring obtains an EntityManager instance and uses it
for all the nested calls within the service method logic. The resource is obtained before the call of
every service method, stored in a variable of type ThreadLocal , and released when the service
method exits.
2. Using the open EntityManager in view pattern with Spring DM
Components using the open EntityManager in view pattern and data access components are
typically separated , because the former implement the UI of applications. Moreover, data access
components must make their EntityManagerFactory entities accessible as OSGi services so that
the user interface component can get at them。
Exporting the EntityManagerFactory bean as an OSGi service:
<bean id="entityManagerFactory" class="(...)">
(...)
</bean>
<osgi:service ref="entityManagerFactory"
interface="javax.persistence.EntityManagerFactory"/>
<osgi:reference id="entityManagerFactory" interface="javax.persistence.EntityManagerFactory"/>
web.xml中的配置:
<filter>
<filter-name>openEntityManagerInViewFilter</filter-name>
<filter-class>
org.springframework.orm.jpa.support.OpenEntityManagerInViewFilter
</filter-class>
</filter>
<filter-mapping>
<filter-name>openEntityManagerInViewFilter</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
You’ll notice that the filter is, by default, based on the EntityManagerFactory bean with the
identifier entityManagerFactory. This configuration can be changed with the
entityManagerFactoryBeanName filter initialization parameter. After performing this configuration,
your web application can lazily load data to build its views.
To summarize, the open EntityManager in view pattern provides a workable solution to using
lazy loading in JPA. This feature isn’t difficult to implement in an OSGi environment using Spring
DM, but it requires the sharing of EntityManagerFactory. Components using this pattern are
then tied to the underlying technology both through the service type and by the packages
needed in the manifest configuration.