강의

멘토링

로드맵

Inflearn brand logo image

인프런 커뮤니티 질문&답변

hj님의 프로필 이미지
hj

작성한 질문수

자바 ORM 표준 JPA 프로그래밍 - 기본편

스프링부트 프로젝트 테스트 코드에서 스프링 컨테이너 없이 직접 엔티티 테스트를 어떻게 할 수 있을까요

작성

·

94

·

수정됨

0

 

<?xml version="1.0" encoding="UTF-8"?>
<persistence version="2.2"
             xmlns="http://xmlns.jcp.org/xml/ns/persistence" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
             xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/persistence http://xmlns.jcp.org/xml/ns/persistence/persistence_2_2.xsd">
    <persistence-unit name="test">
        <properties>
            <!-- 필수 속성 -->
            <property name="javax.persistence.jdbc.driver" value="org.h2.Driver"/>
            <property name="javax.persistence.jdbc.user" value="sa"/>
            <property name="javax.persistence.jdbc.password" value=""/>
            <property name="javax.persistence.jdbc.url" value="jdbc:h2:mem:db;MODE=MySQL "/>
            <property name="hibernate.dialect" value="org.hibernate.dialect.H2Dialect"/>

            <!-- 옵션 -->
            <property name="hibernate.show_sql" value="true"/>
            <property name="hibernate.format_sql" value="true"/>
            <property name="hibernate.use_sql_comments" value="true"/>
            <property name="hibernate.jdbc.batch_size" value="10"/>
            <property name="hibernate.default_batch_fetch_size" value="100" />
            <property name="hibernate.hbm2ddl.auto" value="update" />
        </properties>
    </persistence-unit>
</persistence>

test.resources.META-INF 에 위의 persistence.xml 파일을 작성하였습니다.

 

package dev.shophub.userauthservice.domain.entity;

import jakarta.persistence.EntityManager;
import jakarta.persistence.EntityManagerFactory;
import jakarta.persistence.EntityTransaction;
import jakarta.persistence.Persistence;
import org.junit.jupiter.api.Test;

class EntityTest {

    @Test
    void testEntity() {
        EntityManagerFactory emf = Persistence.createEntityManagerFactory("test");
        EntityManager em = emf.createEntityManager();
        EntityTransaction tx = em.getTransaction();
        tx.begin();

        TestEntity testEntity = new TestEntity();
        testEntity.setName("tester");

        em.persist(testEntity);
        em.flush();

        TestEntity find = em.find(TestEntity.class, testEntity.getId());
        System.out.println("find = " + find);
    }

}
@Data
@Entity
public class TestEntity {
    @Id
    @GeneratedValue
    private Long id;
    private String name;
}

스프링 컨테이너를 띄우지 않고 테스트를 수행하고싶어 위와 같이 코드를 작성하였는데

00:27:16.392 [Test worker] INFO org.hibernate.jpa.internal.util.LogHelper -- HHH000204: Processing PersistenceUnitInfo [name: test]
00:27:16.467 [Test worker] INFO org.hibernate.Version -- HHH000412: Hibernate ORM core version 6.6.4.Final
00:27:16.474 [Test worker] WARN org.hibernate.orm.deprecation -- HHH90000021: Encountered deprecated setting [javax.persistence.jdbc.user], use [jakarta.persistence.jdbc.user] instead
00:27:16.476 [Test worker] WARN org.hibernate.orm.deprecation -- HHH90000021: Encountered deprecated setting [javax.persistence.jdbc.password], use [jakarta.persistence.jdbc.password] instead
00:27:16.477 [Test worker] WARN org.hibernate.orm.deprecation -- HHH90000021: Encountered deprecated setting [javax.persistence.jdbc.url], use [jakarta.persistence.jdbc.url] instead
00:27:16.478 [Test worker] WARN org.hibernate.orm.deprecation -- HHH90000021: Encountered deprecated setting [javax.persistence.jdbc.driver], use [jakarta.persistence.jdbc.driver] instead
00:27:16.502 [Test worker] INFO org.hibernate.cache.internal.RegionFactoryInitiator -- HHH000026: Second-level cache disabled
00:27:16.625 [Test worker] WARN org.hibernate.orm.connections.pooling -- HHH10001002: Using built-in connection pool (not intended for production use)
00:27:16.780 [Test worker] WARN org.hibernate.orm.deprecation -- HHH90000025: H2Dialect does not need to be specified explicitly using 'hibernate.dialect' (remove the property setting and it will be selected by default)
00:27:16.833 [Test worker] INFO org.hibernate.orm.connections.pooling -- HHH10001005: Database info:
	Database JDBC URL [jdbc:h2:mem:db;MODE=MySQL]
	Database driver: org.h2.Driver
	Database version: 2.3.232
	Autocommit mode: false
	Isolation level: undefined/unknown
	Minimum pool size: 1
	Maximum pool size: 20
