본문으로 건너뛰기
피드

블로그 글이 현재 시간을 알려준다? CDN 헤더로 만든 서버리스 시계 실험

frontend 약 9분
vote
0
댓글
북마크

이 글은 Cloudflare CDN의 응답 헤더와 브라우저 PerformanceResourceTiming API를 이용해 웹페이지 안에서 현재 시간을 추정하는 실험을 다룬다. NTP처럼 전용 시간 서버를 운영하지 않고도 CDN이 사실상 시간 기준점처럼 동작할 수 있다는 아이디어다. 실제 테스트에서는 웹 시계 오차 범위가 약 60ms로, ntpdig의 약 6ms보다 한 자릿수 정도 덜 정밀했다.

  • 1

    Cloudflare CDN 응답 헤더에 서버 측 타임스탬프를 넣고 브라우저에서 시간을 추정

  • 2

    PerformanceResourceTiming으로 DNS, TCP, TLS, 대기 시간 등을 분리해 네트워크 지연을 보정

  • 3

    웹 시계는 테스트에서 대략 60ms 오차 범위를 보였고 ntpdig는 약 6ms 수준

  • 4

    HTTPS 인증 덕분에 보안 없는 NTP 응답 변조 문제를 일부 피할 수 있음

  • 5

    Cloudflare는 공식 시간 서버가 아니므로 실사용 동기화 시스템으로 의존하긴 위험

CDN을 시간 서버처럼 써보기

  • 이 글의 아이디어는 단순한데 꽤 기발함. 웹페이지가 Cloudflare CDN을 통해 아주 작은 파일을 요청하고, 응답 헤더에 찍힌 서버 측 시간을 이용해 현재 시간을 추정함

    • 전통적인 시간 동기화는 NTP(Network Time Protocol) 서버와 데몬이 필요함
    • 여기서는 Cloudflare Pages에 올린 작은 정적 자산, CDN 헤더 변환 규칙, 브라우저 자바스크립트만으로 비슷한 걸 해봄
  • 핵심은 Cloudflare가 응답을 만들 때 HTTP 헤더에 시간 정보를 넣는 것임

    • 예를 들어 http.request.timestamp.sec 같은 값이 응답 헤더에 들어감
    • 브라우저는 그 응답을 받은 뒤 PerformanceResourceTiming API로 요청의 세부 타이밍을 분석함
  • 문제는 서버가 찍은 시간은 브라우저에 도착하는 순간 이미 과거가 됐다는 점임

    • 그래서 NTP처럼 왕복 시간(round trip time)을 보고 네트워크 지연을 추정해야 함
    • 보통은 응답 지연을 왕복 시간의 절반쯤으로 가정하지만, 네트워크 경로가 비대칭이면 틀릴 수 있음
sequenceDiagram
    participant 브라우저
    participant 클라우드플레어CDN
    participant 클라우드플레어페이지
    participant 성능타이밍API
    브라우저->>클라우드플레어CDN: 작은 자산 요청
    클라우드플레어CDN->>클라우드플레어페이지: 원본 응답 확인
    클라우드플레어CDN-->>브라우저: 시간 헤더가 포함된 응답
    브라우저->>성능타이밍API: 네트워크 단계별 타이밍 조회
    성능타이밍API-->>브라우저: DNS, TCP, TLS, 대기 시간 제공
    브라우저->>브라우저: 지연 보정 후 현재 시간 추정

브라우저 타이밍 API가 은근히 큰일 함

  • PerformanceResourceTiming은 개발자 도구 네트워크 탭에 보이는 정보를 자바스크립트에서 꺼내 쓰게 해주는 API임

    • DNS 조회, 연결, TLS 설정, 서버 대기, 수신 같은 단계가 분리돼 보임
    • 글쓴이는 이 정보를 이용해 시간 계산에서 DNS, TCP 핸드셰이크, TLS 초기화 지연을 제외하려고 함
  • 요청과 응답이 워낙 작아서 ‘sending’과 ‘receiving’은 0ms처럼 보일 수 있음

    • 작은 요청과 응답이 단일 패킷에 들어가면 전송 자체는 측정상 거의 즉시 끝난 것처럼 보임
    • 결국 의미 있는 구간은 네트워크와 서버가 작업하는 ‘waiting’ 쪽임
  • Cloudflare의 서버 측 타이밍 정보도 보정에 도움을 줌

    • 클라이언트만 보면 네트워크 지연과 서버 지연을 구분하기 어려움
    • cf.timings.origin_ttfb_msec 같은 값은 CDN이 Cloudflare Pages 응답을 기다린 시간을 알려줘서, 서버가 언제 타임스탬프를 만들었는지 더 잘 추정하게 해줌

