모든 아티클

JSON Sort Keys: 객체의 키를 왜 정렬하는가

JSON 명세는 객체의 키 순서를 형식적으로 정의하지 않습니다 — {"a": 1, "b": 2}{"b": 2, "a": 1}은 동일한 데이터를 나타냅니다. 하지만 실무에서는 사람과 그 데이터를 다루는 도구 모두에게 키 순서가 여전히 자주 중요합니다.

왜 키를 정렬하는가

  • 비교(diff). 동일한 데이터를 가진 두 JSON 문서의 키 순서가 다르면, 텍스트 diff는 잘못된 차이를 보여줍니다. 정렬은 이 문제를 없애줍니다.
  • 결정적인 출력. 같은 객체를 여러 번 직렬화할 경우(해시나 캐시 키 생성 등), 정렬된 키는 매번 같은 결과를 보장합니다.
  • 가독성. 알파벳순으로 정렬된 객체는 특히 큰 구조에서 빠르게 훑어보고 특정 필드를 찾기 더 쉽습니다.

재귀적 정렬

결과를 예측 가능하게 만들기 위해, 정렬은 보통 재귀적으로 적용됩니다 — 최상위 레벨의 키뿐 아니라 어떤 깊이에 있는 모든 중첩 객체의 키에도 적용됩니다. 배열 요소의 순서는 이때 바뀌지 않는데, 배열에서는 요소 순서 자체가 데이터의 의미 있는 부분이기 때문입니다.

필요 없는 경우

JSON을 프로그램만 사용하고 사람이나 diff 도구가 관여하지 않는다면, 키 정렬은 보통 실질적인 이점을 주지 않습니다 — 파서는 필드 순서와 무관하게 객체를 동일하게 읽습니다.

한글은 왜 유니코드 순서 그대로 정렬해도 맞는가

한글 음절(가, 나, 다...)은 유니코드에서 U+AC00부터 U+D7A3까지 하나의 연속된 블록으로 배정되어 있고, 이 배정 자체가 초성·중성·종성 순서를 조합한 알고리즘(초성 인덱스 × 588 + 중성 인덱스 × 28 + 종성 인덱스)으로 설계되어 있어, 코드포인트 순서가 한글 자모 순서(ㄱㄴㄷㄹㅁㅂㅅㅇㅈㅊㅋㅌㅍㅎ)와 정확히 일치합니다. 그 결과 한글로 된 JSON 키를 단순히 코드포인트 기준으로 정렬해도 실제 가나다순과 다르지 않습니다 — 한자나 데바나가리 문자와 달리, 별도의 로케일 인식 콜레이션 없이도 "그냥 되는" 드문 사례입니다.

정렬과 로케일

라틴 문자가 아닌 문자를 포함한 키를 알파벳순으로 정렬할 때 결과는 문자를 바이트 단위(Unicode code point)로 비교하는지, 아니면 언어 규칙을 고려한 로케일 인식 정렬(locale-aware collation)을 사용하는지에 따라 달라집니다. 예를 들어 코드 포인트 기준 비교는 알파벳과 무관하게 항상 대문자를 소문자보다 앞에 놓지만, 로케일을 고려한 정렬은 다른 순서를 만들어낼 수 있습니다.

도구 사용해보기