-
4. 두 번째 요구사항 추가하기 - 도서 대출 현황Kotlin/실전! 코틀린과 스프링 부트로 ... 개발 2023. 8. 7. 10:03
25. 유저 대출 현황 보여주기 - 프로덕션 코드 개발
1. join 쿼리의 종류와 차이점을 이해한다.
2. JPA N + 1 문제가 무엇이고 발생하는 원인을 이해한다.
3. N + 1 문제를 해결하기 위한 방법을 이해하고 활용할 수 있다.
4. 새로운 API를 만들 때 생길 수 있는 고민 포인트를 이해하고 적절한 감을 잡을 수 있다.
Controller를 구분하는 3가지 기준
1. 화면에서 사용되는 API 끼리 모아 둔다.
- 장점
ㆍ화면에서 어떤 API가 사용되는 한 눈에 알기 용이하다
- 단점
ㆍ한 API가 여러 화면에서 사용되면 위치가 애매하다.
ㆍ서버 코드가 화면에 종속적이다.
2. 동일한 도메인끼리 API를 모아둔다.
- 장점
ㆍ화면 위치와 무관하게 서버 코드는 변경되지 않아도 된다.
ㆍ비슷한 API끼리 모이게 되며 코드의 위치를 예측할 수 있다.
- 단점
ㆍ이 API가 어디서 사용되는지 서버 코드만 보고 알기는 어렵다.
3. (간혹) 1 API 1 Controller를 사용한다.
- 장점
ㆍ화면 위치와 무관하게 서버 코드는 변경되지 않아도 된다.
- 단점
ㆍ이 API가 어디서 사용되는지 서버 코드만 보고 알기는 어렵다.
26. 유저 대출 현황 보여주기 - 테스트 코드 개발
- 큰 테스트 코드 1개보다 작은 테스트 코드 2개가 나은 이유
ㆍ복잡한 테스트 1개보다, 간단한 테스트 2개가 유지보수하기 용이하다.
ㆍ테스트가 합쳐지게 되면, 앞 부분에서 실패가 나는 경우 뒷 부분은 아예 검증되지 않는다.
- 그래서 복잡한 테스트 1개보다 작은 테스트 N개를 선호
27. N+1 문제와 N+1 문제가 발생하는 이유
- 서버 코드를 보고 Query를 생각할 수 있어야 한다.
@Transactional(readOnly = true) fun getUserLoanHistories(): List<UserLoanHistoryResponse> { return userRepository.findAll().map { user -> UserLoanHistoryResponse( name = user.name, books = user.userLoanHistories.map { history -> BookHistoryResposne( name = history.bookName, isReturn = history.status == UserLoanStatus.RETURNED ) } ) } }
- 최초에 모든 유저를 가져오고(쿼리 1회), Loop를 통해 유저별로 히스토리를 가져온다(쿼리 N회)
JPA 1 : N 연관관계의 동작원리
- 최초 유저 로딩 시 가짜 List<UserLoanHistory>가 들어간다.
- 시작부터 모든 진짜 히스토리를 들고 오는 것은 비효율적일 수 있기 때문이다.
- 실제 히스토리에 접근할때에 진짜 UserLoanHistory를 불러온다. - 이러한 전략을 Lazy Fetching 이라고 한다.
N + 1 문제를 해결하는 방법
- SQL의 join query를 알아야 한다.
28. SQL join에 대해 알아보자
- 쿼리 한번으로 두 테이블의 결과를 한 번에 보는 법!
- join을 사용할 때 '별칭'을 줄 수도 있다.
select * from user u join user_loan_history ulh on u.id = ulh.user_id
- inner join : 테이블 양쪽에 데이터가 모두 존재하는 경우에만 하나로 합쳐준다.
- left join : 기준테이블을 기준으로 다 보여준다. 없는 데이터는 null로 보여준다.
29. N+1 문제를 해결하는 방법! fetch join
30. 조금 더 깔끔한 코드로 변경하기
31. 두 번째 요구사항 클리어!
'Kotlin > 실전! 코틀린과 스프링 부트로 ... 개발' 카테고리의 다른 글
6. 네 번째 요구사항 추가하기 - Querydsl (0) 2023.08.08 5. 세 번째 요구사항 추가하기 - 책 통계 (0) 2023.08.08 3. 첫 번째 요구사항 추가하기 - 책의 분야 (0) 2023.08.05 2. Java 서버를 Kotlin 서버로 리팩토링 (0) 2023.08.02 1. 리펙토링 준비 (0) 2023.07.31