我有一个带字段的实体
@Temporal(TemporalType.TIMESTAMP)
@Column(name = "edit_timestamp",
columnDefinition="TIMESTAMP DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP")
private Date editTimestamp;
@Version
@Column(name = "edit_count")
private short editCount;
private String text;
当我尝试使用Spring-Data-JPA进行更新时,我发现edit_count已经增加,但edit_timestamp仍然保持不变。如果我手动调用SQL
UPDATE post SET TEXT='456' WHERE post_id=1;
edit_timestamp已更新。如果我添加
@PreUpdate
protected void onUpdate() {
editTimestamp = new Date();
}
它没有问题。我的问题是为什么w / o @PreUpdate没有更新edit_timestamp?
答案 0 :(得分:8)
这是一个老问题,但我想如果其他人发现它有用,我会提出答案。 我认为您需要更改列注释以包含updatable = false。这将导致edit_timestamp列不显示在更新sql中,因此JPA提供程序将不包含该字段的当前值,这是导致它覆盖默认值的原因。
@Temporal(TemporalType.TIMESTAMP)
@Column(name = "edit_timestamp",
updatable = false
columnDefinition="TIMESTAMP DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP")
private Date editTimestamp;
答案 1 :(得分:0)
因为在你的初始注释集中,所有你告诉它的关于edit_timestamp列的是它是一个时间戳; JPA不知道它需要更新它。我猜测当你手动执行SQL语句时,你会有一些更新后的触发器,它会为你改变这些字段 - 但是当你更新它时,它会被来自持久化实体的数据覆盖。 /> 如果您不需要“已编辑”的计数/时间戳,请尝试从实体中删除它们,看看是否有效。否则,你有一个可行的解决方案。
答案 2 :(得分:0)
您可以在实体中将变量标记为更新或创建时间戳。在以下示例中,您可以看到如何使用休眠注释轻松完成此操作:
@UpdateTimestamp
private LocalDateTime editTimestamp;
@CreationTimestamp
private LocalDateTime creationTimestamp;
仅供参考并确保没有混淆,我将以下包导入用于相应的数据类型和注释:
import org.hibernate.annotations.CreationTimestamp
import org.hibernate.annotations.UpdateTimestamp
import java.time.LocalDateTime