spring-bootkotlinjpatestingspring-data-jpa

Exception "Error creating bean with name 'testEntityManager'" while run test in Kotlin + Springboot


I'm encountering an error when running DataJpaTest test. None of the solutions I've found on the internet have successfully resolved the specific issue I’m facing.

The project was generated using Spring Initializr.

The repository and the entity:

@Repository
interface HouseRepository : JpaRepository<House, Long>

@Entity
data class House(
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    @Column(name = "houseId")
    val houseId: Long? = null
)

The test:

@DataJpaTest
class HouseRepositoryTest {

    @Autowired
    lateinit var houseRepository: HouseRepository

    @Test
    fun shouldSave() {
        val house = House()
        val savedHouse = houseRepository.save(house)
        assertNotNull(savedHouse)
    }
}

The dependencies:

dependencies {
    implementation("org.springframework.boot:spring-boot-starter-data-rest")
    implementation("org.springframework.data:spring-data-jpa:3.4.4")
    implementation("org.hibernate.orm:hibernate-core:6.6.11.Final")
    implementation("org.jetbrains.kotlin:kotlin-reflect")
    runtimeOnly("com.h2database:h2")
    runtimeOnly("org.postgresql:postgresql")

    testImplementation("org.springframework.boot:spring-boot-starter-test")
    testImplementation("org.jetbrains.kotlin:kotlin-test-junit5")
    testRuntimeOnly("org.junit.platform:junit-platform-launcher")
}

The exception:

