Java 为JUnit4/5创建注释以在测试中初始化和注入对象
我正在为卡夫卡开发一个测试库。该库允许您使用流畅优雅的(?!)API为Kafka开发集成测试。现在,我为Spring Kafka开发了一个版本Java 为JUnit4/5创建注释以在测试中初始化和注入对象,java,junit,apache-kafka,annotations,spring-kafka,Java,Junit,Apache Kafka,Annotations,Spring Kafka,我正在为卡夫卡开发一个测试库。该库允许您使用流畅优雅的(?!)API为Kafka开发集成测试。现在,我为Spring Kafka开发了一个版本 @SpringBootTest(classes = {TestConfiguration.class}) @Kafkaesque( topics = {SpringKafkaesqueTest.CONSUMER_TEST_TOPIC, SpringKafkaesqueTest.PRODUCER_TEST_TOPIC}) class SpringK
@SpringBootTest(classes = {TestConfiguration.class})
@Kafkaesque(
topics = {SpringKafkaesqueTest.CONSUMER_TEST_TOPIC, SpringKafkaesqueTest.PRODUCER_TEST_TOPIC})
class SpringKafkaesqueTest {
@Autowired
private Kafkaesque kafkaesque;
@Test
void consumeShouldConsumeMessagesProducesFromOutsideProducer() {
kafkaTemplate.sendDefault(1, "data1");
kafkaTemplate.sendDefault(2, "data2");
kafkaesque
.<Integer, String>consume()
.fromTopic(CONSUMER_TEST_TOPIC)
.waitingAtMost(1L, TimeUnit.SECONDS)
.waitingEmptyPolls(5, 100L, TimeUnit.MILLISECONDS)
.withDeserializers(new IntegerDeserializer(), new StringDeserializer())
.expecting()
.havingRecordsSize(2)
.assertingThatPayloads(Matchers.containsInAnyOrder("data1", "data2"))
.andCloseConsumer();
}
在每次测试中都需要初始化库:
@Test
void consumeShouldConsumeMessagesProducesFromOutsideProducer() {
kafkaTemplate.sendDefault(1, "data1");
kafkaTemplate.sendDefault(2, "data2");
new SpringKafkaesque(broker)
.<Integer, String>consume()
.fromTopic(CONSUMER_TEST_TOPIC)
.waitingAtMost(1L, TimeUnit.SECONDS)
.waitingEmptyPolls(5, 100L, TimeUnit.MILLISECONDS)
.withDeserializers(new IntegerDeserializer(), new StringDeserializer())
.expecting()
.havingRecordsSize(2)
.assertingThatPayloads(Matchers.containsInAnyOrder("data1", "data2"))
.andCloseConsumer();
}
可能吗?有什么建议吗?JUnit4
一种可能的解决方案是使用反射创建自定义注释处理。您可以使用@Rule
获取测试方法名称,例如:
公共类CustomAnnotationTest{
《卡夫卡夫卡夫卡夫卡夫卡夫卡夫卡夫卡夫卡夫卡夫卡夫卡夫卡夫卡夫卡夫卡夫卡夫卡夫卡夫卡夫卡夫卡夫卡夫卡夫卡夫卡夫卡夫卡夫卡夫卡夫卡;
@统治
public TestName TestName=new TestName();
@以前
公共void init(){
方法=null;
试一试{
方法=this.getClass().getMethod(testName.getMethodName());
}捕获(例外情况除外){
//处理异常
}
if(方法isAnnotationPresent(EmbeddedKafka.class)){
//这里是你的斯普林卡夫卡式实例
//kafkaesqueInstance=新的SpringKafkaesque(经纪人)
//
}
}
@嵌入卡夫卡
@试验
public void testCustomAnnotated(){
//你的测试在这里
}
@保留(RetentionPolicy.RUNTIME)
@目标(ElementType.METHOD)
@嵌入卡夫卡的接口{
}
}
您需要将此实例存储在类级别变量中。对于没有@EmbeddedKafka
注释的方法,此变量将为null
少年5
公共类KafkaesqueResolver实现ParameterResolver{
@凌驾
公共布尔支持参数(ParameterContext ParameterContext,
ExtensionContext(扩展上下文)抛出参数ResolutionException{
返回parameterContext.getParameter().getType()==SpringKafkaesque.class;
}
@凌驾
公共对象resolveParameter(ParameterContext ParameterContext,
ExtensionContext(扩展上下文)抛出参数ResolutionException{
//在此处创建一个SpringKafkaesque实例并返回它
返回新春卡夫卡式();
}
}
接下来,将@ExtendWith(kafkaesquerysolver.class)
注释添加到测试类中,并向测试方法添加一个参数,其中需要SpringKafkaesque的实例:
@extendedwith(kafkaesquerysolver.class)
公共类参数注入测试{
@试验
公共void testNoParams(){
//无需注射
}
@试验
public void testWithParam(SpringKafkaesque实例){
//对实例执行所需操作
}
}
这种情况下不需要自定义注释。我想知道,如果在测试配置中有一种简单的方法使用@KafkaListener
,为什么会这样做……嗨,@ArtemBilan。谢谢你的评论。SpringKafka提供的库的问题在于它是完全异步的。每当有人想从某个主题中获取某些内容时,他必须编写代码,等待该主题中的消息可用,然后将它们放入队列,以此类推。或者,至少,这是我对春天卡夫卡的体验。如果你有更好的主意,请告诉我:)谢谢。但是,如何使用名为testCustomAnnotated
?@riccardo.cardin为其声明一个类级变量并将实例分配给it@riccardo.cardin,我用JUnit 5解决方案更新了我的答案