懒加载错误的三种处理方案

懒加载错误
Exception occurred during processing request: org.hibernate.LazyInitializationException: 
failed to lazily initialize a collection of role: cn.itcast.bos.domain.base.Courier.fixedAreas,
could not initialize proxy - no Session
org.apache.struts2.json.JSONException: org.hibernate.LazyInitializationException: 
failed to lazily initialize a collection of role: cn.itcast.bos.domain.base.Courier.fixedAreas, 
could not initialize proxy - no Session

第一种解决方案:在getFixedAreas方法上加上@JSON(serialize = false)
@JSON(serialize = false)
public Set<FixedArea> getFixedAreas() {
return fixedAreas;
}
只要加上了@JSON(serialize = false),返回的数据格式里不会含有fixedAreas字段及数据,
可以理解为过滤掉了fixedAreas数据

第二种解决方案:在web.xml中配置,延长EntityManager的生命周期,类似Hibernate里面延长Sesseion的生命周期
<filter>
<filter-name>OpenEntityManagerInView</filter-name>
<filter-class>org.springframework.orm.jpa.support.OpenEntityManagerInViewFilter</filter-class>
</filter>
<filter-mapping>
<filter-name>OpenEntityManagerInView</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>

第三种解决方案:不配置OpenEntityManagerInViewFilter,不配置@JSON(serialize = false),设置为立即加载
@ManyToMany(mappedBy = "couriers",fetch=FetchType.EAGER)
private Set<FixedArea> fixedAreas = new HashSet<>();
此时,返回的数据格式里有fixedAreas字段及数据
获取A对象时,A对象关联B对象,FetchType默认是立即加载
获取A对象时,A对象关联B对象的集合,FetchType默认是懒加载

总结:不管是Hibernate还是JPA,有加载策略的问题,都是基于性能的考虑
### Hibernate 框架中的懒加载 #### 懒加载的概念及其工作原理 在Hibernate框架中,懒加载是一种优化技术,用于延迟加载关联对象直到实际访问这些对象时才进行加载。这种方式可以显著减少不必要的数据库查询次数和数据传输量,从而提高应用程序性能[^2]。 #### 实现懒加载的方法 为了实现懒加载,在映射文件(如`hbm.xml`配置文件或注解方式)定义实体类之间的关系时指定`fetch="lazy"`属性即可启用该功能。对于使用Java注解的方式来说,则是在相应的字段上加上`@LazyToOne(LazyToOneOption.NO_PROXY)` 或者 `@OneToMany(fetch = FetchType.LAZY)`等类似的声明来开启懒加载特性[^1]。 ```java @Entity public class Parent { @Id private Long id; @OneToMany(mappedBy = "parent", fetch = FetchType.LAZY) private Set<Child> children; // getters and setters... } ``` 当通过Parent实例获取children集合的时候,默认情况下不会立即执行SQL语句去读取子表的数据;只有真正遍历这个集合或者调用了size()之类会触发初始化的操作才会发起新的查询请求并填充child记录到内存当中。 #### 常见问题及解决方案 然而,在应用懒加载的过程中可能会遇到一些挑战,其中最典型的就是`org.hibernate.LazyInitializationException: could not initialize proxy - no Session`异常。此错误通常发生在尝试访问未被加载的对象图部分而此时Session已经关闭的情况下[^3]。 针对上述提到的问题有几种常见的处理办法: - **确保Session处于打开状态**:可以在业务逻辑层保持住当前事务范围内的持久化上下文不被过早释放; - **采用EAGER策略代替LAZY**:虽然这违背了懒加载的设计初衷,但在某些特定场景下可能是必要的折衷方案之一; - **利用Open Session In View模式**:这是一种Web开发实践,它允许HTTP请求期间始终维持一个活跃的SessionFactory连接直至视图渲染完成后再断开链接; - **提前触发加载操作**:比如可以通过编写自定义方法显式地触发展示所需的部分数据结构之前就将其完全加载入内存之中。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值