spring - Spring Hibernate - 不同事务之间的@Transactional
问题描述
我正在创建一个测试,并且基本上在一个@Transactional
方法中执行不同的事务。
我添加 a Project
,然后添加 a Task
,最后将再次从数据库中获取项目以测试它是否已保存任务。
请注意我展示的案例是一个单元测试,但我更感兴趣的是修复事务方法而不是测试本身,因为我过去在“生产代码”中已经有了这个。
模型类:
@Entity
@Table(name = "Task")
data class Task(
@Id
@SequenceGenerator(name = "TaskSeq", sequenceName = "TaskSeq", initialValue = 100)
@GeneratedValue(generator = "TaskSeq")
val id: Long = 0,
@Column(nullable = false)
val name: String,
val description: String,
val inZ: LocalDateTime = LocalDateTime.now(),
var outZ: LocalDateTime = JpaConstants.MAX_DATETIME,
var completed: Boolean = false,
@ManyToOne(cascade = [CascadeType.PERSIST, CascadeType.MERGE, CascadeType.REFRESH])
@JoinColumn(name = "projectId")
var project: Project? = null
) {
}
@Entity
@Table(name = "Project")
data class Project(
@Id
@SequenceGenerator(name = "ProjectSeq", sequenceName = "ProjectSeq", initialValue = 100)
@GeneratedValue(generator = "ProjectSeq")
val id: Long = 0,
@Column(nullable = false)
var name: String,
@OneToMany(mappedBy = "project", cascade = [CascadeType.MERGE, CascadeType.PERSIST, CascadeType.REFRESH])
val tasks: MutableList<Task> = Lists.mutable.empty()
) {
}
服务等级:
@Service
class ProjectServiceImpl(private val projectRepository: ProjectRepository) : ProjectService {
override fun save(project: Project): Project {
return projectRepository.save(project)
}
}
@Service
class TaskServiceImpl(private val taskRepository: TaskRepository, private val projectRepository: ProjectRepository) : TaskService {
override fun save(task: Task): Task {
return taskRepository.save(task)
}
override fun addTaskToProject(projectId: Long, task: Task): Task {
val project = projectRepository.findById(projectId).orElseThrow { RecordNotFoundException("Couldn't find project with id {$projectId}") }
task.project = project
return save(task)
}
}
我正在尝试使用事务方法的类:
class TaskServiceImplTest : TaskApplicationTests() {
@Autowired
private lateinit var taskService: TaskService
@Autowired
private lateinit var taskRepository: TaskRepository
@Autowired
private lateinit var projectService: ProjectService
@Test
@Transactional
fun canInsertTaskToProject() {
val project = projectService.save(Project(name = "Conquer Paris"))
var task = Task(name = "Check how many people we need to hire", description = "")
task = taskService.addTaskToProject(project.id, task)
assertTrue(task.id > 0)
val projects = projectService.findAll()
assertEquals(1, projects.size())
assertEquals(1, projects[0].tasks.size)
assertEquals(task.id, projects[0].tasks[0].id)
}
如果我将 a 添加@Transactional(REQUIRES_NEW)
到服务中的方法,它将起作用,但我不希望它就像在真实事务中调用此方法一样,我希望它相应地回滚。另外我想避免使用太多 REQUIRES_NEW 以避免将来出现问题
如果我@Transactional
从测试方法中删除 ,当我在最后两行测试任务列表的大小时,它将不起作用,因为它们是惰性的。
使它工作的最佳方法是什么?我认为@Transactional
当我使用 db 中的另一个命令时,它会获得尚未提交的最新更新。
如果需要,Java 中的代码也可以:)
提前致谢!
解决方案
根据您的场景,您可以使用@TestEntityManager
以便可以在事务上下文中管理每个测试。这个例子可以帮助你,
推荐阅读
- javascript - 如何为tone.js中正在播放的音符添加事件监听器
- vba - 初始化集合对象时出现 ActiveX 错误
- javascript - json2Csv Angular - 添加总计行
- javascript - 如何使用 jquery 或 javascript 隐藏空的 href 值按钮
- python - 我在给定的图像中找不到此问题的 Oython 代码?
- css - 如何将流体文本大小公式基于 rem 值?
- firebase - 如何让 Firebase.dart 中的 updateProfile 工作?
- c - 如何使用星星作为框架和内部的破折号创建一个框架框?
- airflow - 气流任务调度独特的子任务
- javascript - .join() 函数在 map 函数中无法正常工作