Spring Data lazyload没有LazyInitializationException

时间:2015-12-23 11:38:18

标签: spring spring-data lazy-loading transactional

@Component
@Transactional
public class TestClass extends AbstractClass
{
   @Autowire
   ClassARepo classARepo;

   @Override
   public void test() {
       ClassA classA = classARepo.findOne(1);
       List<ClassB> list = classA.getClassBs();
       list.size();
   }
}

ClassB被映射为onetomany并且延迟加载。

在上面的代码中

classARepo.findOne(1);

执行正确。但是

List<ClassB> list = classA.getClassBs();
list.size();

LazyInitializationException失败。

public interface ClassARepo extends CrudRepository<ClassA, Integer> {
} 

TestA的实例创建如下

@PersistJobDataAfterExecution
@DisallowConcurrentExecution
@Transactional
@Component
public class TestClassJOB extends AbstractJob
{
    @Autowired
    TestClass indexer;
}

上下文:

<!-- JPA mapping configuration -->
<bean id="persistenceXmlLocation" class="java.lang.String">
    <constructor-arg value="classpath:/persistence.xml"></constructor-arg>
</bean>

<!-- entity manager -->
<bean id="entityManagerFactory" class="org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean" 
    p:dataSource-ref="dataSource" p:persistenceUnitName="jpaData"
    p:persistenceXmlLocation-ref="persistenceXmlLocation">
    <property name="packagesToScan" value="com..persist.entity" />
    <property name="jpaVendorAdapter">
        <bean class="org.springframework.orm.jpa.vendor.HibernateJpaVendorAdapter" />
    </property>
</bean>

<!-- transaction manager -->
<bean id="transactionManager" class="org.springframework.orm.jpa.JpaTransactionManager" 
    p:entityManagerFactory-ref="entityManagerFactory" lazy-init="true" p:dataSource-ref="dataSource" />

<!-- JPA repositories -->
<jpa:repositories base-package="com..persist.repo" 
    entity-manager-factory-ref="entityManagerFactory" transaction-manager-ref="transactionManager" />

我尝试了很多资源但无法解决问题。显示以下错误消息“无法初始化代理 - 无会话”。

问题的原因是什么? 当调用classARepo.findOne(1)时会话可用时,为什么在延迟提取(list.size())期间不可用?

1 个答案:

答案 0 :(得分:1)

问题是TestClassJOB的实例是由Quartz创建的。所以跨国代理人没有适用于这个问题的原因。

我通过声明交易模板来解决问题

@Autowired
TransactionTemplate transactionTemplate;

然后将代码包装在

    transactionTemplate.execute(new TransactionCallbackWithoutResult()
    {
        @Override
        protected void doInTransactionWithoutResult(TransactionStatus status)
        {
           <code here>
        }
   }