Home > Blockchain >  @MockBean injected into a constructor-autowired component
@MockBean injected into a constructor-autowired component

Time:10-24

From the official documentation:

When registered by type, any existing single bean of a matching type (including subclasses) in the context will be replaced by the mock

What if the service under test is autowired in the constructor, though? E.g. in Kotlin (I suppose @MockkBean and @MockBean work the same regarding DI):

 @RunWith(SpringRunner.class)
 class ExampleTests @Autowired constructor(val userOfService: UserOfService) {

   @MockkBean
   private lateinit var service: ExampleService

   ...
}

I would expect this example to fail because in order to instantiate ExampleTests Spring has to first obtain a proper instance of UserOfService. That shouldn't be possible at that time, though, because there's no bean of type ExampleService in the application context yet.

Contrary to my expectation, this works. How is it possible?

CodePudding user response:

Because you miss the other part from the documentation :

In either case, if no existing bean is defined a new one will be added.

So @MockBean will also instantiate a bean automatically if that bean is not found in the spring context.

The sequence of actions are mainly as follows :

  1. Start up the spring context which create all the spring BeanDefinition only that are registered in the spring context.

  2. Process @MockBean which will replace the BeanDefinition in (1) or create a new BeanDefinition

  3. Actually instantiate all the beans based on these BeanDefinition. It will handle which bean to be actually instantiated first and later.

  4. Create a test instance (i.e ExampleTests) to execute its test methods. If any beans required to be auto-wired into the test instance are not created , it will fail.

So as long as you define UserOfService bean , ExampleTests can be instantiated as you are now using @MockBean on the ExampleService which means it must exist no matter you define it or not in the spring context for the test.

  • Related