[Spring] MongoDB 조회 개선 수정
전에 시도했던 조회 개선 데이터를 늘리고 테스트를 진행해보고자 코드를 다시 보았는데
로직이 잘못되었다는것을 알게 되었고 코드를 수정하고 데이터를 추가하여 테스트를 진행해보았다.
현재 게시글 조회의 로직
현재 게시글에 대한 데이터를 가져오기 위해선 아래의 사진과 같이
- MongoDB의 데이터에서 해당 userId 를 가진 Document를 조회한다.
- Mysql에서 해당 유저의 프로필 정보를 가져온다.
각 게시글을 조회를 하기 위해서 게시글 마다 Mysql에서 유저의 프로필 정보를 조회하여
게시글 정보와 프로필 정보를 응답한다.
현재 MongoDB의 Document
현재 몽고디비에는 게시글을 작성한 유저의 PK 값을 저장하고 있다.
성능 개선 방향
- 글을 작성할때 Mysql에서 해당 유저의 프로필 정보를 조회하여 프로필 정보를 함께 저장한다.
- 현재 성능 개선을 위해서는 MySQL에서의 조회와 유저를 분리시키는 작업을 없애면 된다고 판단하였다.
변경한 구조 - 1차 시도
데이터 준비
6만개 데이터
변경 전
변경 후
더 느려졌다..?
userId, nickName, image를 엔티티에 각각 객체로 저장하여 그럴것이라고 판단했다…
변경한 구조 - 2차 시도
데이터 준비
10만 데이터
변경 전
변경 후
Load Time이 조금 빨라진것을 확인할 수 있었다.
데이터를 더 늘려보았다.
데이터 준비
31만개 데이터
변경 전
변경 후
결과
Load Time이 줄어든 것은 확인하였고 게시글 전체의 총 유저 수가 40명정도라서 많이 차이가 나지 않는것 같다고 생각한다.
하지만 이렇게 역정규화를 이용한 과정에도 문제가 있었다.
이 과정의 문제점
- 유저가 게시글을 작성할때 MySQL에서 프로필 조회를 진행하고 게시글 작성을 진행한다.
- 유저가 프로필을 수정할때 해당 유저가 프로필을 수정하기 전 작성한 모든 게시글의 유저 프로필도 수정해야한다.
결론
조회에서는 Load Time이 줄어들었지만 게시글 작성과 수정에서 유저의 프로필을 조회해야하는 로직이 추가 되었다. 결국 조회에서 장점을 얻을 수 있지만 작성과 수정에서 추가로 쿼리가 진행되는 트레이드 오프이다.
해당 문제 해결 방향
주기적으로 일정시간에 모든 게시글의 프로필을 수정한다면 해결할 수 있지 않을까?
이 과정의 예시 사이트
리그오브레전드의 승률 사이트인 op.gg과 같은 사이트에서는 전에 게임을 진행했던 유저 리스트와
해당 유저의 프로필을 들어갔을때 유저의 정보가 다른 경우가 있다.
그렇기에 프로필을 일정시간에 수정할 수 있도록 Scheduler를 만들어보았다.
느낀점
데이터베이스 설계와 추가적인 개선 방향을 고민해보는 시간이 중요하다는 것을 배울 수 있었던 경험이었다.