중요

> 글쓴이 테스트에서 웹 시계는 자주 약 60ms 오차 범위를 보였고, ntpdig time.cloudflare.com은 약 6ms 수준이었다고 함. 한 자릿수 차이라서 데모로는 재밌지만 정밀 시간 동기화 대체재는 아님.

정확도와 보안, 그리고 함정

  • 이 방식은 Cloudflare CDN 서버의 시계와 꽤 그럴듯하게 맞을 수 있음

    • 글쓴이는 ntpdig 결과와 비교했을 때 웹 시계가 130±70ms 뒤처진다고 나왔고, 두 측정값은 오차 범위 안에서 맞아떨어졌다고 함
    • GPS 디버깅 앱과도 비교했는데, 웹 시계와 GPS 시간이 거의 같이 움직였다고 함
  • 그래도 Cloudflare는 공식 시간 서버가 아님. 이게 제일 중요한 주의점임

    • CDN 서버의 시간이 틀리면 브라우저 계산이 아무리 정교해도 틀린 시간을 정교하게 보여줄 뿐임
    • 글쓴이도 Cloudflare의 명시적 보장 없이 이걸 데모 이상으로 보긴 위험하다고 선을 그음
  • NTP와 비교하면 보안 측면에서 흥미로운 장점도 있음

    • 전통적 NTP는 보안이 약하다는 지적을 오래 받아왔고, 중간자 공격자가 응답을 조작하면 시스템 시간이 망가질 수 있음
    • NTS(Network Time Security)는 이를 암호학적으로 인증하려는 대안임
    • CDN 방식은 HTTPS의 인증된 암호화 덕분에, 적어도 중간에서 응답을 함부로 바꾸는 공격은 막기 쉬움

⚠️주의

> Microsoft의 Secure Time Seeding(STS)은 TLS 메타데이터를 시간 기준으로 쓰려다, 실제로는 많은 서버가 해당 필드에 랜덤 데이터를 넣는 바람에 시계가 엉뚱한 시간으로 리셋되는 문제가 있었다고 함. ‘시간 서버가 될 생각이 없는 시스템’을 시간 서버처럼 쓰면 이런 사고가 난다는 경고 사례임.

결론은 장난감 같지만 배울 게 많음

  • 이 실험은 전용 서버 없이 브라우저와 CDN만으로 시간 동기화를 흉내 낸다는 점에서 웹다운 해킹임

    • Cloudflare Workers도 필요 없고, GitLab에 올린 파일과 Cloudflare Pages, CDN 설정만 있으면 됨
    • 서버는 엄청 많지만 개발자가 직접 관리하는 서버는 없으니 ‘서버리스’라고 부르는 맥락도 이해됨
  • 실사용 시간 동기화 프로토콜로는 부족하지만, 브라우저 성능 API 활용 예제로는 꽤 맛있음

    • 네트워크 타이밍을 단순 성능 분석이 아니라 시간 보정 계산에 사용함
    • 여러 번 요청해서 통계 분석을 적용하면 정밀도를 더 끌어올릴 여지도 있다고 함
  • 개발자 입장에서는 “내 시스템 시간이 생각보다 자주 틀릴 수 있다”는 점도 가져갈 만함

    • 절전, suspend, hibernate 이후에는 시계가 살짝 어긋나는 일이 흔함
    • CMOS 배터리가 없거나 고장 난 장비는 훨씬 크게 어긋날 수 있음

