在休眠状态下懒惰地加载 clob

2022-09-03 06:50:34

关于这个谷歌搜索,人们可以找到很多,但我还没有找到解决这个问题的可行解决方案。

基本上,我拥有的是我想要按需加载的特定类上的一个大CLOB。这样做的天真方法是:

class MyType {

  // ...

  @Basic(fetch=FetchType.LAZY)
  @Lob
  public String getBlob() {
    return blob;
  }
}

但是这不起作用,显然是因为我使用的是oracle驱动程序,即Lob对象不被视为简单的句柄,而是始终加载。至少,我从我的尝试中被引导相信。有一种解决方案使用特殊的检测来延迟加载属性,但是由于Hibernate文档似乎表明他们对使其正常工作不太感兴趣,所以我宁愿不走这条路。特别是必须运行额外的编译传递和所有。

因此,我设想的下一个解决方案是将此对象分离为另一种类型并定义关联。不幸的是,虽然文档提供了相互矛盾的信息,但对我来说很明显,延迟加载不适用于具有共享主键的OneToOne关联。我将关联的一端设置为 ManyToOne,但当有共享主键时,我不太确定如何执行此操作。

那么,任何人都可以提出最好的方法来解决这个问题吗?


答案 1

此,只有PostgreSQL将Blob实现为真正懒惰。因此,最好的解决方案是将 Blob 移动到另一个表。是否必须使用共享主密钥?你为什么不做这样的事情:

public class MyBlobWrapper {
    @Id
    public Long getId() {
       return id;
    }
    @Lob
    public String getBlob() {
        return blob;
    }
    @OneToOne(fetch=FetchType.LAZY,optional=false) 
    public MyClass getParent() {
        return parent;
    }
}

答案 2

与其使用休眠注释进行平衡,不如尝试将字段从转换为(或):StringClobBlob

@Lob  
@Basic(fetch=FetchType.LAZY)  
@Column(name = "FIELD_COLUMN")  
public Clob getFieldClob() {  
  return fieldClob;  
}  

public void setFieldClob(Clob fieldClob) {  
  this.fieldClob = fieldClob;  
}  

@Transient  
public String getField()  
{  
  if (this.getFieldClob()==null){  
    return null;  
  }  
  try {  
    return MyOwnUtils.readStream(this.getFieldClob().getCharacterStream());  
  } catch (Exception e) {  
    e.printStackTrace();  
  }  

  return null;  
}  

public void setField(String field)  
{  
  this.fieldClob = Hibernate.createClob(field);  
} 

为我工作(该领域开始在Oracle上懒惰地加载)。


推荐