Instagram-Clone-Coding / Spring_instagram-clone

Instagram Clone Coding - Backend using Spring Framework
http://ec2-52-79-71-191.ap-northeast-2.compute.amazonaws.com
MIT License
82 stars 23 forks source link

게시물 목록 조회(단건, 페이징) API 응답 데이터 추가 & 게시물 관련 쿼리 최적화 #209

Closed seonpilKim closed 2 years ago

seonpilKim commented 2 years ago

📌Linked Issues

✏Change Details

기능 추가

    select
        distinct post0_.post_id as col_0_0_,
        post0_.post_content as col_1_0_,
        post0_.post_upload_date as col_2_0_,
        post0_.member_id as col_3_0_,
        (select
            count(comments8_.post_id) 
        from
            comments comments8_ 
        where
            post0_.post_id = comments8_.post_id) as col_4_0_,
        (select
            count(postlikes9_.post_id) 
        from
            post_likes postlikes9_ 
        where
            post0_.post_id = postlikes9_.post_id) as col_5_0_,
        exists (select
            1 
        from
            bookmarks bookmark3_ 
        where
            bookmark3_.post_id=post0_.post_id 
            and bookmark3_.member_id=?) as col_6_0_,
        exists (select
            1 
        from
            post_likes postlike4_ 
        where
            postlike4_.post_id=post0_.post_id 
            and postlike4_.member_id=?) as col_7_0_,
        post0_.post_comment_flag as col_8_0_,
        post0_.post_like_flag as col_9_0_,
        member1_.member_id as member_i1_13_,
        member1_.member_email as member_e2_13_,
        member1_.member_gender as member_g3_13_,
        member1_.member_image_name as member_i4_13_,
        member1_.member_image_type as member_i5_13_,
        member1_.member_image_uuid as member_i6_13_,
        member1_.member_image_url as member_i7_13_,
        member1_.member_introduce as member_i8_13_,
        member1_.member_name as member_n9_13_,
        member1_.member_password as member_10_13_,
        member1_.member_phone as member_11_13_,
        member1_.member_role as member_12_13_,
        member1_.member_username as member_13_13_,
        member1_.member_website as member_14_13_ 
    from
        posts post0_ 
    inner join
        members member1_ 
            on post0_.member_id=member1_.member_id 
    where
        member1_.member_username in (
            select
                member7_.member_username 
            from
                follows follow6_ cross 
            join
                members member7_ 
            where
                follow6_.follow_member_id=member7_.member_id 
                and follow6_.member_id=?
        ) 
    order by
        post0_.post_id desc limit ?

🔹변경 후 쿼리 ```sql select distinct post0_.post_id as col_0_0_, post0_.post_content as col_1_0_, post0_.post_upload_date as col_2_0_, post0_.member_id as col_3_0_, (select count(comments10_.post_id) from comments comments10_ where post0_.post_id = comments10_.post_id) as col_4_0_, (select count(postlikes11_.post_id) from post_likes postlikes11_ where post0_.post_id = postlikes11_.post_id) as col_5_0_, exists (select 1 from bookmarks bookmark3_ where bookmark3_.post_id=post0_.post_id and bookmark3_.member_id=?) as col_6_0_, exists (select 1 from post_likes postlike4_ where postlike4_.post_id=post0_.post_id and postlike4_.member_id=?) as col_7_0_, post0_.post_comment_flag as col_8_0_, post0_.post_like_flag as col_9_0_, member1_.member_id as member_i1_13_, member1_.member_email as member_e2_13_, member1_.member_gender as member_g3_13_, member1_.member_image_name as member_i4_13_, member1_.member_image_type as member_i5_13_, member1_.member_image_uuid as member_i6_13_, member1_.member_image_url as member_i7_13_, member1_.member_introduce as member_i8_13_, member1_.member_name as member_n9_13_, member1_.member_password as member_10_13_, member1_.member_phone as member_11_13_, member1_.member_role as member_12_13_, member1_.member_username as member_13_13_, member1_.member_website as member_14_13_ from posts post0_ inner join members member1_ on post0_.member_id=member1_.member_id where post0_.member_id in ( select follow5_.follow_member_id from follows follow5_ where follow5_.member_id=? ) or post0_.post_id in ( select hashtagpos6_.post_id from hashtag_posts hashtagpos6_ inner join hashtag_follows hashtagfol7_ on ( hashtagfol7_.member_id=? and hashtagfol7_.hashtag_id=hashtagpos6_.hashtag_id ) inner join posts post8_ on hashtagpos6_.post_id=post8_.post_id and ( post8_.member_id<>? ) ) order by post0_.post_id desc limit ? ```

