如何包装JUnit5测试 [英] How can you wrap a JUnit 5 Test

查看:19
本文介绍了如何包装JUnit5测试的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

在JUnit4中,您可以使用规则来包装测试,以便可以在测试运行之前和之后执行代码。在大多数情况下,这可以通过@BEFORE和@AFTER方法或ExternalResource规则完成。但是,一些控制流构造(如Try-with-Resources)不能拆分成两个方法。在大多数情况下,除了这些构造之外,还有其他方法可以将它们拆分成两个方法。例如,使用Try-With-Resources,您可以手动获取并关闭资源,而不是使用Try块。

我遇到的具体问题是,我使用的数据库jOOQ只有接受回调的事务方法。(参见https://www.jooq.org/doc/latest/manual/sql-execution/transaction-management/)您不能调用如下代码:

context.startTransaction()
doStuff()
context.commit() // Or rollback()

在JUnit4中,这是可以的,因为您可以这样编写规则(在Kotlin中,但同等的规则在Java中有效):

class TransactionRule(private val dbSessionManager: DBSessionManager) : TestRule {
    override fun apply(base: Statement, description: Description): Statement {
        return object : Statement() {
            override fun evaluate() {
                dbSessionManager.transaction {
                    base.evaluate()

                }
            }
        }
    }
}

JUnit5中有类似的东西吗?

推荐答案

您可以编写InvocationInterceptor来代替JUnit4规则:

public class TransactionInvocationInterceptor implements InvocationInterceptor {

    @Override
    public void interceptTestMethod(Invocation<Void> invocation,
            ReflectiveInvocationContext<Method> invocationContext,
            ExtensionContext extensionContext) throws Throwable {
        runInTransaction(() -> {
            try {
                invocation.proceed();
            } catch (Throwable t) {
                throw new RuntimeException(t);
            }
        });
    }
}

@ExtendWith(TransactionInvocationInterceptor.class)
class InvocationInterceptorTest {

    @Test
    void test() {
        …
    }
}

一个区别是interceptTestMethod只包装了测试方法,而不是其他生命周期方法,如beforeEach。可以使用InvocationInterceptor中的其他方法单独截取其他生命周期方法,但不能一次截获多个方法(例如,如果要在一个事务中同时调用beforeEach和测试方法)。

这篇关于如何包装JUnit5测试的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