Appearance
Spring Batch 单元测试指南
单元测试是确保批处理作业可靠性的关键环节。本教程将使用 Kotlin 和注解配置,通过
spring-batch-test
模块简化测试流程。
🧪 一、创建单元测试类
使用注解加载作业上下文并注入测试工具:
kotlin
@SpringBatchTest
@SpringJUnitConfig(SkipSampleConfiguration::class)
class SkipSampleFunctionalTests {
@Autowired
lateinit var jobLauncherTestUtils: JobLauncherTestUtils
// 注意:当有多个Job Bean时需手动指定测试对象
@Test
fun setupJob(@Autowired job: Job) {
jobLauncherTestUtils.job = job
}
}
关键注解说明
@SpringJUnitConfig
:启用 Spring 的 JUnit 测试支持@SpringBatchTest
:自动注入JobLauncherTestUtils
等测试工具
🔁 二、端到端作业测试
完整测试作业从启动到结束的全流程:
kotlin
@Test
fun testEndToEndJob() {
// 1. 准备测试数据
jdbcTemplate.update("DELETE FROM CUSTOMER")
(1..10).forEach { i ->
jdbcTemplate.update(
"INSERT INTO CUSTOMER VALUES (?, 0, ?, 100000)",
i, "customer$i"
)
}
// 2. 启动作业并验证结果
val jobExecution = jobLauncherTestUtils.launchJob()
assertEquals("COMPLETED", jobExecution.exitStatus.exitCode)
}
⚙️ 三、测试单个步骤
对复杂作业中的特定步骤进行精准测试:
kotlin
@Test
fun testSingleStep() {
val stepExecution = jobLauncherTestUtils.launchStep("fileProcessingStep")
// 验证步骤指标
assertEquals(100, stepExecution.readCount)
assertEquals(0, stepExecution.filterCount)
assertEquals(100, stepExecution.writeCount)
}
隔离测试要点
- 仅初始化该步骤所需数据
- 直接验证
StepExecution
中的指标数据 - 避免依赖其他步骤的输出
🎯 四、测试步骤作用域组件
测试依赖步骤上下文的组件(如 ItemReader
):
kotlin
@SpringBatchTest
@SpringJUnitConfig
class StepScopeIntegrationTests {
@Autowired
lateinit var reader: ItemReader<String> // 步骤作用域组件
// 提供模拟的步骤上下文
fun getStepExecution(): StepExecution {
return MetaDataInstanceFactory.createStepExecution().apply {
executionContext.putString("input.data", "A,B,C,D")
}
}
@Test
fun testReader() {
assertNotNull(reader.read()) // 验证组件行为
}
}
作用域激活原理
@SpringBatchTest
自动添加 StepScopeTestExecutionListener
,通过 getStepExecution()
方法模拟真实步骤上下文
🧩 五、模拟领域对象
使用 MetaDataInstanceFactory
简化领域对象创建:
kotlin
@Test
fun testNoWorkFoundListener() {
// 传统方式需手动构造多层对象
// val stepExecution = StepExecution("step", JobExecution(JobInstance(...)))
// 推荐方式:工厂快速创建
val stepExecution = MetaDataInstanceFactory.createStepExecution()
stepExecution.readCount = 0
val exitStatus = NoWorkFoundStepExecutionListener().afterStep(stepExecution)
assertEquals(ExitStatus.FAILED.exitCode, exitStatus.exitCode)
}
领域对象工厂方法清单
kotlin
// 常用工厂方法
MetaDataInstanceFactory.createJobExecution()
MetaDataInstanceFactory.createStepExecution()
MetaDataInstanceFactory.createJobParameters()
✅ 最佳实践总结
场景 | 工具 | 示例 |
---|---|---|
完整作业测试 | JobLauncherTestUtils.launchJob() | 端到端测试 |
步骤隔离测试 | launchStep("stepName") | 单步骤测试 |
作用域组件测试 | @SpringBatchTest + 上下文工厂 | 步骤作用域测试 |
领域对象模拟 | MetaDataInstanceFactory | 对象模拟 |
测试效率提升技巧
- 使用
@MockBean
模拟外部服务依赖 - 对长时间运行作业启用
@DirtiesContext
重置状态 - 结合
TestEntityManager
验证数据库变更
通过本指南,您可系统掌握 Spring Batch 组件的测试方法,确保批处理作业在生产环境中的可靠性。