본문 바로가기
개발

[sql, sqlalchemy] 특정 조건으로 order_by 정렬하기 - case문

by 박영귤 2023. 8. 3.

데이터를 정렬시키는 코드를 짜다가, 정수 크기순, 혹은 역순 등으로 정렬하는게 아니라, 어떤 문자열일 땐 맨 위로, 어떤건 아래로 가게끔 정렬을 해야할 일이 생겼다.

아래는 요구 조건이다.

유저가 받은 알림들을 타입이 '공지'인 알림을 맨 위로 올리고, 나머지는 그 아래 위치시킨다. 또한, 시간 역순으로 정렬한다.

시간 역순으로 정렬하는 것은, order by created_at DESC 로 작성하면 쉽게 짤 수 있었다.

ORDER BY created_at DESC

이는 flask의 sqlalchemy로는 아래와 같이 짤 수 있다.

Table.query.order_by(Table.created_at.desc())

하지만, 공지인 것만을 맨 위로 올리는건 쉽지 않았다. 구글링좀 해보니 case문을 사용하면 특정 조건을 만족하는 행에 대해 특정 값으로 지정해놓을 수 있다는 것을 알게 되었다.

case문의 사용법은 다음과 같다.

SELECT
	*
FROM 
	table A
ORDER BY 
	CASE WHEN A.product_name = '자전거' THEN 1 
	ELSE
		2
	END

A테이블의 product_name이 자전거인 행은 1로, 그게 아니라면 2로 설정해놓은 것이고, 이로서 새로운 열 한개가 나온 것이라고 볼 수 있다. 그 새로운 열에 대해 order_by한 것이라고 생각하면 된다.

이는 sqlalchemy문법으로 아래와 같이 작성할 수 있다.

order_by(
	case(
    	[(NotificationLog.type_code == 'announcement', 0)],
	    else_ = 1
   )
)

타입이 announcement인 것은 0으로, 그게 아니라면 1로 설정하고 order by 한 것이다. 이 코드의 결과는 아래처럼 공지인 것들만 맨 위로 올라온 것을 볼 수 있다.

아이디랑 타입만 간단하게 출력함