에듀테크 프로젝트 대시보드
날짜와 시간
시간대 처리에서 사고가 가장 많이 납니다. 규칙은 간단합니다 — 저장은 timestamptz, 표시할 때만 지역 시간대로.
timestamptz — 입력값을 UTC 로 정규화해 저장, 출력 시 세션 TimeZone 으로 변환. 절대 시각.timestamp — 시간대 정보 없이 숫자만 저장. '벽시계 시간'이 필요할 때만(드묾).timestamptz 가 정답입니다.CREATE TABLE events (
id bigint GENERATED ALWAYS AS IDENTITY,
happened_at timestamptz NOT NULL DEFAULT now()
);
SHOW TimeZone; -- 'Asia/Seoul' 등
SET TimeZone = 'UTC'; -- 세션 한정| 함수 | 값 |
|---|---|
now() = current_timestamp | 트랜잭션 시작 시각 (같은 txn 내 고정) |
statement_timestamp() | 현재 문(statement) 시작 시각 |
clock_timestamp() | 실제 벽시계 (호출할 때마다 다름) |
current_date / current_time | 날짜 / 시각 부분 |
SELECT now() - interval '7 days';
SELECT happened_at + interval '1 hour 30 minutes' FROM events;
SELECT age(timestamp '2000-01-01'); -- '25 years ...'
SELECT extract(epoch FROM (now() - happened_at)); -- 경과 초-- 일자별 집계
SELECT date_trunc('day', happened_at) AS day, count(*)
FROM events
WHERE happened_at >= now() - interval '30 days'
GROUP BY day ORDER BY day;
-- 특정 시간대 기준 하루
SELECT * FROM events
WHERE happened_at >= '2026-09-10'::date
AND happened_at < '2026-09-11'::date; -- 반열린 구간이 인덱스 친화적WHERE date(happened_at) = '2026-09-10' 처럼 컬럼에 함수를 씌우면 인덱스를 못 탐 — 위처럼 범위 조건으로