ISO 8601
고친 사람 github-actions[bot]
ISO 8601 은 날짜와 시각을 어느 나라에서 읽어도 같은 순간으로 읽히게 적는 법을 정한 국제 표준입니다. 2026-09-24 처럼 큰 단위부터 작은 단위 차례로 적습니다. 이렇게 적어 두면 시스템끼리 날짜를 주고받을 때 몇 월 며칠인지 되묻지 않아도 됩니다.
쉽고 빠른 이해
ISO 8601 은 날짜와 시각을 적는 순서를 하나로 정한 규칙입니다. 서울에서 9월 24일 오후 2시 30분은
2026-09-24T14:30:00+09:00 으로 적습니다.
이게 없으면 03/09/2026 을 받은 쪽이 3월 9일인지 9월 3일인지 알 수 없습니다. 나라마다 읽는 차례가
달라서입니다. 시각도 어느 지역의 시각인지 모르면 같은 글자가 여러 순간을 가리킵니다.
- 연·월·일을 하이픈으로 잇습니다
- 글자 T 를 두고 시·분·초를 콜론으로 잇습니다
- 끝에 세계 기준 시각과 몇 시간 차이 나는지를 붙입니다
시스템끼리 날짜를 주고받을 때 씁니다. 사람에게 보여 줄 때는 그 사람의 지역 방식으로 바꿉니다.
대가는 같은 순간을 적는 방법이 여럿이라는 것입니다. 프로그램마다 읽어 내는 표기가 다릅니다. 그래서 주고받을 때는 그중 한 가지 표기만 골라 씁니다.
상세
이 절은 ISO 8601 문자열 하나를 조각내 읽는 데서 출발합니다. 거기서 날짜와 시간을 적는 다른 표기로 넓혀 갑니다.
ISO(International Organization for Standardization, 국제표준화기구)는 나라마다 다른 방식을 하나로 맞춰 문서로 펴내는 국제 기구입니다. 8601 은 이 기구가 펴낸 문서의 번호입니다. 그래서 ISO 8601 은 「국제표준화기구의 8601 번 문서」라는 뜻의 이름입니다.
날짜를 적는 차례는 나라마다 다릅니다. 미국은 월·일·연, 유럽 여러 나라는 일·월·연, 한국은
연·월·일 차례로 적습니다. 03/09/2026 한 줄이 두 날짜로 읽히는 까닭입니다. ISO 8601 은 차례를
하나로 정해 이 갈림을 없앱니다.
큰 단위에서 작은 단위로
먼저 문자열 하나를 조각으로 나눠 봅니다. 아래는 서울에서 찍은 한 순간입니다.
2026-09-24T14:30:00+09:00
왼쪽에서 오른쪽으로 갈수록 단위가 작아집니다. 조각마다 하는 일은 이렇습니다.
| 조각 | 예 | 하는 일 |
|---|---|---|
| 연 | 2026 |
네 자리로 적습니다 |
| 월 · 일 | 09 · 24 |
두 자리로 적고, 모자라면 앞에 0 을 채웁니다 |
T |
T |
날짜와 시각을 가릅니다 |
| 시 · 분 · 초 | 14:30:00 |
24시간제로 적습니다 |
| 오프셋 | +09:00 |
세계 기준 시각과 몇 시간 차이 나는지 적습니다. 다음 소절에서 봅니다 |
초 뒤에 점과 숫자를 붙이면 초보다 작은 단위를 적습니다. 14:30:00.250 은 14시 30분 0.25초입니다.
자릿수는 필요한 만큼 늘릴 수 있습니다.
뒤쪽 조각은 떼어 내도 됩니다. 2026-09 는 2026년 9월 한 달을 가리킵니다. 2026 은 한 해를
가리킵니다. 적은 데까지만 알고 있다는 뜻입니다.
끝에 붙는 오프셋
같은 14시 30분이라도 서울과 런던에서는 다른 순간입니다. 그래서 시각 끝에 기준 시각과의 차이를 붙입니다. 이 소절은 그 차이가 무엇을 뜻하는지 봅니다.
기준이 되는 것은 UTC(Coordinated Universal Time, 협정 세계시)입니다. 세계가 함께 기준으로 삼는 시각입니다. 지역마다 쓰는 시각은 이 기준보다 몇 시간 앞서거나 뒤집니다. 서울 시각은 UTC 보다 9시간 앞섭니다.
그 차이를 오프셋이라고 부르고 +09:00 처럼 적습니다. 오프셋은 지역 시각에서
UTC 를 뺀 값입니다. 그러니 적힌 시각에서 오프셋을 빼면 UTC 시각이 나옵니다.
2026-09-24T14:30:00+09:00 // 서울 시각
2026-09-24T05:30:00Z // 같은 순간
두 줄은 글자가 달라도 같은 순간을 가리킵니다. 아래 줄 끝의 Z 는 오프셋이 0 이라는 표시입니다.
곧 그 시각이 UTC 그 자체라는 뜻입니다.
오프셋을 아예 안 붙여도 문법에는 맞습니다. 받는 쪽이 문자열 끝을 보고 가르는 차례는 이렇습니다.
flowchart TD
A["시각 문자열을 받았다"] --> B{"끝에 Z 가 붙었나"}
B -->|붙었다| U["UTC 시각이다"]
B -->|없다| C{"+09:00 같은 오프셋이 붙었나"}
C -->|붙었다| O["오프셋을 빼면 UTC 시각이 나온다"]
C -->|없다| L["어느 지역 시각인지 알 수 없다"]
오프셋은 시간대와 다릅니다. 시간대는 「서울」처럼 한 지역이 따르는 시각 규칙 전체를 가리킵니다. 오프셋은 그 규칙이 어느 한 순간에 내놓는 숫자 하나입니다. ISO 8601 문자열에는 이 숫자만 들어가고 지역 이름은 안 들어갑니다.
한 지역의 오프셋이 늘 같지는 않습니다. 서머타임은 여름철에 시계를 한 시간 앞당기는 제도입니다. 이 제도를 쓰는 지역은 여름과 겨울의 오프셋이 한 시간 다릅니다.
이미 지나간 순간은 그때의 오프셋이 정해져 있습니다. 그래서 오프셋만 적어도 그 순간을 되살릴 수 있습니다.
앞으로 열릴 회의는 다릅니다. 그날의 오프셋은 그 지역 규칙에 달려 있습니다. 오늘 계산한 오프셋을 미리 박아 두면 어긋날 수 있습니다. 그날이 서머타임 전환 뒤이거나 그사이 규칙이 고쳐졌을 때입니다. 그래서 이런 시각은 시간대 이름을 따로 들고 다닙니다.
글자 순서가 곧 시간 순서
큰 단위를 앞에 두고 자릿수를 고정하면 쓸모 있는 성질이 하나 생깁니다. 문자열을 글자 순서대로 정렬한 결과가 시간 순서와 같아집니다. 날짜를 숫자로 바꾸지 않고 문자열 비교만으로 앞뒤를 가릴 수 있다는 뜻입니다.
2026-09-24T09:05:00Z
2026-09-24T14:30:00Z
2026-10-01T00:00:00Z
세 줄을 글자 순서로 늘어놓으면 위와 같습니다. 이것이 시간 순서이기도 합니다. 앞자리 0 이 빠져
T9:05 로 적혔다면 이 줄은 T14:30 보다 뒤로 밀립니다. 글자 9 가 글자 1 보다 뒤에 오기
때문입니다.
이 성질에는 조건이 셋 붙습니다. 첫째, 모든 값의 오프셋이 같아야 합니다. 오프셋이 섞이면 글자 순서와 시간 순서가 갈립니다.
2026-09-24T06:00:00Z // UTC 06:00
2026-09-24T14:30:00+09:00 // UTC 05:30
글자 순서로는 위 줄이 먼저 옵니다. 그런데 아래 줄을 UTC 로 바꾸면 05시 30분이라 더 이른 순간입니다.
둘째, 같은 오프셋은 같은 글자로 적어야 합니다. Z 와 +00:00 은 둘 다 오프셋 0 입니다. 한쪽은
…05:30:00Z 로, 다른 쪽은 …05:30:00+00:00 으로 적으면 같은 순간인데도 문자열로는 다른 값이 됩니다.
셋째, 초 아래 자릿수도 같아야 합니다.
2026-09-24T05:30:00Z // 먼저인 순간
2026-09-24T05:30:00.5Z // 0.5초 뒤
글자 순서로는 아래 줄이 먼저 옵니다. 점(.)이 글자 Z 보다 앞서기 때문입니다. 그래서 로그나
파일 이름에 시각을 찍을 때는 흔히 전부 UTC 로 맞추고 Z 를 붙입니다. 초 아래 자릿수도 하나로 정해 둡니다.
기본 형식과 확장 형식
지금까지 본 표기는 하이픈과 콜론으로 조각을 가른 확장 형식입니다. 구분 기호를 모두 뺀 기본 형식도 같은 표준에 들어 있습니다.
2026-09-24T14:30:00+09:00 // 확장 형식
20260924T143000+0900 // 기본 형식
두 줄은 같은 순간입니다. 기본 형식은 짧고 콜론이 없어서 파일 이름처럼 콜론을 쓰기 곤란한 곳에 맞습니다. 대신 사람 눈으로 조각을 가르기는 어렵습니다.
날짜를 적는 다른 두 표기
연·월·일 말고도 날짜를 가리키는 표기가 둘 더 있습니다. 하나는 그해의 몇째 날인지로 적습니다. 다른 하나는 몇째 주의 무슨 요일인지로 적습니다. 셋 다 같은 날을 가리킬 수 있습니다.
| 표기 | 2026-09-24 를 적으면 | 읽는 법 |
|---|---|---|
| 달력 날짜 | 2026-09-24 |
9월 24일 |
| 서수 날짜 | 2026-267 |
그해의 267번째 날 |
| 주 날짜 | 2026-W39-4 |
39번째 주의 넷째 날 |
주 날짜에서 한 주는 월요일에 시작합니다. 요일 번호는 월요일이 1, 일요일이 7 입니다. 그래서 위의 넷째 날은 목요일입니다.
주 날짜의 연도는 달력의 연도와 어긋날 수 있습니다. 한 해의 첫 주를 「그해 첫 목요일이 든 주」로 정하기 때문입니다. 달리 말하면 한 주는 그 주의 목요일이 든 해에 속합니다. 그래서 해가 바뀌는 주의 며칠은 앞뒤 해로 넘어갑니다.
2027-01-01 을 주 날짜로 적으면 2026-W53-5 입니다. 그 주의 목요일은 2026년 12월 31일입니다.
목요일이 2026년에 있으니 월요일부터 일요일까지 주 전체가 2026년의 마지막 주가 됩니다.
flowchart TD
subgraph W["2026-W53 · 한 주는 월요일에 시작"]
subgraph Y1["달력으로 2026년"]
D1["월 12-28"] --> D2["화 12-29"] --> D3["수 12-30"] --> D4["목 12-31 · 이 목요일이 2026년"]
end
subgraph Y2["달력으로 2027년"]
D5["금 01-01 · 2026-W53-5"] --> D6["토 01-02"] --> D7["일 01-03"]
end
D4 --> D5
end
그림의 아래 세 날은 달력으로는 2027년인데 주 날짜로는 2026년입니다. 주 날짜의 연도를 달력 연도로 착각하고 찍으면 연말연초 며칠만 엉뚱한 해로 찍히는 버그가 납니다.
기간과 구간
ISO 8601 은 한 순간뿐 아니라 시간의 길이도 적습니다. 길이만 적는 표기를 기간이라 합니다. 두 순간 사이를 적는 표기는 구간이라 합니다.
기간은 글자 P 로 시작합니다. 그 뒤에 숫자와 단위 글자를 큰 단위부터 붙입니다. 시·분·초 앞에는
T 를 한 번 둡니다.
P3D // 사흘
PT30M // 30분
P1Y2M10DT2H // 1년 2개월 10일 2시간
M 이 두 번 나오는 데 주의해야 합니다. T 앞의 M 은 달입니다. 뒤의 M 은 분입니다. 그래서
P1M 은 한 달, PT1M 은 1분입니다.
구간은 두 값을 슬래시 / 로 잇습니다. 시작과 끝을 적어도 됩니다. 시작과 기간을 적어도 됩니다.
2026-09-24/2026-09-30 // 시작과 끝
2026-09-24/P7D // 시작과 기간
RFC 3339 프로필
인터넷에서 주고받는 날짜는 대개 RFC 3339 를 따릅니다. RFC 3339 는 RFC(Request for Comments)라 부르는 인터넷 규칙 문서 묶음의 하나입니다. ISO 8601 에서 표기 하나만 골라 좁힌 규칙을 담고 있습니다.
큰 표준에서 일부만 골라 쓰기로 정한 규칙을 프로필이라고 부릅니다. RFC 3339 는 ISO 8601 의 프로필입니다. 새 인터넷 프로토콜에는 이 프로필을 쓰기를 권합니다.
프로필이 필요한 까닭은 ISO 8601 의 넓이에 있습니다. 지금까지 보았듯 조각을 떼거나, 구분 기호를 빼거나, 날짜를 주 단위로 적을 수 있습니다. 받는 프로그램이 이 모두를 읽어야 한다면 읽는 코드를 짜기가 까다로워집니다.
문자열을 읽어 값으로 바꾸는 코드를 파서라고 부릅니다. 파서마다 지원하는 표기가 다르면 한쪽이 쓴 날짜를 다른 쪽이 못 읽습니다. 프로필은 표기를 하나로 좁혀 이 어긋남을 막습니다.
| ISO 8601 | RFC 3339 | |
|---|---|---|
| 뒤쪽 조각 떼기 | 된다 | 연·월·일을 다 적는다 |
| 구분 기호 | 넣어도 빼도 된다 | 하이픈과 콜론을 넣는다 |
| 오프셋 | 없어도 된다 | 시각에는 꼭 붙인다 |
| 주 날짜 · 서수 날짜 · 기간 | 있다 | 없다 |
| 날짜와 시각 사이 | T |
T, 읽기 쉽게 빈칸도 쓴다 |
표의 오른쪽 열은 선택지를 거의 다 없앴습니다. 선택지가 적을수록 파서끼리 서로 다르게 읽을 틈도 줄어듭니다.
그래서 RFC 3339 로 적은 문자열은 대개 올바른 ISO 8601 문자열이기도 합니다. 예외는 표의 마지막 줄,
날짜와 시각 사이를 빈칸으로 적은 경우입니다. ISO 8601 은 그 사이에 T 를 둡니다.
두 쪽 모두 초 칸에 60 을 허용합니다. 한 분을 61초로 늘리는 윤초를 적기 위해서입니다.
1990-12-31T23:59:60Z 는 1990년 끝에 끼워 넣은 윤초를 가리킵니다.
JSON(JavaScript Object Notation)에는 날짜 타입이 따로 없습니다. 그래서 날짜는 문자열로 담깁니다. 그 문자열은 대개 RFC 3339 프로필을 따릅니다.
맞는 곳과 안 맞는 곳
ISO 8601 이 제값을 하는 곳은 시스템 사이의 경계입니다. 보내는 쪽과 받는 쪽이 어느 언어로 짰든 같은 순간으로 읽습니다. 로그와 파일 이름에도 맞습니다. 앞에서 본 대로 정렬이 따라오기 때문입니다.
사람에게 보여 줄 때는 맞지 않습니다. 사용자는 자기 나라 방식으로 읽는 편이 편합니다. 그래서 주고받을 때는 ISO 8601 로 적습니다. 사용자의 지역 방식으로는 화면에 띄울 때만 바꿉니다.
계산이 잦은 값도 문자열로 들고 있지 않습니다. 두 시각의 차이를 구하려면 문자열을 매번 숫자로 되돌려야 합니다. 그런 값은 유닉스 시간처럼 기준 시각부터 흐른 초를 세는 숫자로 둡니다. ISO 8601 로는 밖으로 내보낼 때만 적습니다.
관련 항목
이 표기를 펴내거나 좁혀 쓰는 기구와 문서
ISO · RFC 3339 · RFC · IETF · RFC 9557
이 문자열이 기대는 시간 기준
UTC · UTC 오프셋 · 시간대 · 서머타임 · 그레고리력 · 윤초 · 타임스케일
이 표준이 적는 시간 값의 하위 종류
타임스탬프 · 달력 날짜 · 서수 날짜 · ISO 주 날짜 · 기간 · 시간 구간
같은 순간을 다른 꼴로 담는 표현 수단
유닉스 시간 · 에포크 · HTTP-date · RFC 2822
이 문자열에 찍히는 시각을 내는 시계
이 문자열을 싣거나 읽는 데이터 형식과 작업
다른 이름: ISO 8601 형식 · ISO 날짜 표기