org.hibernate.LazyInitializationException( could not initialize proxy ) 에러 질문합니다!
4981
작성한 질문수 2
안녕하세요.
게시글을 등록하는 기능을 구현중인데, LazyInitializationException 에러를 해결 못하고 있습니다.
테이블 관계(Account - Post) 는 양방향 관계로 설정하였고, 다음과 같이 설정했습니다.
Account 테이블
@Entity
@Getter
@Setter
public class Account implements UserDetails {
@Id
@GeneratedValue
private Integer accountNo;
// 다른 컬럼들 생략...
@OneToMany(mappedBy = "account")
private List<Post> post = new ArrayList<>();
Post 테이블
@Entity
@Getter
@Setter
public class Post {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private Integer postNo;
@ManyToOne
@JoinColumn(name = "accountNo")
private Account account;
//다른 컬름들 생략...
public void setAccount(Account account) {
if(this.account != null){
this.account.getPost().remove(this);
}
this.account = account;
this.account.getPost().add(this);
}
문제가 발생한 로직 함수 부분
@PostMapping("")
public ResponseEntity enrollPost(@RequestParam("file") MultipartFile multipartFile,
@RequestParam("content") String content,
@RequestParam("score") float score,
@AuthenticationPrincipal Account account) throws Exception{
Path fileNameAndPath = Paths.get("./images/",multipartFile.getOriginalFilename());
try{
Files.write(fileNameAndPath, multipartFile.getBytes());
}catch (IOException e){
throw new InvalidImageException("이미지 업로드에 실패했습니다.");
}
Post post = new Post();
post.setScore(score);
post.setContent(content);
post.setPostPic(fileNameAndPath.toString());
post.setAccount(account); << 문제가 발생한 부분!! #############
Post save = postRepository.save(post);
위와 같습니다.
문제가 발생한 부분은 아래 함수를 처리하다가 오류가 생겼습니다.
위의 post.setAccount(account) 부분에서
public void setAccount(Account account) {
if(this.account != null){
this.account.getPost().remove(this);
}
this.account = account;
this.account.getPost().add(this); << 문제가 발생한 지점!! ##############
}
account.getPost()를 가져오는 부분에서 Lazy초기화에러가 발생했습니다.
해당 문제는 Account의 post @OneToMany 컬럼에 fetch = FetchType.EAGER 설정을 주면 쉽게 해결이 되는데,
Post의 FetchType을 Eager로 주게 될 경우, 유저를 조회할 때마다 항상 Post를 조회하는게 성능상 문제가 될것같아서 위와 같은 방식은 사용하고 싶지 않습니다.
@PostMapping 함수 로직을 실행하기전에
@AuthenticationPrincipal Account account
인증권한 확인하는부분에서 Accont의 데이터를 한번 조회해오는데, 로그는 다음과 같습니다.
/* select
generatedAlias0
from
Account as generatedAlias0
where
generatedAlias0.email=:param0 */ select
account0_.accountNo as accountN1_0_,
account0_.accountId as accountI2_0_,
account0_.accountName as accountN3_0_,
account0_.accountPwd as accountP4_0_,
account0_.authority as authorit5_0_,
account0_.bio as bio6_0_,
account0_.email as email7_0_,
account0_.instagram as instagra8_0_,
account0_.profilePic as profileP9_0_,
account0_.regDate as regDate10_0_,
account0_.twitter as twitter11_0_,
account0_.updDate as updDate12_0_,
account0_.useStateCode as useStat13_0_
from
Account account0_
where
account0_.email=?
Account 테이블에서 Post를 참조하고 있는 리스트를 가지고 오지 않아서 에러가 발생하는것 같은데, 어떻게 하면 Account가 참조하고 있는 Post정보를 가지고올 수 있을까요?
에러가 발생한 로그는 아래와 같습니다.
// 2020-01-20 22:04:40.867 ERROR 6330 --- [nio-8098-exec-1] o.a.c.c.C.[.[.[/].[dispatcherServlet] : Servlet.service() for servlet [dispatcherServlet] in context with path [] threw exception [Request processing failed; nested exception is org.hibernate.LazyInitializationException: failed to lazily initialize a collection of role: com.toffeestory.backend.account.Account.post, could not initialize proxy - no Session] with root cause
//
// org.hibernate.LazyInitializationException: failed to lazily initialize a collection of role: com.toffeestory.backend.account.Account.post, could not initialize proxy - no Session
// at org.hibernate.collection.internal.AbstractPersistentCollection.throwLazyInitializationException(AbstractPersistentCollection.java:602) ~[hibernate-core-5.3.11.Final.jar:5.3.11.Final]
// at org.hibernate.collection.internal.AbstractPersistentCollection.withTemporarySessionIfNeeded(AbstractPersistentCollection.java:217) ~[hibernate-core-5.3.11.Final.jar:5.3.11.Final]
// at org.hibernate.collection.internal.AbstractPersistentCollection.initialize(AbstractPersistentCollection.java:581) ~[hibernate-core-5.3.11.Final.jar:5.3.11.Final]
// at org.hibernate.collection.internal.AbstractPersistentCollection.write(AbstractPersistentCollection.java:408) ~[hibernate-core-5.3.11.Final.jar:5.3.11.Final]
// at org.hibernate.collection.internal.PersistentBag.add(PersistentBag.java:386) ~[hibernate-core-5.3.11.Final.jar:5.3.11.Final]
// at com.toffeestory.backend.post.Post.setAccount(Post.java:55) ~[main/:na]
// at com.toffeestory.backend.post.PostController.enrollPost(PostController.java:55) ~[main/:na]
답변 2
3
Account 객체의 상태가 Detached 상태기 때문에 LazyLoading을 할 수 없어서 에러가 나는겁니다. @Transactional 안에서 코드를 실행하시면 잘 동작할 겁니다.
제 강좌는 JPA에 대한 강좌는 아니지만 강좌 중에 분명 객체의 상태에 대해 설명한 수업이 있었던 걸로 기억합니다. 해당 부분을 복습해 보시길 추천드립니다.
spring boot 2.7.13-SNAPSHOT trace 소문자 로그 안나옴
0
533
1
<스프링 데이터 Common: 기본 리포지토리 커스터마이징> 에 대한 질문
0
392
1
comment table에서 저장될떄 왜 id값이 2부터저장이되는건가요?
0
407
1
@EnableJpaRepositories 설정을 스프링부트가 어디에서 자동설정하나요?
0
451
0
PersistenceContext 관련 질문드립니다.
0
335
1
지금(Eager), 나중에(Lazy)의 의미를 모르겠습니다
0
338
1
transaction 구간이 길어질 경우의 처리방법 문의드립니다.
0
905
1
docker postgres
0
293
1
Multiple DataSource 사용 시 transaction 관련 질문 드립니다.
0
2908
1
entity 중 null이 아닌 필드만 update 할 방법이 있을까요?
0
1191
1
Eager 모드일 경우, join을 inner join으로 바꾸는 법이 있을까요?
0
385
1
엔티티를 상속받는 DTO가 일반적인가요?
1
1847
1
커스텀 타입 클래스를 String 타입 처럼 이용해 쿼리하는 방법에 대해 질문하고 싶습니다.
0
339
1
연관관계 매핑 어떤식으로 해야될지 감이 안잡힙니다.
0
566
4
EntityManager 주입시 Annotation관련 질문드립니다.
0
565
1
클래스 기반 프로젝션 사용 관련 질문
0
560
1
save 메서드 질문드립니다.
0
258
1
복잡한 통계쿼리도 JPA로 가능한가요?
2
5593
1
find 와 get의 차이가 무엇인가요?
0
890
1
실무에서 JPA 할 때 FK로 개발할때 연관관계를 꼭 맺어주어야 하나요?
0
998
1
\dt Did not find any relations.
0
481
1
소스코드는 어디서 볼 수 있을까요?
1
287
1
table 생성과 select 문에 대한 질문
0
174
1
스프링 데이터 RepositoryTest 관련 질문
0
2173
2





