P2P 연결이 막히는 이유 — NAT, ICE, STUN, TURN
NAT mapping과 filtering 동작 때문에 endpoint끼리 직접 연결되지 않는 경우를 설명합니다. ICE agent가 host·server-reflexive·relay candidate pair를 검사하고 STUN binding과 TURN relay를 사용하는 흐름을 현재 RFC 기준으로 정리합니다. 오래된 NAT 네 가지 분류는 진단의 참고 모델로만 다룹니다.
P2P(피어 간 직접 연결)는 공유기(NAT) 의 매핑·필터링 동작이나 방화벽 정책 때문에 실패할 수 있습니다. 이 글에서는 레거시 NAT 4분류와 현행 RFC의 동작 기반 분류, STUN·TURN·ICE의 관계를 정리합니다.
NAT란?
NAT(Network Address Translation)는 내부망(가정·회사)의 사설 IP:포트와 외부에 보이는 공인 IP:포트를 매핑해 주는 장치입니다. 외부에서는 “공인 IP:포트”로만 보이기 때문에, 상대방이 “내가 보이는 주소”를 모르면 P2P 연결을 시도하기 어렵습니다. STUN 서버에 요청을 보내면 “당신의 공인 주소는 1.2.3.4:5000입니다”처럼 알려 주고, 이 주소를 상대에게 전달해 서로 연결을 시도합니다. 다만 NAT 종류에 따라 “한 번 매핑된 포트로 누가 접속해도 되는지”, “목적지가 바뀌면 포트도 바뀌는지”가 달라져 P2P가 막히는 경우가 있습니다.
레거시 NAT 4분류
| NAT 타입 | 설명 |
|---|---|
| Full Cone | 한 번 매핑되면 어디서든 해당 포트로 접속 가능 |
| Restricted Cone | 클라이언트가 접속했던 IP에서만 해당 포트로 접속 가능 |
| Port Restricted Cone | 접속했던 IP:포트에서만 접속 가능 |
| Symmetric | 목적지(IP:포트)마다 다른 포트가 매핑됨 → P2P가 가장 까다로움 |
위 4분류는 RFC 3489의 레거시 모델입니다. 현행 문서에서는 매핑(Mapping) 과 필터링(Filtering) 을 분리해 설명합니다. RFC 4787의 UDP 매핑 동작은 Endpoint-Independent, Address-Dependent, Address-and-Port-Dependent로 구분합니다. "Symmetric NAT"를 하나의 현행 분류와 일대일로 대응시키기보다 매핑·필터링 조합을 확인하는 편이 정확합니다.
레거시 용어의 Symmetric NAT에서 흔히 설명하는 시나리오는 목적지에 따라 외부 매핑이 달라지는 경우입니다. 이때 STUN 서버를 대상으로 얻은 주소가 다른 피어와 통신할 때 그대로 유효하지 않을 수 있습니다. 다만 실제 연결 가능성은 양쪽 NAT의 매핑·필터링과 ICE 후보 조합에 따라 달라지며, 직접 후보 쌍이 모두 실패할 때 TURN relay를 사용합니다.
Symmetric NAT 예시: 목적지별 포트 매핑 (클릭 시 시각화)
1. STUN 서버에 패킷을 보낼 때
STUN 서버가 "당신의 공인 주소는 1.2.3.4:5000 입니다"라고 알려 줍니다.
2. Peer B에게 패킷을 보낼 때
목적지가 다르면 NAT가 다른 포트를 새로 만들어 버립니다.
3. 왜 B가 5000으로 접속하면 차단되나요?
- B는 STUN을 통해 “상대 주소는 1.2.3.4:5000”이라고만 알고 있습니다.
- 하지만 공유기 입장에서 5000번은 “STUN 서버와 통신할 때 쓴 전용 문”입니다.
- B가 5000번으로 접속해 오면, 공유기는 “이 문은 STUN 전용인데?”라고 보고 차단합니다.
- B가 들어올 수 있는 문은 5001번인데, B는 그 번호를 알 수 없습니다.
이 예시는 Address-and-Port-Dependent Mapping 때문에 STUN 서버에 대한 매핑과 Peer B에 대한 매핑이 달라지는 상황입니다. 이것만으로 모든 피어 조합의 홀펀칭이 불가능하다고 단정할 수는 없지만, ICE의 직접 후보 쌍 검사가 실패하면 TURN relay가 필요합니다.
TURN이란? (클릭 시 시각화)
TURN(Traversal Using Relays around NAT)은 현행 RFC 8656에 정의된 릴레이 프로토콜입니다. 직접 후보 쌍의 연결 검사가 실패하면 TURN 서버가 중간에서 미디어를 받아 상대 피어에게 전달합니다.
- Allocate: 클라이언트가 TURN 서버에 요청을 보내면, 서버가 릴레이 전용 주소(IP:포트) 를 발급합니다. 이 주소를 시그널링으로 상대에게 알려 주면, 상대는 그 주소로 패킷을 보냅니다.
- Permission: 아무나 릴레이 주소로 보낼 수 없도록, "이 Peer의 IP만 허용"하는 Permission을 등록합니다. TURN 서버는 허가된 IP에서 오는 패킷만 해당 클라이언트에게 전달합니다.
- 데이터 중계: 실제 오디오·영상 데이터는 내 PC ↔ TURN ↔ Peer 경로로 모두 서버를 경유합니다. 따라서 대역폭·비용이 들지만, "연결이 안 되는 경우"의 최후 수단으로 사용됩니다.
ICE는 host·srflx·relay 후보로 후보 쌍 체크리스트를 만들고 우선순위 순서로 연결 검사를 수행합니다. 세 후보 유형을 고정된 세 단계로 하나씩 시도하는 구조는 아닙니다.
ICE는 local×remote 후보 쌍으로 체크리스트를 만들고, RFC 8445의 우선순위와 pacing 규칙에 따라 STUN 연결 검사를 진행한 뒤 유효한 쌍을 nominate합니다. 기본 type preference는 일반적으로 직접 후보를 relay보다 선호하지만,
iceTransportPolicy: "relay"처럼 정책이 relay만 허용할 수도 있습니다.
방화벽
NAT 외에도 방화벽 정책이 후보 쌍의 연결 검사를 막을 수 있습니다. 회사·학교·공공 Wi‑Fi처럼 허용 포트·전송 프로토콜이 제한된 환경에서는 직접 후보가 실패할 수 있으며, 그 경우 허용된 전송을 사용하는 TURN relay가 대안이 됩니다.
한 줄 요약: NAT의 매핑·필터링과 방화벽 정책에 따라 직접 P2P 후보가 실패할 수 있으며, ICE가 유효한 직접 후보 쌍을 찾지 못하면 TURN relay를 사용합니다.
관련 글
- #0 WebRTC란? ICE/STUN/NAT/TURN 기초 — ICE/STUN/NAT/TURN 전체 그림을 먼저 잡고 이 글로 들어오면 이해가 빠릅니다
- #9 Agora 기업 방화벽 우회 — Cloud Proxy — STUN/TURN으로도 안 되는 엄격한 기업 방화벽을 우회하는 실전 해법
- #32 시그널링과 미디어 분리 — RTSP/SIP vs RTP — STUN으로 교환한 후보 주소를 어떤 시그널링 채널로 주고받는지 연결됩니다
- #47 WebRTC 벤더 지형도 — TURN 인프라를 직접 운영할지 매니지드를 쓸지 판단할 때 참고
참고 자료
- RFC 8489 — Session Traversal Utilities for NAT (STUN) — 현행 STUN 표준. RFC 3489/5389를 대체
- RFC 8656 — Traversal Using Relays around NAT (TURN) — 현행 TURN 표준. RFC 5766을 개정
- RFC 8445 — Interactive Connectivity Establishment (ICE) — host/srflx/relay 후보 수집과 우선순위·연결성 점검 절차
- RFC 4787 — NAT Behavioral Requirements for Unicast UDP — 매핑/필터링 동작 분리(EIM·EDM) 정의, Symmetric NAT를 대체하는 현행 분류
- W3C WebRTC 1.0 —
RTCPeerConnection, ICE transport policy와 브라우저 API 표준
실제 데모
/agora-demo/rtc