A Quick Guide to @DirtiesContext – 快速指南@DirtiesContext

最后修改: 2019年 10月 6日

中文/混合/英文(键盘快捷键:t)

1. Overview

1.概述

In this quick tutorial, we’ll learn about the @DirtiesContext annotation. We’ll also show a standard way to use the annotation for testing.

在这个快速教程中,我们将了解@DirtiesContext注解。我们还将展示一种使用注解进行测试的标准方法。

2. @DirtiesContext

2.@DirtiesContext

@DirtiesContext is a Spring testing annotation. It indicates the associated test or class modifies the ApplicationContext. It tells the testing framework to close and recreate the context for later tests.

@DirtiesContext是一个Spring测试注解。它表示相关的测试或类修改了ApplicationContext。它告诉测试框架关闭并为以后的测试重新创建该上下文。

We can annotate a test method or an entire class. By setting the MethodMode or ClassMode, we can control when Spring marks the context for closure.

我们可以注解一个测试方法或整个类。通过设置MethodModeClassMode我们可以控制Spring何时标记上下文进行关闭

If we place @DirtiesContext on a class, the annotation applies to every method in the class with the given ClassMode.

如果我们将@DirtiesContext放在一个类上,该注解将适用于该类中具有给定ClassMode的每个方法。

3. Testing Without Clearing the Spring Context

3.在不清除Spring上下文的情况下进行测试

Let’s say we have a User:

假设我们有一个User

public class User {
    String firstName;
    String lastName;
}

We also have a very simple UserCache:

我们也有一个非常简单的UserCache:

@Component
public class UserCache {

    @Getter
    private Set<String> userList = new HashSet<>();

    public boolean addUser(String user) {
        return userList.add(user);
    }

    public void printUserList(String message) {
        System.out.println(message + ": " + userList);
    }

}

We create an integration test to load up and test the full application:

我们创建一个集成测试来加载和测试整个应用程序。

@TestMethodOrder(OrderAnnotation.class)
@ExtendWith(SpringExtension.class)
@SpringBootTest(classes = SpringDataRestApplication.class)
class DirtiesContextIntegrationTest {

    @Autowired
    protected UserCache userCache;
    
    ...
}

The first method, addJaneDoeAndPrintCache, adds an entry to the cache:

第一个方法,addJaneDoeAndPrintCache,向缓冲区添加一个条目。

@Test
@Order(1)
void addJaneDoeAndPrintCache() {
    userCache.addUser("Jane Doe");
    userCache.printUserList("addJaneDoeAndPrintCache");
}

After adding a user to the cache, it prints the contents of the cache:

在将一个用户添加到缓存中后,它打印了缓存的内容。

addJaneDoeAndPrintCache: [Jane Doe]

Next, printCache prints the user cache again:

接下来,printCache再次打印用户缓存。

@Test
@Order(2)
void printCache() {
    userCache.printUserList("printCache");
}

It contains the name added in the previous test:

它包含前一个测试中添加的名称。

printCache: [Jane Doe]

Let’s say a later test was relying on an empty cache for some assertions. The previously inserted names may cause undesired behavior.

比方说,后来的测试在一些断言上依赖于一个空的缓存。之前插入的名字可能会导致不希望的行为。

4. Using @DirtiesContext

4.使用@DirtiesContext

Now we’ll show @DirtiesContext with the default MethodModeAFTER_METHOD. This means Spring will mark the context for closure after the corresponding test method completes.

现在我们将显示@DirtiesContext与默认的MethodModeAFTER_METHOD。这意味着Spring将在相应的测试方法完成后将上下文标记为关闭。

To isolate changes to a test, we add @DirtiesContext. Let’s see how it works.

为了隔离测试的变化,我们添加@DirtiesContext。让我们看看它是如何工作的。

The addJohnDoeAndPrintCache test method adds a user to the cache. We have also added the @DirtiesContext annotation, which says the context should shut down at the end of the test method:

addJohnDoeAndPrintCache测试方法将一个用户添加到缓存中。我们还添加了@DirtiesContext注解,它说上下文应该在测试方法结束时关闭。

@DirtiesContext(methodMode = MethodMode.AFTER_METHOD)
@Test
@Order(3)
void addJohnDoeAndPrintCache() {
    userCache.addUser("John Doe");
    userCache.printUserList("addJohnDoeAndPrintCache");
}

The output is now:

现在的输出是。

addJohnDoeAndPrintCache: [John Doe, Jane Doe]

Finally, printCacheAgain prints the cache again:

最后, printCacheAgain 再次打印缓存。

@Test
@Order(4)
void printCacheAgain() {
    userCache.printUserList("printCacheAgain");
}

Running the full test class, we see the Spring context reload in between addJohnDoeAndPrintCache and printCacheAgain. So the cache reinitializes, and the output is empty:

运行完整的测试类,我们看到Spring上下文在addJohnDoeAndPrintCacheprintCacheAgain之间重新加载。所以缓存重新初始化,而输出是空的。

printCacheAgain: []

5. Other Supported Test Phases

5.其他支持的测试阶段

The example above shows the after current test method phase. Let’s do a quick summary of the phases:

上面的例子显示了当前测试方法后阶段。让我们对各阶段做一个快速总结。

5.1. Class Level

5.1.班级水平

The ClassMode options for a test class define when the context is reset:

测试类的ClassMode选项定义了上下文何时被重置

  • BEFORE_CLASS: Before current test class
  • BEFORE_EACH_TEST_METHOD: Before each test method in the current test class
  • AFTER_EACH_TEST_METHOD: After each test method in the current test class
  • AFTER_CLASS: After the current test class

5.2. Method Level

5.2.方法级别

The MethodMode options for an individual method define when the context is reset:

单个方法的MethodMode选项定义了上下文何时被重置

  • BEFORE_METHOD: Before the current test method
  • AFTER_METHOD: After the current test method

6. Conclusion

6.结论

In this article, we presented the @DirtiesContext testing annotation.

在这篇文章中,我们介绍了@DirtiesContext测试注解。

As always, the example code is available over on GitHub.

像往常一样,示例代码可在GitHub上获得