Home > front end >  Wiring beans during integration tests with embedded mongo
Wiring beans during integration tests with embedded mongo

Time:12-17

I am using spring-boot (2.2.7.RELEASE) with webflux for a small-ish rest service with mongodb. I have 2 repositories (ARepository, BRepository) implemented something like this:

@Repository
public interface ARepository extends ReactiveMongoRepository<DataDTO, Integer> {
}

I also have an extra service which is using these 2 and a ReactiveMongoTemplate instance. It's wired something like this:

@Slf4j
@Service
public class DefaultTheService implements TheService {
    private final ARepository aRepository;
    private final BRepository bRepository;
    private final ReactiveMongoTemplate mongoTemplate;

    @Autowired
    public DefaultTheService(ARepository aRepository, BRepository bRepository, ReactiveMongoTemplate mongoTemplate) {
        this.aRepository = aRepository;
        this.bRepository = bRepository;
        this.mongoTemplate = mongoTemplate;
    }
}

All is good, it works as it should, no problems there.

Now, I want to write some integration tests and I started like this:

@DataMongoTest
@Slf4j
class DefaultTheServiceTest {

    @Autowired
    private ARepository aRepository;

    @Autowired
    private BRepository bRepository;

    @Autowired
    private ReactiveMongoTemplate reactiveMongoTemplate;

    @Autowired
    private DefaultTheService defaultTheService;

    @Test
    void runTheMagicTest() {
        // empty body, I just want to see if everything wires up correctly.
    }
}

When I want to execute runTheMagicTest (junit5), I am always getting this error:

org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'com.example.DefaultTheServiceTest': Unsatisfied dependency expressed through field 'defaultTheService'; nested exception is org.springframework.beans.factory.NoSuchBeanDefinitionException: No qualifying bean of type 'com.example.DefaultTheService' available: expected at least 1 bean which qualifies as autowire candidate. Dependency annotations: {@org.springframework.beans.factory.annotation.Autowired(required=true)}

    at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredFieldElement.inject(AutowiredAnnotationBeanPostProcessor.java:643)
    at org.springframework.beans.factory.annotation.InjectionMetadata.inject(InjectionMetadata.java:130)

Caused by: org.springframework.beans.factory.NoSuchBeanDefinitionException: No qualifying bean of type 'com.example.DefaultTheService' available: expected at least 1 bean which qualifies as autowire candidate. Dependency annotations: {@org.springframework.beans.factory.annotation.Autowired(required=true)}
    at org.springframework.beans.factory.support.DefaultListableBeanFactory.raiseNoMatchingBeanFound(DefaultListableBeanFactory.java:1716)
    at org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:1272)
    at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:1226)

*! notice the bean name: DefaultTheServiceTest

Normally, I could maybe get away simply creating an instance of DefaultTheService before each test and then calling the methods I want to test, but I'd like to give it a try using spring.

If I simply remove the private DefaultTheService defaultTheService declaration - the test is "running". I am pretty sure I am missing something stupid and I am chasing my tail.

So, can someone ease my pain and point me to the (possibly?) obvious error I am making?

Thanks!

CodePudding user response:

@DataMongoTest:

Annotation that can be used for a MongoDB test that focuses only on MongoDB components.

Using this annotation will disable full auto-configuration and instead apply only configuration relevant to MongoDB tests.

Try a @SpringBootTest for a "full"/default application context instead.

For general information refer to:

For (auto-)configuration details & refinement to:


... setting @DataMongoTest(useDefaultFilters = false) ( fine tuning include-/excludeFilters) can also do the desired.

  • Related