homelab89 Docs Logs Legacy Files ☰ TOC 🌓
guidehomelab 2026-06-29cloudflaretunneldnshomelab

Cloudflare 도메인 활성화 런북 — quick tunnel → 고정 도메인 + Named Tunnel (+ Access)

Date: 2026-06-29 호스트: ubuntu (home server) 도메인: Networking / 운영 용도: 위키 포털의 임시 *.trycloudflare.com URL(리붓마다 변경)을 고정 커스텀 도메인으로 승격.


0. 왜 필요한가 (동기)

현재 포털은 Cloudflare quick tunnel로 노출 중이다. quick tunnel은 kb-tunnel 컨테이너가 재시작될 때마다 URL이 바뀐다(예: 직전 리붓 후 https://space-recovery-personnel-experimental.trycloudflare.com). 외울 수도, 북마크할 수도, 사내에 고정 공유할 수도 없다. → 본인 소유 도메인 + Named Tunnel로 바꾸면 리붓해도 주소가 불변이고, 선택적으로 Cloudflare Access(SSO)로 private을 보호할 수 있다.

현실 체크: Named Tunnel은 도메인이 Cloudflare 존(zone)으로 등록돼 있어야 자동 CNAME을 만든다. DuckDNS 등 무료 서브도메인은 네임서버를 본인이 제어 못 하므로 불가. 즉 본인 소유 도메인(저렴해도)이 사실상 필수.

현재 상태 (런북 기준점)

  • Compose: ~/docs-publish/docker-compose.ymlkb-tunnel(cloudflared)이 command: tunnel --url http://localhost:8080 으로 quick tunnel 실행.
  • Caddyfile: ~/docs-publish/Caddyfile:8080 단일 프런트도어. /files*→127.0.0.1:8081(dufs 다운로드), /private*→basic_auth, /+/public*→포털.
  • 좌측 nav(viz.js)는 /public/_site.json·/private/_site.json절대경로(same-origin) 로 fetch → 호스트를 쪼개면 base-URL 문제(5단계 참고).
  • cloudflared 아웃바운드: TCP/UDP 7844(+443). 가정용 회선이면 보통 열림.

1. 도메인 구하기

옵션 내용 비고
(A) Cloudflare Registrar ★추천 원가 판매. .com$10.44/년(등록=갱신 동일), 일부 TLD $4~5/년. WHOIS 프라이버시 무료 단, 이미 Cloudflare에 활성화된 존에 대해서만 구매 메뉴가 열림 → 2단계(사이트 추가) 먼저. 네임서버가 자동 Cloudflare라 2단계가 자동 완료
(B) 외부 등록업체(Namecheap/Porkbun 등) 첫 해 프로모가 쌀 수 있으나 갱신가가 비쌈. 네임서버를 직접 Cloudflare로 위임 2단계에서 네임서버 수동 변경
(C) 무료(Freenom .tk 등) 2024년 폐쇄, 사용 불가. DuckDNS/No-IP는 살아있으나 Named Tunnel/Access 불가 비추천

추천: (A) Cloudflare Registrar. 도메인+DNS+터널+Access가 한 대시보드에서 끝나고 갱신가가 원가라 장기적으로 가장 단순/저렴. 짧은 이름이면 .com(~$10), 더 싸게는 .net/.org/.dev.

이 문서는 도메인을 example.com 으로 표기. 실제 본인 도메인으로 치환.


2. 도메인을 Cloudflare에 추가·활성화

  1. https://dash.cloudflare.com 로그인 (이메일 [email protected] 권장 — Access 정책 이메일과 일치시키면 편함).
  2. Add a domain(또는 우상단 + Add → Existing domain) → 도메인 입력 → Continue.
  3. 플랜 Free 선택 → Continue.
  4. DNS 스캔 결과 화면 → Continue to activation.
  5. Cloudflare가 네임서버 2개(예: mia.ns.cloudflare.com, todd.ns.cloudflare.com) 제시.
    • (A) Registrar 구매: 이미 Cloudflare NS라 자동 통과.
    • (B) 외부 등록업체: 등록업체 대시보드 → 네임서버 설정 → 기존 NS 삭제 후 위 2개 정확히 입력 → 저장. DNSSEC가 켜져 있으면 먼저 끄기(켜진 채 NS 변경 시 도메인 먹통).

확인:

dig +short NS example.com    # cloudflare.com 네임서버 2개가 떠야 함

활성화는 보통 수 분~수십 분(최대 24h). 완료 시 이메일 알림 + 대시보드 상태 Active(초록).


3. Named Tunnel 생성 (대시보드 토큰 방식 ★추천) + compose 배선

3-A. 대시보드에서 터널 생성

  1. 좌측 Zero Trust 진입(첫 진입 시 team name 1회 설정 + Free 플랜).
  2. Networks → Tunnels(계정에 따라 Networking → Tunnels) → Create a tunnel.
  3. 커넥터 CloudflaredNext.
  4. 터널 이름(예: homelab) → Save tunnel.
  5. 환경에서 Docker 선택. 표시되는 설치 명령 안의 토큰(eyJhIjoi.... 아주 긴 문자열)만 복사. (전체 docker run은 실행하지 말 것 — compose에 넣는다.)
  6. Next → Public Hostnames(또는 Routes) → Add a public hostname:
    • Subdomain: 비우면 루트, 또는 docs
    • Domain: example.com
    • Type: HTTP, URL: localhost:8080 ← 현재 Caddy 프런트도어
    • Save
    • 가장 단순한 구성은 호스트네임 1개(docs.example.com → localhost:8080). 분리는 5단계.

3-B. compose 배선 (quick → named 교체)

~/docs-publish/.env 에 추가:

CF_TUNNEL_TOKEN=eyJhIjoi....(복사한 토큰)

~/docs-publish/docker-compose.ymltunnel 서비스 command: 한 줄만 교체:

  tunnel:
    image: cloudflare/cloudflared:latest
    container_name: kb-tunnel
    network_mode: host
    restart: unless-stopped
    command: tunnel --no-autoupdate run --token ${CF_TUNNEL_TOKEN}   # quick tunnel 줄을 이걸로 교체
    depends_on: [docs, fileshare]

(이전 command: tunnel --url http://localhost:8080 은 롤백용으로 주석 남겨도 됨.) 적용:

docker compose -f ~/docs-publish/docker-compose.yml up -d tunnel
docker logs --tail 30 kb-tunnel   # 'Registered tunnel connection' 4개가량, 에러 없음

대시보드 Tunnels에서 상태 HEALTHY 확인.

3-C. (참고) CLI 방식 — 안 써도 됨

cloudflared tunnel login
cloudflared tunnel create homelab        # ~/.cloudflared/<UUID>.json
cloudflared tunnel route dns homelab docs.example.com

~/.cloudflared/config.yml:

tunnel: <UUID>
credentials-file: /home/jinsoo/.cloudflared/<UUID>.json
ingress:
  - hostname: docs.example.com
    service: http://localhost:8080
  - service: http_status:404

docker에선 ~/.cloudflared 볼륨 마운트 + command: tunnel run homelab. ingress를 서버 파일로 관리하고 싶을 때만. 초보자는 3-A 권장.


4. DNS 확인

3-A에서 Public Hostname 저장 시 Cloudflare가 CNAME 자동 생성(docs → <UUID>.cfargotunnel.com, Proxied).

dig +short docs.example.com   # Proxied라 cfargotunnel이 아니라 Cloudflare 애니캐스트 IP(104.x/172.67.x)가 정상

브라우저 https://docs.example.com → 포털 표시. HTTPS 인증서는 Cloudflare 엣지가 자동 발급(Caddy auto_https off 유지 — TLS 종단은 엣지).


5. Caddy: 단일 :8080 유지(★추천) vs 호스트 분리(선택)

추천(가장 단순): :8080 유지 + 호스트네임 1개

Caddyfile 수정 불필요. 터널을 localhost:8080으로 보냈고 Caddy가 기존대로 /files·/private·/ 라우팅. 단일 호스트라 viz.js의 절대경로 fetch 정상.

  • https://docs.example.com/ → 포털 + public
  • .../private/... → basic_auth
  • .../files/... → 다운로드 허브

선택 업그레이드: 호스트 분리(docs./kb./files.)

  1. 3-A에서 Public Hostname 복수 추가(docs→8080, files→8081 등). dufs(8081)는 현재 --path-prefix /files라 서브도메인 루트로 쓰려면 prefix도 조정.
  2. Caddyfile을 :8080 단일 → 호스트 기반 사이트 블록으로 재작성.

⚠️ viz.js base-URL 함정: 좌측 nav가 /public/_site.json·/private/_site.json을 절대경로로 fetch. public/private를 다른 호스트로 쪼개면 nav가 깨진다. → public+private+포털은 같은 호스트(docs.)에 두고, 다운로드(files.)만 분리가 안전. 완전 분리하려면 viz.js가 상대경로/호스트별 base-URL을 쓰도록 코드 수정 선행. 처음엔 단일 호스트로 가고 분리는 나중에.


6. (선택·권장) Cloudflare Access로 private 보호

/private의 basic_auth를 엣지 SSO로 대체. 오리진(터널 뒤)이 더 안전해지고 이메일/Google 로그인으로 진입.

  1. Zero Trust → Access controls → Applications → Create new application → Self-hosted.
  2. Add public hostname: Subdomain docs, Domain example.com, Path private (→ docs.example.com/private 하위 전체 + /private/_site.json 보호).
  3. Add a policy: name allow-me, Action Allow, Rule Selector Emails = [email protected] (회사 도메인 전체 허용 시 Emails ending in @회사도메인 OR 규칙 추가). 기본 deny by default.
  4. Login methods: 기본 One-time PIN(이메일 코드). Google 로그인은 Settings → Authentication에서 Google IdP 추가.
  5. 동작 검증 후 Caddyfile의 /private basic_auth 제거 가능(엣지가 이미 막음). 검증 전에는 제거 금지.

⚠️ 회사망/프록시 — 반드시 테스트

  • /files(dufs)는 의도적으로 GET-only·무인증 → 회사 프록시가 입력성 메서드를 막아도 다운로드(GET)는 통과(이 설계의 핵심).
  • 반면 Access 로그인은 IdP 리다이렉트 + OTP 코드 제출(POST) 포함. 회사 프록시가 POST/입력 제출을 막으면 Access 로그인 자체가 실패할 수 있음.
  • 권장 구성:
    • /files(사내 다운로드 허브)에는 Access를 걸지 말 것 — 공개 GET 유지(회사망 호환).
    • /private(주로 집 접근)에만 Access — 집에서 OTP/SSO 로그인.
    • 사내에서 /private가 필요하면, 회사망에서 Access 로그인(POST)이 실제로 되는지 먼저 테스트하고 안 되면 basic_auth 유지.

7. 검증 체크리스트 & 롤백

검증

docker logs --tail 20 kb-tunnel                       # connection registered, 에러 없음
dig +short docs.example.com                           # 104.x/172.67.x
curl -sI http://localhost:8080/ | head -n1            # 200 (오리진 직통)
curl -sI https://docs.example.com/ | head -n1         # 200 (공개)
curl -sI https://docs.example.com/files/ | head -n1   # 200 (다운로드)
# https://docs.example.com/private/...  → Access 적용 시 로그인 화면(브라우저)
  • 대시보드: Tunnels homelab = HEALTHY, 도메인 = Active.
  • 포털 좌측 nav 정상(단일 호스트면 문제없음).

롤백 (quick tunnel 즉시 복귀)

  1. ~/docs-publish/docker-compose.ymltunnel.command를 원복: command: tunnel --url http://localhost:8080
  2. docker compose -f ~/docs-publish/docker-compose.yml up -d tunneldocker logs --tail 30 kb-tunnel | grep trycloudflare 로 새 임시 URL 확인.
  • 도메인/DNS/터널은 남아있으니 문제 해결 후 3-B만 재적용하면 재전환.
  • Access만 문제면 Zero Trust → Access → Applications에서 앱 Disable/Delete(Caddyfile basic_auth 미삭제 전제)로 즉시 복귀.

빠른 의사결정 요약

  • 도메인: Cloudflare Registrar .com(~$10/년). 무료(DuckDNS)는 Named Tunnel 비호환.
  • 터널: 대시보드 토큰 방식 → compose command 한 줄 교체.
  • Caddy: 단일 :8080 + 호스트네임 1개(가장 단순, viz.js 무문제). 분리는 나중에.
  • Access: /private에만, /files는 공개 유지(회사망 다운로드 호환). 사내 Access 로그인 POST 가능 여부 별도 테스트.

검증 출처 (2026-06 확인)

  • Tunnel 원격 생성 + Docker 토큰 + Public Hostname: developers.cloudflare.com/cloudflare-one/networks/connectors/cloudflare-tunnel/get-started/create-remote-tunnel/ , /tunnel/setup/
  • 도메인 추가/NS 변경/활성화: developers.cloudflare.com/fundamentals/manage-domains/add-site/ , /dns/zone-setups/full-setup/setup/
  • Registrar 원가(.com ~$10.44): cloudflare.com/products/registrar/ , cfdomainpricing.com
  • Freenom 폐쇄(2024): netcraft.com/blog/cloudflare-loses-22-of-its-domains-in-freenom-tk-shutdown
  • Access self-hosted + 이메일 Allow: developers.cloudflare.com/cloudflare-one/access-controls/applications/http-apps/self-hosted-public-app/ , /policies/

UI 라벨은 계정별로 Networks/Networking → Tunnels, Public Hostnames/Routes 로 다를 수 있음(기능 동일).

Files