问题描述
我正在使用Postgres数据库使用Spring Boot + JPA编写应用程序.我有一个用户实体,并且试图获取保存和/或修改用户记录时的时间戳.这是行不通的.保存的记录的createdDate和lastModifiedDate都为"null".
I am writing an app with Spring Boot + JPA, using a Postgres database. I have a User Entity and I am trying to get a timestamp when the user record is saved and/or modified. This is not working. The record that is being saved has "null" for both createdDate and lastModifiedDate.
以下是Kotlin中的所有相关代码:
Here is all the relevant code in Kotlin:
@Entity
@Table(name = "app_user")
@EntityListeners(AuditingEntityListener::class)
data class User(
@Id
@GeneratedValue(strategy = GenerationType.AUTO)
@Column(name = "id")
val id: UUID? = null,
@NotNull
@Column(unique = true)
val email: String,
val name: String,
private val password: String,
@CreatedDate
@Column(name = "created_date", nullable = false, updatable = false)
var createdDate: LocalDateTime? = null,
@LastModifiedDate
@Column(name = "last_modified_date", nullable = false)
var lastModifiedDate: LocalDateTime? = null
)
我添加日期字段的SQL查询如下:
My SQL queries to add the date fields look like this:
ALTER TABLE app_user
ADD COLUMN last_modified_date TIMESTAMP,
ADD COLUMN created_date TIMESTAMP;
我也有一个配置类
@Configuration
@EnableJpaAuditing(auditorAwareRef = "auditorProvider")
class JpaAuditingConfiguration {
@Bean
fun auditorProvider(): AuditorAware<String> {
return AuditorAware { Optional.of(SecurityContextHolder.getContext().authentication.name) }
}
}
我的考试班:
@Autowired
private lateinit var userRepository: UserRepository
val user = User(
email = "email",
name = "name",
password = "password"
)
@Test
fun `it sets the timestamps when a user is created`() {
userRepository.save(user)
user.let {
assertThat(it.createdDate).isNotNull()
assertThat(it.lastModifiedDate).isNotNull()
}
}
更新:
似乎问题仅在测试中发生.当我在开发环境中而不是在测试环境中执行相同的代码来创建用户时,这似乎很好.
It seems the problem only happens in tests. It seems to be fine when i execute the same code to create a user in the development environment and not in tests.
测试中是否需要其他配置?
Do i need some additional config in the tests?
更新2
我还尝试过这样使用实体管理器:
I also tried to use the entity manager like this:
@Autowired
lateinit var entityManager: TestEntityManager
然后在测试中执行以下操作:
Then in the test do:
entityManager.persist(user)
entityManager.flush()
还有
entityManager.persistAndFlush(user)
仍然没有填充时间戳.
推荐答案
在@PrePersist
和@PreUpdate
阶段调用AuditingEntityListener方法.
The AuditingEntityListener methods are called in the @PrePersist
and @PreUpdate
phase.
这意味着它们将在执行插入或更新SQL语句之前被调用.
This means they are called just before the insert or update SQL statements are executed.
在Hibernate文档中了解有关JPA事件的更多信息: https://docs.jboss.org /hibernate/orm/5.2/userguide/html_single/Hibernate_User_Guide.html#events-jpa-callbacks
Read more about JPA events in the Hibernate doc:https://docs.jboss.org/hibernate/orm/5.2/userguide/html_single/Hibernate_User_Guide.html#events-jpa-callbacks
单元测试
在测试"中使用时,您还必须在测试中启用审核
When using in Tests you have to enable auditing as well on the test
@DataJpaTest
@RunWith(SpringRunner.class)
@EnableJpaAuditing
public class EntityListenerTest {
这篇关于保存对象时未填充Spring Boot JPA @ CreatedDate @LastModifiedDate的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!