相关文章推荐

Spring boot @MockBean annotation used to add mocks to a Spring ApplicationContext . In this tutorial, we will learn the different ways to use this annotation.

1. Spring @MockBean Annotation

  • It allows us to mock a class or an interface and record & verify its behaviors .
  • It can be used on the class-level or on fields in either @Configuration classes, or test classes that are @RunWith the SpringRunner .
  • @RunWith(SpringRunner.class)
    public class ApiControllerTest {
      @MockBean
      private ApiService service;
    
    @RunWith(SpringRunner.class)
    @MockBean(ApiService.class) 
    public class ApiControllerTest {
      @Autowired
      private ApiService service;
    
    @RunWith(SpringRunner.class)
    public class ApiControllerTest {
      @Autowired
      private ApiService service;
      @Configuration
        @Import(AppConfiguration.class)
        static class Config {
            @MockBean
            private ApiService service;
    
  • The mock will replace any existing single bean of the same type defined in the context. If no existing bean is defined a new one will be added.
  • Mocks can be registered by type or by bean name.
  • If there is more than one bean of the requested type, @Qualifier metadata must be specified at the field level.
  • @MockBean
    @Qualifier("apiV1")
    private ApiService service;
  • The mock will also be injected into the field when @MockBean is used on a field and registered in the application context.
  • This annotation is @Repeatable and may be specified multiple times when working with Java 8 or contained within an @MockBeans annotation.
  • @MockBeans({ @MockBean(EmployeeService.class), @MockBean(EmployeeRepository.class) })
    public class EmployeeControllerTest 
      @Autowired
      EmployeeService service;
      @Autowired
      EmployeeRepository repository;
    
  • @MockBean is similar to Mockito’s @Mock but with Spring support.
  • 2. Difference between Mockito @Mock and Spring Boot @MockBean

    Both annotations are used to add mock objects, which allow to mock a class or an interface and to record and verify behaviors on it. However, we can prefer to use one over another in a certain way.

    As we write a test that doesn’t need any dependencies from the Spring Boot container, the Mockito‘s @Mock shall be used. It is fast and favors the isolation of the tested component.

    If the test needs to rely on the Spring Boot container and we want also to add or mock one of the container beans then @MockBean from Spring Boot is preferred way to add mocks.

    3. @MockBean in Unit Testing

    We will generally use @MockBean along with either @WebMvcTest or @WebFluxTest annotations. These annotations are for web test slices and are limited to a single controller.

    We can use @MockBean to provide mock implementations for required collaborators in the controller class.

    4. @MockBean Example

    We have already seen the usage of @MockBean in @WebFluxTest example.

    In the given test class, we are testing the REST endpoints of the flux controller class EmployeeController. It tests the api methods and service interaction – while it mocks the persistence layer code (i.e. EmployeeRepository).

    @ExtendWith(SpringExtension.class)
    @WebFluxTest(controllers = EmployeeController.class)
    @Import(EmployeeService.class)
    public class EmployeeControllerTest
        @MockBean
        EmployeeRepository repository;
        @Autowired
        private WebTestClient webClient;
        @Test
        void testCreateEmployee() {
            Employee employee = new Employee();
            employee.setId(1);
            employee.setName("Test");
            employee.setSalary(1000);
            Mockito.when(repository.save(employee)).thenReturn(Mono.just(employee));
            webClient.post()
                .uri("/create")
                .contentType(MediaType.APPLICATION_JSON)
                .body(BodyInserters.fromObject(employee))
                .exchange()
                .expectStatus().isCreated();
            Mockito.verify(repository, times(1)).save(employee);
    

    Drop me your questions in the comments.

    Happy Learning !!

    Sourcecode on Github

    Discover More

    Related Articles And Resources

    About Us

    HowToDoInJava provides tutorials and how-to guides on Java and related technologies.

    It also shares the best practices, algorithms & solutions and frequently asked interview questions.

    Tutorial Series

    Regex

    Maven

    Logging

    TypeScript

    Python

    Meta Links

    About Us

    Advertise

    Contact Us

    Privacy Policy

    Our Blogs

    REST API Tutorial

     
    推荐文章