JPA를 사용하며 겪은 여러 오류들을 기록합니다. (to be continued)
org.hibernate.DuplicateMappingException
JPA는 Entity를 관리합니다. Entity 등록은 클래스에 @Entity를 붙여서 이뤄집니다. @Entity(name="~")로 name 속성을 가집니다. name 속성을 생략하면 클래스명으로 JPA가 관리합니다. 만약 다른 패키지에 동일한 이름의 Entity로 설정한 클래스가 있다면 이러한 오류가 발생합니다. 따라서 name속성에 패키지명까지 붙여서 지정해주는 것이 좋습니다.
resources/META-INF/persistence.xml에서 application 실행 시에 DB 테이블을 자동으로 생성하는 옵션을 아래처럼 지정할 수 있습니다.
<property name="hibernate.hbm2ddl.auto" value="create" />
이렇게 설정해 두면 원하지 않아도 프로젝트에 있는 테이블들이 모두 생성되기 때문에 문제가 될 수 있습니다. 사용하지 않는 것이 좋을듯 합니다.
spring-data-jpa의 경우 application.properties에 선언하는 것으로 설정. 개발 시에는 sql-show와 함께 사용하면 DDL을 볼 수 있어서 편하다고 생각.
JdbcSQLIntegrityConstraintViolationException
Unique index or primary key violation
이건 프로그래밍 실수로 인해 발생할 수 있는 오류입니다.
Primary나 Unique 제약조건을 설정한 컬럼에 대해 그 제약조건을 위반했을 때 발생합니다. PK로 설정된 컬럼의 어떤 값이 DB에 이미들어 있는데 또 insert하려는 경우 등이 이에 해당합니다. 로그를 보면 자세한 원인까지 출력됩니다.
해결 방법 : application.properties에 설정 추가
hibernate 4의 경우
spring.jpa.hibernate.naming.strategy
=org.hibernate.cfg.ImprovedNamingStrategy
hibernate 5의 경우
spring.jpa.hibernate.naming.implicit-strategy
=org.springframework.boot.orm.jpa.hibernate.SpringImplicitNamingStrategy
spring.jpa.hibernate.naming.physical-strategy
=org.springframework.boot.orm.jpa.hibernate.SpringPhysicalNamingStrategy
Review 클래스의 member에 대한 fetch방식이 LAZY면 한번에 Review와 Member를 조회할 수 없음.
review.getMember().getEmail()때문에 오류 발생.
해결 방법
@Query 이용해서 조인시켜서 구하기
이게 제일 편하긴 함. 하지만 left outer join을 2번 해서 그렇게 베스트는 아니라 생각.
@EntityGraph..?
효율은 이게 제일 좋은듯. left outer join 1번만 수행.
@Transactional
최악의 효율.
JPA 조회 결과를 받을 때 DTO 클래스를 만들어서 반환받으면 ConverterNotFoundException가 발생.
왜 인지 모르겠으나, getter를 정의한 인터페이스를 사용해야 정상 작동.
Pageable vs PageRequest
레포지토리의 메서드에 PageRequest를 넘겨줬을 경우, applicationContext load 자체가 안 될 수 있음.
하이버네이트가 만든 쿼리가 정상적인 것 같은데 이유를 모르겠으면
실제 DB를 확인해보기.
DB를 확인해 보니 컬럼명이 file_id로 되어 있었다.
DB의 컬럼명을 수정해준다.
java.sql.SQLSyntaxErrorException:
Table 'naverreservation.hibernate_sequence' doesn't exist
Entity 클래스의 키 자동 생성 전략을 잘못 설정하면 발생.
GenerationType.AUTO로 설정하면 hibernate는 default hibernate_sequence table를 찾음.
IDENTITY로 변경하여 해결.
갓택 오버플로우 답변