Java Hibernate在从相关实体删除时加载LOB(是否应该是惰性的)?

Java Hibernate在从相关实体删除时加载LOB(是否应该是惰性的)?,java,hibernate,jpa,lazy-loading,Java,Hibernate,Jpa,Lazy Loading,我有一个使用JPA和Hibernate进行DB交互的web应用程序 有一个generiec JPA存储库,一个我现在遇到问题的实体。 现在调用delete方法时,我得到一个java.lang.OutOfMemoryError:java堆空间异常。 (它是DeleteByCreatedDataTelessThan) 当表中只有一些条目(使用20测试)时,这可以正常工作,但实际负载高达20.000 分析转储后,发现应用程序正在从数据库加载整个IbGeneratedData.IbPdf&IbGener

我有一个使用JPA和Hibernate进行DB交互的web应用程序

有一个generiec JPA存储库,一个我现在遇到问题的实体。 现在调用delete方法时,我得到一个java.lang.OutOfMemoryError:java堆空间异常。 (它是DeleteByCreatedDataTelessThan)

当表中只有一些条目(使用20测试)时,这可以正常工作,但实际负载高达20.000

分析转储后,发现应用程序正在从数据库加载整个IbGeneratedData.IbPdf&IbGeneratedData.IbXml(占heapspace的80%)。
我怎样才能阻止这一切?要删除它,只需检查ID即可删除它们

我也在LOB上尝试了
@Basic(fetch=FetchType.LAZY)

public interface ResponseRepository extends JpaRepository<IbResponse, String>, JpaSpecificationExecutor<IbResponse> {
    @Modifying
    void deleteByCreatedDateLessThan(Date maxAgedDate);

    Collection<IbResponse> findByOwningUserIdEquals(String id, Sort sort);
}



@Entity(name = "IbResponse")
@Table(name = "IB_RESPONSE")
public class IbResponse implements Serializable {

    @Id
    @GeneratedValue(generator = "system-uuid")
    @GenericGenerator(name = "system-uuid", strategy = "uuid")
    @Column(name = "ID")
    private String id;

    @ManyToOne(fetch = FetchType.LAZY, optional = false, targetEntity = IbUser.class)
    @JoinColumn(name = "USER_ID", updatable = false)
    private IbUser owningUser;

    @OneToOne(fetch = FetchType.LAZY, cascade = CascadeType.ALL)
    @JoinColumn(name = "GENERATED_DATA_ID")
    private IbGeneratedData generatedData;

    ...
}

@Entity(name = "IbGeneratedData")
@Table(name = "IB_GENERATED_DATA")
public class IbGeneratedData implements Serializable {

    @Id
    @GeneratedValue(generator = "system-uuid")
    @GenericGenerator(name = "system-uuid", strategy = "uuid")
    @Column(name = "ID")
    private String id;

    @Lob
    @Column(name = "PDF")
    private byte[] IbPdf;

    @Lob
    @Column(name = "XML")
    private byte[] IbXml;

    ...
}
public interface ResponseRepository扩展了JpaRepository,JpaSpecificationExecutor{
@修改
作废DeleteByCreatedDataTelessthan(日期maxAgedDate);
集合findByowningUsereQuals(字符串id、排序);
}
@实体(名称=“IbResponse”)
@表(name=“IB_响应”)
公共类IbResponse实现可序列化{
@身份证
@GeneratedValue(generator=“系统uuid”)
@GenericGenerator(name=“system uuid”,strategy=“uuid”)
@列(name=“ID”)
私有字符串id;
@manytone(fetch=FetchType.LAZY,可选=false,targetEntity=IbUser.class)
@JoinColumn(name=“USER\u ID”,updateable=false)
私人IbUser拥有者;
@OneToOne(fetch=FetchType.LAZY,cascade=CascadeType.ALL)
@JoinColumn(name=“生成的数据\u ID”)
私有IbGeneratedData generatedData;
...
}
@实体(name=“IbGeneratedData”)
@表(name=“IB_生成的_数据”)
公共类IbGeneratedData实现可序列化{
@身份证
@GeneratedValue(generator=“系统uuid”)
@GenericGenerator(name=“system uuid”,strategy=“uuid”)
@列(name=“ID”)
私有字符串id;
@高球
@列(name=“PDF”)
私有字节[]IbPdf;
@高球
@列(name=“XML”)
私有字节[]IbXml;
...
}
春季数据jpa:1.7.0
休眠:4.3.7
在Oracle数据库上运行

1)
LAZY
只是对持久性提供程序的提示,不是必须的

2)根据Jpa标准,
deleteBy
在Spring数据Jpa中的工作方式是,它首先将所有实体加载到持久性上下文中,然后为每个结果调用
delete(entity)

解决方案

创建更新查询并在新事务中运行(传播。需要\u new):

修改 @查询(“从iResponse i中删除,其中i.createdDate<:date”,) 作废DeleteByCreatedDataTelessthan(@Param(“日期”)日期);
这将省略将实体加载到持久性上下文中并执行直接批量删除。

也许吧。谢谢你-我的朋友现在提供了几乎相同的解决方案(没有原因)-此外,使用@Query我们更改了关系:让IB_生成的数据存储响应的id。但是:我仍然不明白为什么在这种情况下它没有将所有实体加载到上下文中。
@Modifying
@Query("delete from IbResponse i where i.createdDate < :date", )
void deleteByCreatedDateLessThan(@Param("date") Date date);