250617 TIL #634 UTC / timestamp / 시간 관리

김춘복·6일 전
0

TIL : Today I Learned

목록 보기
638/638

Today I Learned

게시판 리뉴얼을 하면서 datetime으로 있던 시간을 unixtimestamp를 써서 bigint로 관리하게 되었다. 관련된 내용을 정리해보려 한다.


UTC

Coordinated Universal Time, 전세계 표준 시간대

  • 모든 타임존은 UTC를 기준으로 오프셋 +-시간으로 정의된다.

  • KST 한국 표준시는 UTC+9

  • 서버, DB, API 등에서 절대적인 시간 기준으로 가장 많이 사용된다.

Unix Timestamp

  • 1970년 1월 1일 00:00:00 UTC를 기준으로 경과한 초를 정수로 표현한 값

  • 항상 UTC 기준으로 타임존 개념이 없다.

  • 상대적으로 변하지 않고 절대적인 값이라는 장점이 있다.

  • 숫자형이라 연산과 비교가 매우 효율적이고 데이터 전송 시 용량이 적어 효율적이다.

  • 다만 가독성이 안좋고, 32비트에는 2038년에 overflow 된다는 단점이 있다.

  • mariadb 기준 from_unixtime()으로 이 값을 datetime으로 변환 가능하다.

TIMESTAMP vs DATETIME

  • MySQL 기준 비교

  • TIMESTAMP
    내부적으로 UTC 기준으로 저장되어 일관성이 유지되고, 조회 시 세션이나 서버의 타임존에 따라 변환되어 보여진다.
    따라서 사용자의 위치에 따라 시간이 다르게 보여야할 때 사용한다.
    4바이트 기준 2038년에 overflow된다.

  • DATETIME
    입력된 값을 그대로 저장해 타임존 변환 없이 항상 동일한 값으로 조회된다.
    즉, 타임존이 바뀌어도 항상 동일한 시간을 보장한다.

UNIX TIMESTAMP를 썼을 때 장단점

  • TIMESTAMP는 DB 서버/세션 타임존에 따라 조회 시 변환이 일어나 혼란을 줄 수 있다.

  • DATETIME은 입력된 값을 그대로 저장하지만, 그 값이 어떤 타임존 기준인지 명시적이지 않으면 오해의 소지가 있다.

  • BIGINT로 저장한 Unix Timestamp는 어떤 환경에서 조회하든 절대적인 값은 변하지 않아 매우 일관적이다.

  • 정수형이라 시간 간격 계산과 비교, 정렬이 효율적이다.

  • 시간 변환 로직이 DB가 아니라 애플리케이션 계층에 있기 때문에 개발자가 세밀하게 제어할 수 있다.

  • 다만 가독성이 심히 좋지 않고, FROM_UNIXTIME() 같은 함수를 써야해 쿼리가 길고 복잡해질 수 있다. DB의 NOW(), DATE_ADD() 같은 날짜 관련 함수를 쓰기 힘들다.

  • 날짜에 대한 유효성 검증(2월 31일 같은)을 하기 힘들다.


언어별 사용 방법

  • python
import datetime
import time

# Unix Timestamp (초) time.time()은 float으로 반환한다.
not_ts = int(time.time())

# 로컬 DateTime
local_datetime = datetime.datetime.now()

# UTC DateTime
utc_datetime = datetime.datetime.utcnow()
  • javascript
// Unix Timestamp (초)
const unixTimestampSec = Math.floor(Date.now() / 1000);

// 로컬 DateTime
const localDateTime = new Date();

// UTC DateTime
const utcDateTime = new Date().toUTCString();
  • Java
import java.time.Instant;
import java.time.LocalDateTime;
import java.time.ZoneId;
import java.time.ZonedDateTime;


// Unix Timestamp (초)
long unixTimestampSec = Instant.now().getEpochSecond();

// 로컬 DateTime
LocalDateTime localDateTime = LocalDateTime.now();

// UTC DateTime
Instant utcInstant = Instant.now();
profile
Full-Stack Dev / MLOps

0개의 댓글