【问题标题】:@PrePersist with entity inheritance@PrePersist 实体继承
【发布时间】:2010-03-31 11:59:44
【问题描述】:

我在继承和 @PrePersist 注释方面遇到了一些问题。 我的源代码如下所示:

_带有注释的 updateDates() 方法的“基”类:

@javax.persistence.Entity
@Inheritance(strategy = InheritanceType.TABLE_PER_CLASS)
public class Base implements Serializable{

    ...

    @Id
    @GeneratedValue
    protected Long id;
    ...
    @Column(nullable=false)
    @Temporal(TemporalType.TIMESTAMP)
    private Date creationDate;
    @Column(nullable=false)
    @Temporal(TemporalType.TIMESTAMP)
    private Date lastModificationDate;
    ...
    public Date getCreationDate() {
        return creationDate;
    }
    public void setCreationDate(Date creationDate) {
        this.creationDate = creationDate;
    }
    public Date getLastModificationDate() {
        return lastModificationDate;
    }
    public void setLastModificationDate(Date lastModificationDate) {
        this.lastModificationDate = lastModificationDate;
    }
    ...
    @PrePersist
    protected void updateDates() {
      if (creationDate == null) {
        creationDate = new Date();
      }
      lastModificationDate = new Date();
    }
}

_ 现在是应该从基类继承所有方法“和注释”的“子”类:

@javax.persistence.Entity
@NamedQueries({
    @NamedQuery(name=Sensor.QUERY_FIND_ALL, query="SELECT s FROM Sensor s")
})
public class Sensor extends Entity {
    ...
    // additional attributes
    @Column(nullable=false)
    protected String value;
    ...
    // additional getters, setters
    ...
}

如果我将 Base 类的实例存储/持久化到数据库中,一切正常。日期正在更新。 但是现在,如果我想持久化一个子实例,数据库会抛出以下异常:

MySQLIntegrityConstraintViolationException: Column 'CREATIONDATE' cannot be null

因此,在我看来,这是因为在 Child 中,在将实例持久化到数据库之前未调用/调用方法“@PrePersist protected void updateDates()”。

我的代码有什么问题?

【问题讨论】:

    标签: inheritance jpa


    【解决方案1】:

    我已经使用 Hibernate 作为 JPA 提供程序(和 HSQLDB)测试了您的代码。我刚刚在基类中进行了以下更改(因为您不能使用 IDENTIY - HSQLDB 的默认值,如果我没记错的话也可以使用 MySQL - 使用 TABLE_PER_CLASS 策略1 ):

    @Id
    @GeneratedValue(strategy = GenerationType.TABLE)
    protected Long id;
    

    通过此更改,以下测试方法通过:

    @Test
    public void test_Insert_EntityWithInheritedPrePersist() {
        EntityWithInheritedPrePersist child = new EntityWithInheritedPrePersist();
        child.setValue("test");
        entityManager.persist(child);
    
        assertEquals(child.getId(), Long.valueOf(1l));
        assertNotNull(child.getCreationDate());
        assertNotNull(child.getLastModificationDate());
    }
    

    所以@PrePersist 注释的方法在继承的类中被调用。

    这引出了一个问题:您使用哪个 JPA 提供程序?

    1 参见 this thread 了解这方面的背景。

    【讨论】:

      猜你喜欢
      • 2016-03-31
      • 1970-01-01
      • 2011-05-19
      • 2010-10-07
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多