美文网首页
如何解决JPA延迟加载no Session报错

如何解决JPA延迟加载no Session报错

作者: 土豆肉丝盖浇饭 | 来源:发表于2020-04-27 10:48 被阅读0次

    异常展示

    org.hibernate.LazyInitializationException: failed to lazily initialize a collection of role: ****, could not initialize proxy - no Session
        at org.hibernate.collection.internal.AbstractPersistentCollection.throwLazyInitializationException(AbstractPersistentCollection.java:582)
        at org.hibernate.collection.internal.AbstractPersistentCollection.withTemporarySessionIfNeeded(AbstractPersistentCollection.java:201)
        at org.hibernate.collection.internal.AbstractPersistentCollection.readSize(AbstractPersistentCollection.java:145)
        at org.hibernate.collection.internal.PersistentBag.size(PersistentBag.java:261)
    
    

    问题原因

    触发延迟加载的时候,session已经失效

    延迟加载原理

    通过cglib对目标Entity实现代理,针对配置了延迟加载的属性,修改对应get方法的逻辑,植入延迟加载逻辑

    解决方式

    1. 不使用延迟加载
    2. 延迟加载的时候session活跃

    我们本来就想使用延迟加载来提高性能的,不使用延迟加载只是你逃避问题的方式!!要用延迟加载的地方必须用它!!

    如何让延迟加载时session活跃

    web项目

    在springboot环境下,打开以下配置即可

    spring.jpa.open-in-view=true
    

    这个配置会通过WebMvcConfigurer配置一个OpenEntityManagerInViewInterceptor拦截器

    而这个拦截器的作用。。我们看他的注释就知道了

    就是处理请求的全程都能获取到EntityManager,其实就是能获取到session的意思。

    普通提供dubbo服务的项目

    在接口方法上加上@Transactional注解即可。

    @Override
    @Transactional(rollbackFor = Exception.class)
    public List<XXDTO> getAllXX() {
        List<XXEntity> result = xXQueryRepository.findAll();
        return XXConverter.INSTANCE.entityListToDTOList(result);
    }
    

    @Transactional会保证在所注解方法作用域内session都生效

    相关文章

      网友评论

          本文标题:如何解决JPA延迟加载no Session报错

          本文链接:https://www.haomeiwen.com/subject/oqaewhtx.html