00:27:17.414 [Test worker] INFO org.hibernate.engine.transaction.jta.platform.internal.JtaPlatformInitiator -- HHH000489: No JTA platform available (set 'hibernate.transaction.jta.platform' to enable JTA platform integration)

Unable to locate persister: dev.shophub.userauthservice.domain.entity.TestEntity
java.lang.IllegalArgumentException: Unable to locate persister: dev.shophub.userauthservice.domain.entity.TestEntity
	at org.hibernate.internal.SessionImpl.firePersist(SessionImpl.java:764)
	at org.hibernate.internal.SessionImpl.persist(SessionImpl.java:745)
	at dev.shophub.userauthservice.domain.entity.EntityTest.testEntity(EntityTest.java:21)
	at java.base/java.lang.reflect.Method.invoke(Method.java:568)
	at java.base/java.util.ArrayList.forEach(ArrayList.java:1511)
	at java.base/java.util.ArrayList.forEach(ArrayList.java:1511)
Caused by: org.hibernate.UnknownEntityTypeException: Unable to locate persister: dev.shophub.userauthservice.domain.entity.TestEntity
	at org.hibernate.metamodel.model.domain.internal.MappingMetamodelImpl.getEntityDescriptor(MappingMetamodelImpl.java:395)
	at org.hibernate.internal.SessionImpl.getEntityPersister(SessionImpl.java:1512)
	at org.hibernate.engine.internal.ForeignKeys.isTransient(ForeignKeys.java:315)
	at org.hibernate.event.internal.EntityState.getEntityState(EntityState.java:64)
	at org.hibernate.event.internal.DefaultPersistEventListener.entityState(DefaultPersistEventListener.java:114)
	at org.hibernate.event.internal.DefaultPersistEventListener.persist(DefaultPersistEventListener.java:87)
	at org.hibernate.event.internal.DefaultPersistEventListener.onPersist(DefaultPersistEventListener.java:79)
	at org.hibernate.event.internal.DefaultPersistEventListener.onPersist(DefaultPersistEventListener.java:55)
	at org.hibernate.event.service.internal.EventListenerGroupImpl.fireEventOnEachListener(EventListenerGroupImpl.java:127)
	at org.hibernate.internal.SessionImpl.firePersist(SessionImpl.java:761)
	... 5 more


