Is it possible to make @Formula annotation lazily loaded?

别来无恙 提交于 2019-12-18 11:59:32

问题


I have used @Formula annotation to use it for getting calculated properties. What I need is that those fields/getters which is annotated with @Formula annotation should be lazily loaded.

Is this even possible and if so how?

thanks


回答1:


Yes . Just annotating the fields/getter of the @Formula property by @Basic(fetch=FetchType.LAZY) and use this ant task provided by hibernate to do the bytecode instrumentation for the entity class. Otherwise , LAZY loading for the @Formula property is silently ignored.

The documentation contains the info on how to use this ant task to do bytecode instrumentation.




回答2:


I saw in the comment that you would like to achieve this without bytecode instrumentation. This can be achieved by implementing the FieldHandled interface and by modifying the getters and setters for the lazy field.

HBM

<property name="deletable" type="true_false" lazy="true">
  <formula>(select something from other tables and such....)</formula>
</property>

JAVA

import org.hibernate.bytecode.javassist.FieldHandled;
import org.hibernate.bytecode.javassist.FieldHandler;
public class Person implements FieldHandled {

/* allows lazy formulas without hibernate bytecode instrumentation */
private FieldHandler fieldHandler;
public FieldHandler getFieldHandler() { return fieldHandler; }
public void setFieldHandler(FieldHandler fieldHandler) { this.fieldHandler = fieldHandler; }


private Boolean deletable;

public void setDeletable(Boolean deletable) {
    if(fieldHandler!=null)
        fieldHandler.writeObject(this, "deletable", this.deletable, deletable);
    this.deletable = deletable;
}

public Boolean getDeletable() {
    if(fieldHandler!=null)
        return (Boolean)fieldHandler.readObject(this, "deletable", deletable);
    return deletable;
}
}

Another example can be found here. But that is lazy loading a one-to-one relationship.




回答3:


I tried with BytecodeEnhancement (Maven Plugin) but doesnt work. So I made this:

  1. Create a Class (FooFormula.java), map it to the table with two field, one for the @id and other for the @Formula.

     @Entity
     @Table(name = "BAR_TABLE")
     public class FooFormula implements Serializable {
    
      private Long idBarTable;
      private Long formula;
    
      public FooFormula() {
        super();
      }
    
      public FooFormula(String idBarTable) {
          super();
          this.idBarTable = idBarTable;
      }    
    
      @Id
      @Column(name = "ID_BAR_TABLE", unique = true, nullable = false, length = 20)
      public Long getIdBarTable() {
          return this.sitidBarTableCodigo;
      }
    
      public void setIdBarTable(Long idBarTable) {
          this.idBarTable = idBarTable;
      }
    
      @Formula("(SELECT 1 from DUAL)")
      public Long getFormula() {
        return formula;
      }
    
      public void setFormula(Long formula) {
        this.formula = formula;
      }
    }
    
  2. Add this new class (FooFormula.java) as a field to your Entity with @ManyToOne and @JoinColumn

     @Entity
     @Table(name = "BAR_TABLE")
     public class Bar implements Serializable {
    
      private Long idBarTable;
      private Long somOtherColumn;
      private FooFormula fooFormula;
    
      public Bar() {
        super();
      }
    
      public Bar(String idBarTable) {
          super();
          this.idBarTable = idBarTable;
      }    
    
      @Id
      @Column(name = "ID_BAR_TABLE", unique = true, nullable = false, length = 20)
      public Long getIdBarTable() {
          return this.sitidBarTableCodigo;
      }
    
      public void setIdBarTable(Long idBarTable) {
          this.idBarTable = idBarTable;
      }
    
      @ManyToOne(fetch = FetchType.LAZY)
      @JoinColumn(name = "ID_BAR_TABLE", nullable = false, insertable=false, updatable=false)
      public FooFormula getFooFormula() {
        return fooFormula;
      }
    
      public void setFooFormula(FooFormula fooFormula) {
        this.fooFormula = fooFormula;
      }
    }
    


来源:https://stackoverflow.com/questions/10070440/is-it-possible-to-make-formula-annotation-lazily-loaded

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!