by 도뎡이 [SQL Query] mysql outer join [2022.02.15 14:06:24]
이전 글에서 답변을 받았었는데요.
핵심은 이러합니다.
=========================================
1. 가족(FAMILY) 테이블에서 나(CLIENT)를 제외한 가족(CLIENT) 데이터를 조회한다.
2. 가족(CLIENT)은 한 사람당 여러 개의 여권(PASSPORT)을 가질 수 있다.
3. 여권(PASSPORT)는 여권 코드(PASSPORT_CODE)와 1:1 관계를 가진다.
=========================================
현재, 재작성된 아래의 쿼리를 실행한 결과 데이터는 파일로 첨부하였습니다.
가족(family) 테이블에서 고객 번호(me_client_id)가 1,039번인 데이터는 총 5개가 있으며,
아래 쿼리의 결괏값도 5개가 나와야 하는 상황입니다.
하지만, 가족(other_client)이 여러 개의 여권을 가지고 있는 경우,
가장 마지막으로 INSERT 된 여권을 조회해서, 가족 테이블과 1:1로 매핑시켜 주어야 합니다.
쿼리를 어떤식으로 작성하면 좋을지 피드백 주시면 감사하겠습니다!
선배님들의 소중한 답변 미리 감사드립니다. (꾸벅)
SELECT F.family_id -- 가족 일련번호 (Key) , F.me_client_id -- 본인 고객 일련번호 (Key) , F.other_client_id -- 가족 고객 일련번호 (Key) , F.gender -- 성별 , F.relationship -- 관계 , C2.cell_phone -- 가족 휴대폰 번호 , C2.phone_number -- 가족 전화번호 , PASS.passport_id -- 여권 일련번호 (Key) , PASS.issue_date -- 여권 발급일 , PASS.expiry_date -- 여권 만료일 , PASS.number -- 여권 번호 , PASS.status -- 여권 상태 FROM family AS F -- 가족 INNER JOIN client AS C1 -- 본인 ON C1.client_id = F.me_client_id INNER JOIN client AS C2 -- 상대방 ON C2.client_id = F.other_client_id LEFT OUTER JOIN ( SELECT P.passport_id , P.client_id , P.issue_date , P.expiry_date , P.number , P.status , PC.name FROM passport AS P -- 여권 INNER JOIN passport_code AS PC ON P.passport_code_id = PC.passport_code_id -- 여권 코드 ) AS PASS ON F.other_client_id = PASS.client_id WHERE F.me_client_id = 1039
-- C1 및 PC 의 조인이 불필요 합니다. -- 불필요한 조인은 제거하세요. SELECT * FROM (SELECT f.family_id -- 가족 일련번호 (Key) , f.me_client_id -- 본인 고객 일련번호 (Key) , f.other_client_id -- 가족 고객 일련번호 (Key) , f.gender -- 성별 , f.relationship -- 관계 , c.cell_phone -- 가족 휴대폰 번호 , c.phone_number -- 가족 전화번호 , p.passport_id -- 여권 일련번호 (Key) , p.issue_date -- 여권 발급일 , p.expiry_date -- 여권 만료일 , p.number -- 여권 번호 , p.status -- 여권 상태 , ROW_NUMBER() OVER(PARTITION BY F.family_id ORDER BY P.passport_id DESC) rn FROM family f -- 가족 INNER JOIN client c -- 상대방 ON f.other_client_id = c.client_id LEFT OUTER JOIN passport p -- 여권 ON f.other_client_id = p.client_id WHERE f.me_client_id = 1039 ) a WHERE rn = 1 ;
-- 서브쿼리 없이 하는 걸 원하시는 듯 하네요. -- SELECT f.family_id -- 가족 일련번호 (Key) , f.me_client_id -- 본인 고객 일련번호 (Key) , f.other_client_id -- 가족 고객 일련번호 (Key) , f.gender -- 성별 , f.relationship -- 관계 , c.cell_phone -- 가족 휴대폰 번호 , c.phone_number -- 가족 전화번호 , p.passport_id -- 여권 일련번호 (Key) , p.issue_date -- 여권 발급일 , p.expiry_date -- 여권 만료일 , p.number -- 여권 번호 , p.status -- 여권 상태 , pc.name -- 여권 코드명 FROM family f -- 가족 INNER JOIN client c -- 상대방 ON f.other_client_id = c.client_id LEFT OUTER JOIN passport p -- 여권(조회용) ON f.other_client_id = p.client_id LEFT OUTER JOIN passport_code pc -- 여권 코드 ON P.passport_code_id = PC.passport_code_id LEFT OUTER JOIN passport s -- 여권(비교용) ON p.client_id = s.client_id AND p.passport_id < s.passport_id WHERE f.me_client_id = 1039 AND s.passport_id IS NULL ;