게시물 관련 쿼리 최적화

1. 각 게시물마다 content에 포함된 멘션 리스트를 파싱하고, 존재하는 username인지 db를 거쳐서 검증하는 쿼리 호출 횟수를 총 N회 -> 1회로 최적화하였습니다. (setMentionAndHashtagList)

🔸변경 전 쿼리 ```sql select member0_.member_id as member_i1_13_, member0_.member_email as member_e2_13_, member0_.member_gender as member_g3_13_, member0_.member_image_name as member_i4_13_, member0_.member_image_type as member_i5_13_, member0_.member_image_uuid as member_i6_13_, member0_.member_image_url as member_i7_13_, member0_.member_introduce as member_i8_13_, member0_.member_name as member_n9_13_, member0_.member_password as member_10_13_, member0_.member_phone as member_11_13_, member0_.member_role as member_12_13_, member0_.member_username as member_13_13_, member0_.member_website as member_14_13_ from members member0_ where member0_.member_username in ( ? , ? , ? ) select member0_.member_id as member_i1_13_, member0_.member_email as member_e2_13_, member0_.member_gender as member_g3_13_, member0_.member_image_name as member_i4_13_, member0_.member_image_type as member_i5_13_, member0_.member_image_uuid as member_i6_13_, member0_.member_image_url as member_i7_13_, member0_.member_introduce as member_i8_13_, member0_.member_name as member_n9_13_, member0_.member_password as member_10_13_, member0_.member_phone as member_11_13_, member0_.member_role as member_12_13_, member0_.member_username as member_13_13_, member0_.member_website as member_14_13_ from members member0_ where member0_.member_username in ( ? , ? , ? ) select member0_.member_id as member_i1_13_, member0_.member_email as member_e2_13_, member0_.member_gender as member_g3_13_, member0_.member_image_name as member_i4_13_, member0_.member_image_type as member_i5_13_, member0_.member_image_uuid as member_i6_13_, member0_.member_image_url as member_i7_13_, member0_.member_introduce as member_i8_13_, member0_.member_name as member_n9_13_, member0_.member_password as member_10_13_, member0_.member_phone as member_11_13_, member0_.member_role as member_12_13_, member0_.member_username as member_13_13_, member0_.member_website as member_14_13_ from members member0_ where member0_.member_username in ( ? , ? , ? ) # (... 생략 ...) ```
🔹변경 후 쿼리 ```sql select member0_.member_id as member_i1_13_, member0_.member_email as member_e2_13_, member0_.member_gender as member_g3_13_, member0_.member_image_name as member_i4_13_, member0_.member_image_type as member_i5_13_, member0_.member_image_uuid as member_i6_13_, member0_.member_image_url as member_i7_13_, member0_.member_introduce as member_i8_13_, member0_.member_name as member_n9_13_, member0_.member_password as member_10_13_, member0_.member_phone as member_11_13_, member0_.member_role as member_12_13_, member0_.member_username as member_13_13_, member0_.member_website as member_14_13_ from members member0_ where member0_.member_username in ( ? , ? , ? ) ```

2. 각 게시물마다 좋아요 숨김 옵션을 설정한 경우, 해당 게시물들의 id로 group by하여 옵션이 적용된 좋아요 횟수 조회 쿼리를 2N회 -> 1회로 최적화하였습니다. (hidePostLikesCountIfPostLikeFlagIsFalse)

