21000: cardinality_violation
PostgreSQL의미
단일 행이 예상되는 곳에서 여러 행이 반환되었다. 스칼라 서브쿼리가 여러 행을 반환했거나, MERGE/ON CONFLICT DO UPDATE가 같은 대상 행에 두 번째로 영향을 주려 했다. Class 21에 속한다.
원인
SELECT 목록이나 WHERE = (subquery) 형태에서 사용한 서브쿼리가 여러 행을 반환했거나, 단일 INSERT ... ON CONFLICT DO UPDATE에서 같은 충돌 키가 두 번 이상 제안되었거나('cannot affect row a second time'), MERGE에서 여러 소스 행이 하나의 대상 행과 매칭된 경우다. UPDATE ... FROM은 다중 매칭 시 오류를 발생시키지 않으며, 대상 행은 소스 행 중 하나로만 예측할 수 없게 갱신된다.
해결 방법
서브쿼리가 단일 행을 반환하도록 한다: LIMIT 1을 추가하거나, 집계(MAX/MIN)를 사용하거나, 매칭을 고유하게 만드는 조건을 지정한다. MERGE와 ON CONFLICT 패턴에서는 DISTINCT ON/집계로 소스 쪽 중복을 제거하고, UPDATE ... FROM에서도 조용히 잘못된 결과가 나오지 않도록 동일하게 처리한다. 예상치 못한 다중 매칭을 찾으려면 서브쿼리를 단독으로 실행해 행 수를 확인한다.