如何在Play中创建自动生成的日期/时间戳字段! / JPA?
我想在实体对象上添加一个Date / DateTime / Timestamp字段,该字段将在创建/持久化实体时自动创建并设置为“now”,永远不会再次更新。
其他用例包括始终更新为包含实体的最后修改日期的字段。
我曾经在mysql架构中实现这样的要求。
在Play中执行此操作的最佳方法是什么! / JPA?
有一个代码片段,您可以调整,以实现您的需求。 看一看:
// Timestampable.java package models; import java.util.Date; import javax.persistence.Column; import javax.persistence.GeneratedValue; import javax.persistence.Id; import javax.persistence.MappedSuperclass; import javax.persistence.PrePersist; import javax.persistence.PreUpdate; import javax.persistence.Version; import play.db.ebean.Model; @MappedSuperclass public class Timestampable extends Model { @Id @GeneratedValue public Long id; @Column(name = "created_at") public Date createdAt; @Column(name = "updated_at") public Date updatedAt; @Version public int version; @Override public void save() { createdAt(); super.save(); } @Override public void update() { updatedAt(); super.update(); } @PrePersist void createdAt() { this.createdAt = this.updatedAt = new Date(); } @PreUpdate void updatedAt() { this.updatedAt = new Date(); } }
我认为你可以通过至少两种方式实现它。
数据库默认值
我认为最简单的方法是将列标记为updateable=false, insertable=false
(这将为您提供不变性 – JPA不会将此列包含在INSERT
和UPDATE
语句中)并将数据库列设置为默认值为现在。
JPA生命周期回调方法
其他方法是提供@PrePersist
生命周期回调方法,该方法将日期对象设置为实际日期new Date()
。 然后你需要确保没有人会编辑这个值,所以你不应该为这个属性提供任何setter。
如果您希望在修改实体时更新日期,您可以类似地实现@PreUpdate
生命周期回调方法,该方法将设置实际修改日期。
请记住,如果您正在使用Date对象,则应该对Date对象执行防御性复制 (因此您应该返回类似new Date(oldDate.getTime());
而不是return oldDate
plain return oldDate
)。
这将阻止用户使用Date的getter并修改其状态。