Error creating bean with name 'testEntityManager' defined in class path resource [org/springframework/boot/test/autoconfigure/orm/jpa/TestEntityManagerAutoConfiguration.class]: Unsatisfied dependency expressed through method 'testEntityManager' parameter 0: No qualifying bean of type 'jakarta.persistence.EntityManagerFactory' available: expected at least 1 bean which qualifies as autowire candidate. Dependency annotations: {}
org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'testEntityManager' defined in class path resource [org/springframework/boot/test/autoconfigure/orm/jpa/TestEntityManagerAutoConfiguration.class]: Unsatisfied dependency expressed through method 'testEntityManager' parameter 0: No qualifying bean of type 'jakarta.persistence.EntityManagerFactory' available: expected at least 1 bean which qualifies as autowire candidate. Dependency annotations: {}
    at app//org.springframework.beans.factory.support.ConstructorResolver.createArgumentArray(ConstructorResolver.java:804)
    at app//org.springframework.beans.factory.support.ConstructorResolver.instantiateUsingFactoryMethod(ConstructorResolver.java:546)
    at app//org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.instantiateUsingFactoryMethod(AbstractAutowireCapableBeanFactory.java:1361)
    at app//org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBeanInstance(AbstractAutowireCapableBeanFactory.java:1191)
    at app//org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:563)
    at app//org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:523)
    at app//org.springframework.beans.factory.support.AbstractBeanFactory.lambda$doGetBean$0(AbstractBeanFactory.java:339)
    at app//org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:347)
    at app//org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:337)
    at app//org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:202)
    at app//org.springframework.beans.factory.support.DefaultListableBeanFactory.instantiateSingleton(DefaultListableBeanFactory.java:1155)
    at app//org.springframework.beans.factory.support.DefaultListableBeanFactory.preInstantiateSingleton(DefaultListableBeanFactory.java:1121)
    at app//org.springframework.beans.factory.support.DefaultListableBeanFactory.preInstantiateSingletons(DefaultListableBeanFactory.java:1056)
    at app//org.springframework.context.support.AbstractApplicationContext.finishBeanFactoryInitialization(AbstractApplicationContext.java:987)
    at app//org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:627)
    at app//org.springframework.boot.SpringApplication.refresh(SpringApplication.java:752)
    at app//org.springframework.boot.SpringApplication.refreshContext(SpringApplication.java:439)
    at app//org.springframework.boot.SpringApplication.run(SpringApplication.java:318)
    at app//org.springframework.boot.test.context.SpringBootContextLoader.lambda$loadContext$3(SpringBootContextLoader.java:144)
    at app//org.springframework.util.function.ThrowingSupplier.get(ThrowingSupplier.java:58)
    at app//org.springframework.util.function.ThrowingSupplier.get(ThrowingSupplier.java:46)
    at app//org.springframework.boot.SpringApplication.withHook(SpringApplication.java:1461)
    at app//org.springframework.boot.test.context.SpringBootContextLoader$ContextLoaderHook.run(SpringBootContextLoader.java:563)
    at app//org.springframework.boot.test.context.SpringBootContextLoader.loadContext(SpringBootContextLoader.java:144)
    at app//org.springframework.boot.test.context.SpringBootContextLoader.loadContext(SpringBootContextLoader.java:110)
    at app//org.springframework.test.context.cache.DefaultCacheAwareContextLoaderDelegate.loadContextInternal(DefaultCacheAwareContextLoaderDelegate.java:225)
    at app//org.springframework.test.context.cache.DefaultCacheAwareContextLoaderDelegate.loadContext(DefaultCacheAwareContextLoaderDelegate.java:152)
    at app//org.springframework.test.context.support.DefaultTestContext.getApplicationContext(DefaultTestContext.java:130)
    at app//org.springframework.test.context.support.DependencyInjectionTestExecutionListener.injectDependencies(DependencyInjectionTestExecutionListener.java:155)
    at app//org.springframework.test.context.support.DependencyInjectionTestExecutionListener.prepareTestInstance(DependencyInjectionTestExecutionListener.java:111)
    at app//org.springframework.test.context.TestContextManager.prepareTestInstance(TestContextManager.java:260)
    at app//org.springframework.test.context.junit.jupiter.SpringExtension.postProcessTestInstance(SpringExtension.java:160)
    at java.base@21.0.4/java.util.stream.ForEachOps$ForEachOp$OfRef.accept(ForEachOps.java:184)
    at java.base@21.0.4/java.util.stream.ReferencePipeline$3$1.accept(ReferencePipeline.java:197)
    at java.base@21.0.4/java.util.stream.ReferencePipeline$2$1.accept(ReferencePipeline.java:179)
    at java.base@21.0.4/java.util.stream.ReferencePipeline$3$1.accept(ReferencePipeline.java:197)
    at java.base@21.0.4/java.util.ArrayList$ArrayListSpliterator.forEachRemaining(ArrayList.java:1708)
    at java.base@21.0.4/java.util.stream.AbstractPipeline.copyInto(AbstractPipeline.java:509)
    at java.base@21.0.4/java.util.stream.AbstractPipeline.wrapAndCopyInto(AbstractPipeline.java:499)
    at java.base@21.0.4/java.util.stream.ForEachOps$ForEachOp.evaluateSequential(ForEachOps.java:151)
    at java.base@21.0.4/java.util.stream.ForEachOps$ForEachOp$OfRef.evaluateSequential(ForEachOps.java:174)
    at java.base@21.0.4/java.util.stream.AbstractPipeline.evaluate(AbstractPipeline.java:234)
    at java.base@21.0.4/java.util.stream.ReferencePipeline.forEach(ReferencePipeline.java:596)
    at java.base@21.0.4/java.util.Optional.orElseGet(Optional.java:364)
    at java.base@21.0.4/java.util.ArrayList.forEach(ArrayList.java:1596)
    at java.base@21.0.4/java.util.ArrayList.forEach(ArrayList.java:1596)
Caused by: org.springframework.beans.factory.NoSuchBeanDefinitionException: No qualifying bean of type 'jakarta.persistence.EntityManagerFactory' available: expected at least 1 bean which qualifies as autowire candidate. Dependency annotations: {}
    at app//org.springframework.beans.factory.support.DefaultListableBeanFactory.raiseNoMatchingBeanFound(DefaultListableBeanFactory.java:2207)
    at app//org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:1630)
    at app//org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:1555)
    at app//org.springframework.beans.factory.support.ConstructorResolver.resolveAutowiredArgument(ConstructorResolver.java:913)
    at app//org.springframework.beans.factory.support.ConstructorResolver.createArgumentArray(ConstructorResolver.java:791)
    ... 45 more

How could I resolve the issue?


Solution

  • The exception is thrown because you do not have EntityManagerFactory bean in your spring container.

    In order to avoid manually creating it, you could add the following dependency:

    implementation("org.springframework.boot:spring-boot-starter-data-jpa")
    

    spring-boot-starter-data-jpa creates beans based on your application.yaml that are needed to work with persistence