failed to lazily initialize a collection of role,解决Hibernate查询报错

Hibernate报错:

org.hibernate.LazyInitializationException: failed to lazily initialize a collection of role: com.jiuqi.gov.common.attatchment.entity.AttachmentEntity.properties, could not initialize proxy - no Session
        at org.hibernate.collection.internal.AbstractPersistentCollection.throwLazyInitializationException(AbstractPersistentCollection.java:614) ~[hibernate-core-5.6.9.Final.jar:5.6.9.Final]
        at org.hibernate.collection.internal.AbstractPersistentCollection.withTemporarySessionIfNeeded(AbstractPersistentCollection.java:218) ~[hibernate-core-5.6.9.Final.jar:5.6.9.Final]
        at org.hibernate.collection.internal.AbstractPersistentCollection.readSize(AbstractPersistentCollection.java:162) ~[hibernate-core-5.6.9.Final.jar:5.6.9.Final]
        at org.hibernate.collection.internal.PersistentMap.size(PersistentMap.java:148) ~[hibernate-core-5.6.9.Final.jar:5.6.9.Final]
        at java.util.HashMap.putMapEntries(HashMap.java:502) ~[?:1.8.0_381]
        at java.util.HashMap.<init>(HashMap.java:491) ~[?:1.8.0_381]
        at com.jiuqi.gov.common.attatchment.entity.AttachmentEntity.toAttachmentInfo(AttachmentEntity.java:293) ~[common.attachment-1.5.1.jar:?]

原代码:

public List<AttachmentInfo> getAttachmentById(UUID id){
		String table = "com.fdw.AttachmentEntity";
		List<AttachmentInfo> result = new ArrayList<>();
		List<AttachmentEntity> resultList = template.execute(new HibernateCallback<List<AttachmentEntity>>() {
			@Override
			public List<AttachmentEntity> doInHibernate(Session session) throws HibernateException {
				String sql = "from " + table + " where Id = :id";
				Query<AttachmentEntity> query = session.createQuery(sql, AttachmentEntity.class);
				query.setParameter("id", id);
				return query.getResultList();
			}
		});
		for (AttachmentEntity attachmentEntity : resultList){
			result.add(attachmentEntity.toAttachmentInfo());
		}
		return result;
	}

问题原因:

 AttachmentEntity 类有个懒加载的字段 properties,关联了其他表。

关于懒加载

所谓懒加载(lazy)就是延时加载,延迟加载。即不是不加载,而是在需要的时候才加载。

什么时候用懒加载呢,我只能回答要用懒加载的时候就用懒加载。

至于为什么要用懒加载呢,就是当我们要访问的数据量过大时,明显用缓存不太合适,

因为内存容量有限 ,为了减少并发量,减少系统资源的消耗,

我们让数据在需要的时候才进行加载,这时我们就用到了懒加载。

比如部门ENTITY和员工ENTITY,部门与员工1对多,

如果lazy设置为 false,那么只要加载了一个部门的po,就会根据一对多配置的关系把所有员工的po也加载出来。

但是实际上有时候只是需要用到部门的信息,不需要用到 员工的信息,这时员工po的加载就等于浪费资源。如果lazy设置为true,那么只有当你访问部门po的员工信息时候才回去加载员工的po的信息。

hibernate3.0 中 lazy有三个值:

lazy有三个属性:true、false、extra

【true】:默认取值,它的意思是只有在调用这个集合获取里面的元素对象时,才发出查询语句,加载其集合元素的数据 。即只有在使用的时候才发出查询命令。

【false】:取消懒加载特性,即在加载对象的同时,就发出第二条查询语句加载其关联集合的数据即加载对象的时候就发出查询语句,加载关联的子类数据。


【extra】:一种比较聪明的懒加载策略,即调用集合的size/contains等方法的时候,hibernate并不会去加载整个集合的数据,而是发出一条聪明的SQL语句,以便获得需要的值,只有在真正需要用到这些集合元素对象数据的时候,才去发出查询语句加载所有对象的数据

 

 

解决后代码:

public List<AttachmentInfo> getAttachmentById(UUID id){
		String table = "com.fdw.AttachmentEntity";
		List<AttachmentInfo> result = new ArrayList<>();
		template.execute(new HibernateCallback<List<AttachmentEntity>>() {
			@Override
			public List<AttachmentEntity> doInHibernate(Session session) throws HibernateException {
				String sql = "from " + table + " where Id = :id";
				Query<AttachmentEntity> query = session.createQuery(sql, AttachmentEntity.class);
				query.setParameter("id", id);
				List<AttachmentEntity> resultList = query.getResultList();
				for (AttachmentEntity attachmentEntity : resultList){
					result.add(attachmentEntity.toAttachmentInfo());
				}
				return null;
			}
		});
		return result;
	}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

ThatMonth

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值