首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >在测试类之外使用Spring /JUnit 5连接到测试生命周期事件

在测试类之外使用Spring /JUnit 5连接到测试生命周期事件
EN

Stack Overflow用户
提问于 2021-01-21 08:28:04
回答 1查看 969关注 0票数 0

JUnit 5具有诸如@BeforeEach@BeforeAll@AfterAll@AfterEach注释等特性,允许您在测试生命周期事件期间执行代码,例如清除在测试之间共享的状态。

我想要一种方法来自动完成某些测试配置,而不必记住在每个测试中放置这些生命周期挂钩。

例如:

如果我有一个Spring测试配置来加载一些存根数据源:

代码语言:javascript
复制
interface DataProvider {
    String getData(String id);
}

还有一个依赖于此的类:

代码语言:javascript
复制
@Component
class ClassThatDependsOnDataProvider {
    private final DataProvider dataProvider;

    @Autowired
    ClassThatDependsOnDataProvider(DataProvider dataProvider) {
        this.dataProvider = dataProvider;
    }

    public String process(String id) {
        String data = dataProvider.get(id);
        return some_processing_of(data);
    }
}

通常情况下,这可能会影响到后端,但是在我的测试中,我会用内存中的解决方案来替换它:

代码语言:javascript
复制
@TestComponent
class InMemoryDataProvider implements DataProvider {
    private Map<String, String> data = new HashMap<>();

    public void setData(String id, String data) {
        data.put(id, data);
    }

    public String getData(String id) {
        return data.get(id);
    }

    public void clear() {
        data.clear();
    }
}

在我的测试中,我可能需要使用它来存根我的后端的数据,比如:

代码语言:javascript
复制
@SpringBootTest
@Import({InMemoryDataProvider.class})
class ClassThatDependsOnDataProviderTests {
    @Autowired InMemoryDataProvider dataProvider;

    @Autowired ClassThatDependsOnDataProvider classThatDependsOnDataProvider;

    @Test
    public void should_correctly_process_data() {
        // given i have an id with a value
        dataProvider.setData("stub_id", "stub_value");

        // when i process my id
        var result = classThatDependsOnDataProvider.process("stub_id");

        // then i receive expected result
        assertThat(result).isWhatIExpect();
    }

    // more @Tests

    // DON'T WANT TO HAVE TO DO THIS IN EACH TEST CLASS
    @AfterEach
    public void tearDown() {
        dataProvider.clear();
    }
} 

我希望能够在这里删除用tearDown()注释的@AfterEach方法,并将该行为移到测试组件/测试假的或者配置类中,这样就可以使用一组这样的提供程序来维护一组测试,这些测试将替换为假版本,而不必手动管理每个测试的生命周期。

是否有某种类型的Spring特性、生命周期事件或JUnit 5特性允许这样做?

请原谅这个简单的例子,显然这个简单的测试是过分的,但它只是一个讨论的参考。假设@MockBean或使用模拟库不是一个选项。

EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2021-01-21 10:30:49

您可以使用JUnit5扩展:https://junit.org/junit5/docs/current/user-guide/#extensions

例如,您的扩展如下所示:

代码语言:javascript
复制
public class InMemoryDataProviderExtension implements AfterEachCallback {

    /**
     * {@inheritDoc}
     */
    @Override
    public void afterEach(final ExtensionContext context) throws Exception {
        final ApplicationContext applicationContext = SpringExtension.getApplicationContext(context);

        final InMemoryDataProvider inMemoryDataProvider = applicationContext.getBean(InMemoryDataProvider.class);
        inMemoryDataProvider.clear();

    }
}

请注意:

  • SpringExtension.getApplicationContext(context);获取spring应用程序上下文,因此您可以检索上下文中定义的beans -扩展实现了AfterEachCallback接口,但是存在于其他扩展点(即BeforeEachCallback、BeforeAllCallback等)

中。

为了激活测试中的扩展:

代码语言:javascript
复制
@SpringBootTest
@ExtendWith(InMemoryDataProviderExtension.class)
public class ClassThatDependsOnDataProviderTests { ... }
票数 2
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/65823561

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档