댓글 리스트 좋아요/싫어요 개수와 로그인한 회원의 좋아요 클릭 여부 관련 질문입니다! 0 8 1,886

by 도뎡이 [SQL Query] mysql 댓글 좋아요/싫어요 로그인 회원 댓글 좋아요 여부 [2022.05.25 11:13:35]


tables.png (50,403Bytes)
html.jpg (27,854Bytes)
query-result.png (42,169Bytes)

안녕하세요, 선배님들!

댓글 리스트에 좋아요/싫어요 개수와 로그인한 회원이 좋아요 또는 싫어요를 클릭하였는지 여부를 확인할 수 있는 쿼리를 작성 중입니다.

테이블은 댓글(Main), 회원(Join), 댓글 좋아요(Join) 총 세 가지를 연결하게 되는데요.

하나의 SQL 쿼리에서 댓글 & 회원 정보, 좋아요/싫어요 개수, 로그인한 회원의 댓글 좋아요/싫어요 여부를 조회해야 하는데,

결과를 얻기가 쉽지 않아 선배님들께 조언을 구해보고자 합니다..

 

우선, 현재 작성된 쿼리는 다음과 같습니다.

SELECT
      C.id -- 댓글 번호
    , C.member_id AS '댓글 작성 회원' 
    , M.login_id  -- 회원 id
    , M.name  -- 회원명
    , COUNT(CASE WHEN CL.like_type = 1 THEN 1 END) AS like_cnt -- 특정 댓글의 좋아요 수
    , COUNT(CASE WHEN CL.like_type = 0 THEN 1 END) AS bad_cnt -- 특정 댓글의 싫어요 수
    , (CASE WHEN CL.member_id = 19 THEN CL.like_type ELSE '' END) AS like_type -- 로그인한 회원의 좋아요/싫어요 클릭 여부
FROM
    tb_comment AS C -- 댓글
    INNER JOIN tb_member AS M ON C.member_id = M.id -- 회원
    LEFT OUTER JOIN tb_comment_like AS CL ON C.id = CL.comment_id -- 댓글
GROUP BY
      C.id -- 댓글 번호
    , C.member_id  
    , M.login_id  -- 회원 id
    , M.name  -- 회원명
    , (CASE WHEN CL.member_id = 19 THEN CL.like_type ELSE '' END) -- (group by에 포함되는 게 맞는지?)
ORDER BY
    C.id DESC

 

좋아요/싫어요 여부를 제외하면 나머지 데이터는 정상적으로 출력이 되지만

LEFT JOIN에 의해 데이터가 정상 출력되지 않는 경우가 있는 듯합니다..

앞의 SQL 쿼리를 어떤식으로 처리하면 좋을지 피드백 주시면 감사드리겠습니다!

결과 예시 HTML 페이지와 쿼리 실행 결과도 첨부하도록 하겠습니다!

소중한 답변 미리 감사드립니다 선배님들. 좋은 하루 되세요 :)

by 마농 [2022.05.25 13:08:35]
-- 그룹바이에 포함시킬게 아니라 집계함수로 감싸 줘야 합니다.
-- 변경전 --  
SELECT ...
     , (CASE WHEN CL.member_id = 19 THEN CL.like_type ELSE '' END) AS like_type
  FROM tb_comment 
 GROUP BY ...
     , (CASE WHEN CL.member_id = 19 THEN CL.like_type ELSE '' END)
;
-- 변경후 --  
SELECT ...
     , MAX(CASE WHEN CL.member_id = 19 THEN CL.like_type END) AS like_type
  FROM tb_comment 
 GROUP BY ...
;

 


by 도뎡이 [2022.05.25 13:33:15]

마농 선생님 답변 감사드립니다! 혹시 MAX( )  함수를 사용해야 하는 이유를 간략히 설명해 주실 수 있으실까요?!


by 마농 [2022.05.25 13:50:20]

GROUP BY 집계 쿼리에서 조건에 따른 값을 보여줄 때 (행을 열로 집계할 때)
CASE 와 집계함수를 함께 사용하게 됩니다.
위 예시 쿼리의 COUNT(CASE ~ ) 와 동일한 방식으로 사용된 것입니다.
COUNT 대신 MAX 를 사용했을 뿐입니다.


by 도뎡이 [2022.05.25 14:14:53]

답변 감사드립니다 선생님! 앞의 쿼리가 잘못된 쿼리이거나 성능을 떨어트리는 쿼리는 아닌 것이지요..?


by 마농 [2022.05.25 14:34:45]

MAX 사용 안하고 GROUP BY 에 넣은 것은 잘못된 쿼리입니다.
이 부분은 댓글처럼 수정하시면 되구요.

쿼리 자체가 성능이 좋을 수가 없는 전체 조회 쿼리입니다.
데이터량이 많아지면 문제가 될 수 있습니다.
검색 조건은 없는지? 페이징 처리는 안하는지?
페이징 처리를 하게 된다면
조인 후 페이징 처리가 아닌 페이징 처리후 조인하는 방식으로 개선해야 합니다.


by 도뎡이 [2022.05.25 15:24:29]

MAX를 사용 안하고 GROUP BY에 넣은 것이 잘못되었다는 건 CASE 문으로 작성된 like_type에 대해 말씀하시는 것일까요 선생님?!..

페이징 처리는 차후에 진행하려고 합니다! 조언 감사드립니다 ^^


by 마농 [2022.05.25 15:48:01]

애초 질문이 그거였죠. like_type
그거에 대한 오류 수정 답변 드린 거였구요.
추가질문인 성능에 대해서 추가 답변 드렸구요.

다 작성된 쿼리에 페이징을 적용하는 것은 성능이 고려되지 않은 것입니다.
페이징까지 고려하여 쿼리를 작성해야 합니다.


by 도뎡이 [2022.05.25 16:38:09]

답변 정말 감사드립니다 선생님! 구루비 방문할 때마다 커다란 배움을 얻고 갑니다 ^^.
항상 감사드립니다! 좋은 하루 되세요 :)

댓글등록
SQL문을 포맷에 맞게(깔끔하게) 등록하려면 code() 버튼을 클릭하여 작성 하시면 됩니다.
로그인 사용자만 댓글을 작성 할 수 있습니다. 로그인, 회원가입