Hibernate недавно представил профили извлечения, которые (в дополнение к настройке производительности) идеально подходят для решения подобных проблем. Это позволяет вам (во время выполнения) выбирать между различными стратегиями загрузки и инициализации.
http://docs.jboss.org/hibernate/core/3.5/reference/en/html/performance.html#performance-fetching-profiles
Редактировать (добавлен раздел о том, как установить профиль выборки с помощью перехватчика):
Прежде чем начать: убедитесь, что профили выборки действительно работают для вас. Я не использовал их сам и вижу, что они в настоящее время ограничены, чтобы присоединиться к выборкам. Прежде чем тратить время на внедрение и подключение перехватчика, попробуйте настроить профиль выборки вручную и убедитесь, что он действительно решает вашу проблему.
Существует множество способов настройки перехватчиков в Spring (в соответствии с предпочтениями), но наиболее простым способом было бы реализовать MethodInterceptor (см. http://static.springsource.org/spring/docs/3.0.x/spring-framework-reference/html/aop-api.html#aop-api-advice-around). Пусть у него есть установщик для требуемого профиля выборки). и установщик для фабрики Hibernate Session:
public class FetchProfileInterceptor implements MethodInterceptor {
private SessionFactory sessionFactory;
private String fetchProfile;
... setters ...
public Object invoke(MethodInvocation invocation) throws Throwable {
Session s = sessionFactory.openSession(); // The transaction interceptor has already opened the session, so this returns it.
s.enableFetchProfile(fetchProfile);
try {
return invocation.proceed();
} finally {
s.disableFetchProfile(fetchProfile);
}
}
}
Наконец, включите перехватчик в конфигурации Spring. Это можно сделать несколькими способами, и у вас, вероятно, уже есть настройка AOP, к которой вы можете добавить ее. См http://static.springsource.org/spring/docs/3.0.x/spring-framework-reference/html/aop.html#aop-schema.
Если вы новичок в AOP, я бы посоветовал сначала попробовать «старый» способ ProxyFactory (http://static.springsource.org/spring/docs/3.0.x/spring-framework-reference/html/aop-api.html#aop-api-proxying-intf), потому что легче понять, как он работает. Вот несколько примеров XML для начала:
<bean id="fetchProfileInterceptor" class="x.y.zFetchProfileInterceptor">
<property name="sessionFactory" ref="sessionFactory"/>
<property name="fetchProfile" ref="gui-profile"/>
</bean>
<bean id="businessService" class="x.y.x.BusinessServiceImpl">
<property name="dao" .../>
...
</bean>
<bean id="serviceForSwinGUI"
class="org.springframework.aop.framework.ProxyFactoryBean">
<property name="proxyInterfaces" value="x.y.z.BusinessServiceInterface/>
<property name="target" ref="businessService"/>
<property name="interceptorNames">
<list>
<value>existingTransactionInterceptorBeanName</value>
<value>fetchProfileInterceptor</value>
</list>
</property>
</bean>