NAT 穿透详解:STUN / TURN / ICE

发布时间:2026/7/7 1:07:33
NAT 穿透详解:STUN / TURN / ICE NAT 穿透详解STUN / TURN / ICEWebRTC 要实现 P2P最大的障碍是 NAT。大部分设备都在路由器后面没有公网 IP怎么直连这篇讲 NAT 是什么、STUN 怎么发现公网地址、TURN 怎么中继、ICE 怎么整合两者选最优路径。大家好我是黒漂技术佬。做 WebRTCNAT 穿透是绕不开的话题。为什么有时候视频通话连不上为什么同一个 Wi-Fi 下可以换个网络就不行为什么需要 TURN 服务器这篇把 NAT、STUN、TURN、ICE 讲明白原理是什么、怎么工作、怎么配置、常见问题怎么排查。一、NAT 是什么全称Network Address Translation网络地址转换。为什么要有 NATIPv4 地址不够用大家共用一个公网 IP。路由器做地址转换内网设备 路由器(NAT) 公网 192.168.1.10 → 公网IP:端口 → 互联网 192.168.1.11 → 公网IP:端口 → 互联网内网设备只有私网 IP外面的设备直接访问不到。NAT 对 P2P 的影响两台都在 NAT 后面的设备互相不知道对方的公网地址和端口直接连不上。这就是 WebRTC 需要 STUN/TURN/ICE 的原因——解决 NAT 穿透问题。二、NAT 的四种类型不同类型的 NAT穿透难度不一样。1. 完全锥型 NATFull Cone一个内网端口映射到一个公网端口任何外部地址都能通过这个公网端口发数据进来。最容易穿透现在比较少见2. 受限锥型 NATRestricted Cone映射也是固定的但只有你主动联系过的外部地址才能发数据回来。中等难度比较常见3. 端口受限锥型 NATPort Restricted Cone比受限锥更严格不仅限制 IP还限制端口。只有你发过数据的那个 IP端口才能发回来。难度较大也比较常见4. 对称型 NATSymmetric每个不同的目标地址分配不同的公网端口。你给 A 发用一个端口给 B 发用另一个端口。最难穿透STUN 基本打不通需要 TURN 中继企业级 NAT、运营商级 NATCGN很多是对称型穿透难度完全锥 受限锥 端口受限锥 对称型前三种用 STUN 大概率能打通对称型基本打不通得上 TURN。三、STUN 服务器全称Session Traversal Utilities for NATNAT 会话穿透工具。作用帮你发现自己的公网 IP 和端口。工作原理内网设备 STUN服务器 │ │ │─── 发个包给STUN ─────────▶│ │ │ 看到你的源IP和端口 │◀── 返回你的公网地址 ──────│ │ │设备给 STUN 服务器发个包STUN 服务器从包里看到源 IP 和端口就是你的公网地址然后告诉设备。这样你就知道自己在公网上是什么地址了然后通过信令告诉对方。STUN 能解决什么发现公网 IP 和端口生成 srflx 类型的 ICE 候选大部分家用路由器能穿透锥型 NATSTUN 不能解决什么对称型 NAT 打不通双重 NAT路由器后面又接路由器可能打不通防火墙禁了 UDP 的话不行常用的公共 STUNstun:stun.l.google.com:19302 stun:stun1.l.google.com:19302 stun:stun.qq.com:3478测试用公共的就行生产环境建议自己搭或者用商用服务。STUN 配置constpcnewRTCPeerConnection({iceServers:[{urls:stun:stun.example.com:3478}]});四、TURN 服务器全称Traversal Using Relays around NAT用中继穿透 NAT。作用STUN 打不通的时候走 TURN 服务器中继——数据发给 TURNTURN 转发给对方。A ────▶ TURN服务器 ────▶ B什么时候需要 TURN对称型 NAT企业防火墙限制严格双重 NAT一方在 IPv4 一方在 IPv6大概 10-20% 的场景需要走 TURN具体看用户网络环境。TURN 和 STUN 的区别STUNTURN作用发现公网地址中继转发数据流量很少只有信令所有媒体流量都过服务器成本低高带宽成本大优先级高优先用低兜底用TURN 服务器实现coturn最主流的开源 TURN 服务器C 语言写的性能好restund另一个开源实现商用服务Twilio、Xirsys 等生产环境一般用 coturn 自己搭。TURN 配置constpcnewRTCPeerConnection({iceServers:[{urls:stun:stun.example.com:3478},{urls:turn:turn.example.com:3478,username:username,credential:password}]});TURN 需要用户名密码认证防止被滥用。TURN 的传输协议UDP默认延迟低TCPUDP 被封的时候用延迟高一点TLS-TCP加密的 TCP更难被封可以都配上自动选能用的。五、ICE整合 STUN 和 TURN全称Interactive Connectivity Establishment交互式连接建立。作用ICE 不是一个具体协议而是一个框架——整合 STUN 和 TURN自动找出两端之间最好的连通路径。ICE 怎么做1. 收集候选地址每个端收集所有可能的地址host 候选本机所有网卡的内网地址srflx 候选STUN 服务器反射的公网地址relay 候选TURN 中继地址2. 交换候选通过信令把自己的候选发给对方。3. 候选配对两边的候选两两配对形成候选对。4. 连通性检查按优先级从高到低每个候选对发探测包看能不能通。优先级host srflx relay5. 选定最佳路径找到第一个能连通的配对就用它传输数据。同时继续检查找到更好的就切换ICE 重启/提名。ICE 状态new初始checking正在检查配对connected找到可用连接了可能还在找更好的completed检查完了确定了最佳路径failed所有配对都不行连不上disconnected连接断了可能暂时的会重试closed关闭Trickle ICE逐滴 ICE传统 ICE收集完所有候选再发给对方慢。Trickle ICE收集到一个发一个边收集边发连接建立更快。WebRTC 默认就是 Trickle ICE所以 onicecandidate 事件会触发多次。六、ICE 候选详解候选格式candidate:foundation component transport priority ip port type ...例子candidate:1234567890 1 udp 2122260223 192.168.1.100 55555 typ host generation 0三种类型对比类型全称来源延迟成本优先级host主机候选本机网卡最低0最高srflx服务器反射候选STUN中低中relay中继候选TURN最高高最低ICE 优先用延迟最低、成本最低的路径实在不行才走 TURN。组件Component1 RTP媒体数据2 RTCP控制信息现在一般用 rtcp-muxRTP 和 RTCP 共用一个端口只有 component 1。七、实际部署建议1. STUN 和 TURN 都配上生产环境一定要同时配 STUN 和 TURNSTUN 负责大部分场景P2P省带宽TURN 负责兜底打不通的时候用2. TURN 服务器部署位置选多线 BGP 机房不同运营商访问都快部署在多个地域用户就近接入带宽要够TURN 是吃带宽的3. 安全配置TURN 一定要开认证不然被人盗用刷流量定期换密码限制速率防止攻击4. 监控监控 TURN 带宽使用统计 P2P 成功率和 TURN 比例TURN 比例太高的话检查是不是 STUN 有问题5. 自己搭还是用商用小流量自己搭 coturn成本低大流量/全球化考虑商用服务省运维八、coturn 快速搭建安装Ubuntuaptinstallcoturn配置编辑/etc/turnserver.conf# 监听端口 listening-port3478 # 中继端口范围 min-port49152 max-port65535 # 认证 lt-cred-mech userusername:password # 域名 realmturn.example.com # 外网 IP云服务器要填 external-ip你的公网IP # 日志 log-file/var/log/turnserver.log verbose启动systemctl start coturn systemctlenablecoturn防火墙开放 UDP 3478 端口以及中继端口范围49152-65535/udp。测试用在线 WebRTC 测试工具或者自己写代码测一下能不能拿到 relay 候选。九、连接失败排查步骤 1看 ICE 状态pc.oniceconnectionstatechange(){console.log(ICE state:,pc.iceConnectionState);};一直 checking候选没交换完或者都不通failed所有候选都失败了步骤 2看收集到哪些候选pc.onicecandidatee{if(e.candidate){console.log(候选:,e.candidate.type,e.candidate.address);}};只有 host 候选STUN 没配置或没通没有 relay 候选TURN 没配置或认证失败步骤 3检查 STUN/TURN 配置地址对不对端口对不对TURN 的用户名密码对不对防火墙有没有开放 UDP 端口步骤 4用测试工具验证网上搜「WebRTC test」「Trickle ICE test」有在线工具可以单独测 STUN 和 TURN。常见失败原因防火墙封了 UDP只能走 TCP TURN对称型 NAT 对称型 NAT基本打不通必须 TURNTURN 中继端口没开拿到了 relay 候选但数据传不过去云服务器没配 external-ipcoturn 拿不到公网 IP中继失败双重 NAT穿透难度大可能需要 TURN十、常见坑坑 1只配 STUN 不配 TURN测试的时候都在同一个 Wi-Fi 下没问题上线后一堆用户连不上。一定要配 TURN 兜底。坑 2TURN 带宽没预估走 TURN 的用户所有音视频流量都过服务器人多了带宽爆炸。提前预估监控带宽。坑 3TURN 没开认证公网 TURN 不设密码分分钟被扫到盗用账单爆炸。坑 4云服务器没开中继端口范围TURN 不止用 3478中继数据用的是随机端口要开放整个端口范围。坑 5coturn 没配 external-ip云服务器内网网卡上是内网 IPcoturn 不知道公网 IP中继会失败。一定要配置 external-ip。坑 6ICE 失败就放弃了ICE 进入 failed 状态可以尝试 ICE restart 重新协商说不定就通了。十一、本篇小结NAT地址转换内网设备共用公网 IPP2P 的主要障碍NAT 分四类完全锥、受限锥、端口受限锥、对称型穿透难度递增STUN发现公网地址解决锥型 NAT 的穿透成本低TURN中继转发兜底方案所有情况都能通但带宽成本高ICE整合 STUNTURN自动收集候选、配对检查、选最优路径候选优先级host内网直连 srflxSTUN公网 relayTURN中继生产环境 STUN 和 TURN 都要配P2P 优先TURN 兜底连接失败排查看 ICE 状态 → 看候选 → 检查配置 → 测服务器下一篇讲音视频编解码VP8/VP9/H.264/Opus 都是什么、怎么选、怎么配置。我是黒漂技术佬。