Unable to locate persister: dev.shophub.userauthservice.domain.entity.TestEntity
org.hibernate.UnknownEntityTypeException: Unable to locate persister: dev.shophub.userauthservice.domain.entity.TestEntity
	at app//org.hibernate.metamodel.model.domain.internal.MappingMetamodelImpl.getEntityDescriptor(MappingMetamodelImpl.java:395)
	at app//org.hibernate.internal.SessionImpl.getEntityPersister(SessionImpl.java:1512)
	at app//org.hibernate.engine.internal.ForeignKeys.isTransient(ForeignKeys.java:315)
	at app//org.hibernate.event.internal.EntityState.getEntityState(EntityState.java:64)
	at app//org.hibernate.event.internal.DefaultPersistEventListener.entityState(DefaultPersistEventListener.java:114)
	at app//org.hibernate.event.internal.DefaultPersistEventListener.persist(DefaultPersistEventListener.java:87)
	at app//org.hibernate.event.internal.DefaultPersistEventListener.onPersist(DefaultPersistEventListener.java:79)
	at app//org.hibernate.event.internal.DefaultPersistEventListener.onPersist(DefaultPersistEventListener.java:55)
	at app//org.hibernate.event.service.internal.EventListenerGroupImpl.fireEventOnEachListener(EventListenerGroupImpl.java:127)
	at app//org.hibernate.internal.SessionImpl.firePersist(SessionImpl.java:761)
	at app//org.hibernate.internal.SessionImpl.persist(SessionImpl.java:745)
	at app//dev.shophub.userauthservice.domain.entity.EntityTest.testEntity(EntityTest.java:21)
	at java.base@17.0.11/java.lang.reflect.Method.invoke(Method.java:568)
	at java.base@17.0.11/java.util.ArrayList.forEach(ArrayList.java:1511)
	at java.base@17.0.11/java.util.ArrayList.forEach(ArrayList.java:1511)

이러한 오류가 출력되고 실행되지 않습니다.

어떻게 스프링 컨테이너 없이 jpa 관련 테스트를 진행할 수 있을까요?

답변 2

0

안녕하세요. hj님, 공식 서포터즈 y2gcoder입니다.

도움을 드리고 싶지만 질문 내용만으로는 답변을 드리기 어렵습니다.

실제 동작하는 전체 프로젝트를 ZIP파일로 압축해서 구글 드라이브로 공유해서 링크를 남겨주세요.

구글 드라이브 업로드 방법은 다음을 참고해주세요.

https://bit.ly/3fX6ygx


주의: 업로드시 링크에 있는 권한 문제 꼭 확인해주세요


추가로 다음 내용도 코멘트 부탁드립니다.

1. 문제 영역을 실행할 수 있는 방법

2. 문제가 어떻게 나타나는지에 대한 상세한 설명 (오류 화면, 오류 로그 포함)


링크: 공식 서포터즈

링크: 자주하는 질문

감사합니다.

0

안녕하세요, 인프런 AI 인턴입니다.
hj님, 스프링 컨테이너 없이 JPA 관련 테스트를 수행하려고 하시는군요.

에러 메시지에 나타난 “Unable to locate persister: dev.shophub.userauthservice.domain.entity.TestEntity”는 Hibernate가 TestEntity 클래스를 인식하지 못하고 있음을 의미합니다. 이는 일반적으로 persistence.xml 파일에서 엔티티 클래스를 명시적으로 등록하지 않았기 때문에 발생할 수 있습니다.

persistence.xml 파일에 <class> 요소를 추가하여 TestEntity를 포함시켜 보세요:

<persistence-unit name="test">
    <!-- 기존 설정들 ... -->
    <class>dev.shophub.userauthservice.domain.entity.TestEntity</class>
</persistence-unit>

이렇게 클래스 경로를 추가하면 Hibernate가 사용할 엔티티 클래스를 알 수 있게 되어 문제를 해결할 수 있습니다. javax.persistence 관련 설정도 jakarta.persistence로 변경하여 경고 메시지를 없앨 수 있습니다.

이후 다시 테스트를 실행해 보세요. 추가적으로 Persistence.createEntityManagerFactory와 함께 지정한 유닛 이름(test)가 persistence.xml의 유닛 이름과 일치하는지 확인하세요.

위 설정들이 올바르게 되어 있다면, 스프링 컨테이너 없이도 JPA 테스트를 수행할 수 있을 것입니다. 문제가 지속되면 추가적인 설정 문제일 수 있으니 다시 말씀해 주시기 바랍니다.


Spring Boot Reference: Use a Traditional persistence.xml File

hj님의 프로필 이미지
hj

작성한 질문수

질문하기