1. 具体报错
Caused by: org.hibernate.LazyInitializationException: could not initialize proxy
[com.example.sell.dataobject.OrderMaster#1584450379194771858] - no Session
2.问题分析
我的代码如下
@Entity
@Data
@DynamicInsert
@DynamicUpdate
public class OrderMaster {
/*订单id*/
@Id
private String orderId;
/*买家名称*/
private String buyerName;
/*买家电话*/
private String buyerPhone;
/*买家地址*/
private String buyerAddress;
/*买家微信openid*/
private String buyerOpenid;
/*订单数量*/
private BigDecimal orderAmount;
/*订单状态,默认为0,最新创建*/
private Integer orderStatus = OrderStatusEnum.NEW.getCode();
/*支付状态,默认为0,未支付*/
private Integer payStatus = PayStatusEnum.WAIT.getCode();
/*订单创建时间*/
private Date createTime;
/*订单更新时间*/
private Date updateTime;
}
使用Spring Data JPA进行数据访问
public interface OrderMasterRepository extends JpaRepository<OrderMaster,String> {
}
下面是测试方法:
@Test
void findTest(){
OrderMaster one = orderMasterRepository.getOne("111111");
System.out.println(one);
}
按照如上操作,测试后会报出1中的错误;在网上找了很多解释,以下是最精炼的:
- hibernate使用sessionFactory来管理session,每进行一次数据库操作都要新建一个session对象,当操作完成后,hibernate就会在dao层立即关闭session,所以操作类中另一个类的具体属性时,session已经关闭,就会报错;(转自:关于could not initialize proxy - no Session问题)
- hibernate默认实现延迟加载,当应用代码使用数据对象的时候才访问数据库取出数据;
- 上述测试代码中的问题在于,打印one对象时,session已经关闭,因此需要关闭懒加载;
3.解决方案
网上有很多解决方案,我自己是在repository中写了一个方法代替getOne()方法:
public interface OrderMasterRepository extends JpaRepository<OrderMaster,String> {
OrderMaster findByOrderId(String orderId);
}
另外还有以下解决方案:
- 在实体类上添加注解@Proxy(lazy=false)
@Proxy(lazy=false)
public class OrderMaster{
}
- 在全局配置文件中配置以下内容
spring.jpa.open-in-view=true