기술 맥락

  • 이 글에서 선택한 기술적 핵심은 NTP 서버를 직접 운영하지 않고 CDN 응답 헤더를 시간 기준으로 쓰는 거예요. 왜냐하면 CDN은 이미 전 세계 가까운 엣지에 배치돼 있어서, 대부분의 사용자가 낮은 지연 시간으로 접근할 수 있거든요.

  • 브라우저의 PerformanceResourceTiming API를 같이 쓰는 이유는 단순히 서버 시간이 몇 시인지 받는 것만으로는 부족하기 때문이에요. 응답이 오는 동안 시간이 지나가니까, DNS나 TLS 같은 구간을 분리해서 실제 대기 시간을 더 잘 추정해야 해요.

  • Cloudflare 서버 측 타이밍을 보는 것도 같은 이유예요. 클라이언트 입장에서는 서버 처리 지연과 네트워크 지연이 섞여 보이는데, CDN이 제공하는 타이밍 값을 쓰면 타임스탬프가 생성된 위치를 조금 더 좁힐 수 있어요.

  • 다만 이 방식은 공식 시간 서비스가 아니라는 한계가 커요. Cloudflare가 시간 정확도를 약속한 게 아니기 때문에, 시계가 틀리면 HTTPS로 안전하게 틀린 시간을 받는 상황이 될 수 있어요.

  • 그래서 결론은 프로덕션 대체재가 아니라 웹 플랫폼 실험에 가까워요. NTP가 하는 왕복 시간 추정, NTS가 다루는 인증 문제, 브라우저 타이밍 API의 정밀도를 한 번에 엮어 보여주는 데 가치가 있어요.

재밌는 해킹이지만 ‘프로덕션 시간 동기화 대체재’는 아니다. 그래도 브라우저 성능 타이밍 API와 CDN 엣지 인프라를 조합하면 어디까지 할 수 있는지 보여주는 좋은 장난감이자 기술 데모임.

댓글

댓글

댓글을 불러오는 중...

frontend

개인 웹사이트에 JSON-LD 넣는 법, 검색엔진과 크롤러가 내 사이트를 제대로 읽게 만들기

개인 웹사이트에 JSON-LD 구조화 데이터를 추가해 검색엔진과 크롤러가 사이트, 사람, 글, 프로젝트를 더 정확히 이해하게 만드는 실전 가이드야. WebSite, Person, ProfilePage, BlogPosting 같은 노드를 어떻게 연결하고 어느 페이지에 넣어야 하는지 예시 중심으로 설명해.

frontend

Deno, 웹 프로젝트를 데스크톱 앱으로 묶는 `deno desktop` 공개

Deno가 TypeScript 파일 하나부터 Next.js 앱까지 데스크톱 앱으로 패키징하는 `deno desktop`을 공개했다. 아직 안정 릴리스는 아니고 Deno v2.9.0 canary에서만 쓸 수 있지만, 운영체제 WebView 기반의 작은 바이너리, 프레임워크 자동 감지, 내장 자동 업데이트까지 한 번에 노린다.

frontend

파비콘 안에 웹사이트를 숨겨 넣은 개발자, 진짜 됨

한 개발자가 웹사이트의 파비콘 이미지를 작은 저장소처럼 사용해 HTML을 픽셀 RGB 값 안에 넣고, 브라우저에서 다시 읽어 렌더링하는 실험을 했다. 208바이트짜리 HTML payload에 4바이트 길이 헤더를 붙여 총 212바이트를 만들었고, 이를 9x9 픽셀 PNG 안에 87% 사용률로 저장했다.

frontend

스크린이 절대 못 보여주는 색은 어디에 있을까

이 글은 우리가 화면에서 보는 색이 인간이 볼 수 있는 색 전체가 아니라, sRGB와 Display-P3 같은 색역 안에 갇힌 일부라는 점을 파고든다. 특히 숲, 바닷속, 새와 나비의 구조색, 생물발광, 교통신호 LED 같은 실제 세계에는 모니터와 카메라가 제대로 담지 못하는 청록색과 녹색 계열이 꽤 많다는 얘기다. 디스플레이, 카메라, 조명, 렌더링을 다루는 개발자라면 “색상값 하나”가 생각보다 물리와 표준의 타협이라는 걸 체감하게 된다.

frontend

크롬, 매니페스트 버전 2 우회로까지 닫는다

구글 크롬이 매니페스트 버전 2 확장 지원을 사실상 최종 종료 단계로 밀어넣고 있다. 기존에는 플래그나 레지스트리 설정으로 유블록 오리진 같은 확장을 살리는 우회가 있었지만, 크로미움 150과 151을 거치며 그 우회 코드까지 제거되는 흐름이다.