🔸변경 전 쿼리 ```sql select postlike0_.post_like_id as post_lik1_22_0_, member1_.member_id as member_i1_13_1_, postlike0_.member_id as member_i2_22_0_, postlike0_.post_id as post_id3_22_0_, member1_.member_email as member_e2_13_1_, member1_.member_gender as member_g3_13_1_, member1_.member_image_name as member_i4_13_1_, member1_.member_image_type as member_i5_13_1_, member1_.member_image_uuid as member_i6_13_1_, member1_.member_image_url as member_i7_13_1_, member1_.member_introduce as member_i8_13_1_, member1_.member_name as member_n9_13_1_, member1_.member_password as member_10_13_1_, member1_.member_phone as member_11_13_1_, member1_.member_role as member_12_13_1_, member1_.member_username as member_13_13_1_, member1_.member_website as member_14_13_1_ from post_likes postlike0_ inner join members member1_ on postlike0_.member_id=member1_.member_id where postlike0_.post_id=? select follow0_.follow_id as follow_i1_5_, follow0_.follow_member_id as follow_m2_5_, follow0_.member_id as member_i3_5_ from follows follow0_ where follow0_.member_id=? select postlike0_.post_like_id as post_lik1_22_0_, member1_.member_id as member_i1_13_1_, postlike0_.member_id as member_i2_22_0_, postlike0_.post_id as post_id3_22_0_, member1_.member_email as member_e2_13_1_, member1_.member_gender as member_g3_13_1_, member1_.member_image_name as member_i4_13_1_, member1_.member_image_type as member_i5_13_1_, member1_.member_image_uuid as member_i6_13_1_, member1_.member_image_url as member_i7_13_1_, member1_.member_introduce as member_i8_13_1_, member1_.member_name as member_n9_13_1_, member1_.member_password as member_10_13_1_, member1_.member_phone as member_11_13_1_, member1_.member_role as member_12_13_1_, member1_.member_username as member_13_13_1_, member1_.member_website as member_14_13_1_ from post_likes postlike0_ inner join members member1_ on postlike0_.member_id=member1_.member_id where postlike0_.post_id=? select follow0_.follow_id as follow_i1_5_, follow0_.follow_member_id as follow_m2_5_, follow0_.member_id as member_i3_5_ from follows follow0_ where follow0_.member_id=? # (... 생략 ...) ```
🔹변경 후 쿼리 ```sql select postlike0_.post_id as col_0_0_, count(postlike0_.post_like_id) as col_1_0_ from post_likes postlike0_ inner join follows follow1_ on ( follow1_.follow_member_id=postlike0_.member_id and follow1_.member_id=? ) where postlike0_.post_id=? group by postlike0_.post_id ```

3. 특정 게시물에 좋아요를 누른 회원 중 본인이 팔로우한 회원을 조회하는 로직에서 발생하는 2개의 쿼리를 하나의 쿼리로 최적화하였습니다. (setFollowingMemberUsernameLikedPost)

🔸변경 전 쿼리 ```sql select follow0_.follow_id as follow_i1_5_, follow0_.follow_member_id as follow_m2_5_, follow0_.member_id as member_i3_5_ from follows follow0_ where follow0_.member_id=? select postlike0_.post_id as col_0_0_, member1_.member_username as col_1_0_ from post_likes postlike0_ inner join members member1_ on postlike0_.member_id=member1_.member_id where ( postlike0_.post_id in ( ? , ? , ? , ? , ? , ? , ? , ? , ? , ? ) ) and postlike0_.member_id=? ```
🔹변경 후 쿼리 ```sql select postlike0_.post_id as col_0_0_, member1_.member_username as col_1_0_ from post_likes postlike0_ inner join members member1_ on postlike0_.member_id=member1_.member_id where ( postlike0_.post_id in ( ? , ? , ? , ? , ? , ? , ? , ? , ? , ? ) ) and ( postlike0_.member_id in ( select follow3_.follow_member_id from follows follow3_ inner join members member4_ on follow3_.follow_member_id=member4_.member_id where follow3_.member_id=? ) ) ```

💬Comment

📑References

✅Check List