CS 준비를 하면서 팀원들이랑 얘기하는데 나왔던 주제였다.
보통 JPA는 쓰기 지연을 사용한다. 그래서 쓰기 지연 SQL 저장소에 쿼리를 모아두었다가, flush를 하면 그 순간 쿼리를 날려서 반영시키는 것이 보통.
근데 이전에도 한번 다뤘던 주제인데
@BeforeEach
void setUp(){
User user = User.builder()
.email("test@test.com")
.profileImage("ex")
.nickname("ex")
.isOnline(false)
.type("kakao").build();
User save = userRepository.save(user);
System.out.println(save.getId());
}
여기서 save를 하면 분명 저장소에 모아둬야 하는데, getId()로 아이디 조회가 가능했었다.
GenerationType.IDENTITY를 사용하면 쓰기 지연을 무시하고 저장한다고 했는데 과연 저 사이에 Thread.sleep()을 걸어두면 DB에서 조회가 가능한지 궁금해졌다.
// 유저 생성
User user = User.builder()
.nickname(dto.getNickname())
.email(dto.getEmail())
.password(encoder.encode(dto.getPassword()))
.loginLastDate(LocalDateTime.now()).build();
User saveUser = userRepository.save(user);
Thread.sleep(30000);
간단하게 유저를 만들어서 save시키고 30초의 sleep을 걸어뒀다.
분명 이론상이라면 save에서 저장을 시키기에 db에서 직접 조회가 가능할 것이라 생각.
그러나 찍히지 않는다. 왜지? 그럼 어떻게 id를 얻어오는 거지? 분명 db에 저장이 돼야 id값을 받는 거 아닌가??
지연이 끝나니깐 바로 아이디 값을 불러오는 걸 확인할 수 있었다.
분명 GenerationType.IDENTITY는 쓰기 지연을 무시하고 insert 쿼리를 날리는 것이 맞다.
30초 지연이 되기 전에 insert를 날린 걸 확인할 수 있다. 근데 왜 db에서는 조회가 안되지??
일단 내가 이해한 바로는 아래와 같다.
user의 회원가입을 하나의 트랜잭션에서 처리한다. save를 통해 쓰기 지연을 무시한 상태로 insert가 날아가지만, db에 저장되는 내용은 user 회원가입 트랜잭션 내에서만 보인다. 즉 트랜잭션 커밋이 안되면 다른 세션에서는 확인을 못하는 것.
그래서 내가 직접 확인하려고 하면 트랜잭션이 분리돼서 확인을 못하는 것으로 파악했다.
트랜잭션.. 세상 어렵네
'기타' 카테고리의 다른 글
Openai에서 발표했던 GPT-4o에 대한 간단한 소감 (0) | 2024.05.14 |
---|---|
서비스에서 서비스로 트랜잭션 전파를 알아보자(궁금증) (1) | 2024.03.25 |
어떻게 HTTP는 로그인된 상태를 판단할까? (0) | 2024.02.07 |
분명 JPA에서는 쿼리를 모았다가 날리는 걸로 알았는데? (0) | 2024.02.06 |