背景:
前言:如果还不清楚webrtc可以先看读这个文章webrtc的RTCPeerConnection使用_new rtcpeerconnection-CSDN博客
webRTC的RTCPeerConnection通讯,是p2p的通讯,配置的时候需要填写个stun和turn服务器
举例:
const configuration = {iceServers: [{ urls: "stun:stun.l.google.com:19302" },{urls: "turn:xxx.xxx.xxx.xxx:3478",username: "admin",credential: "123456",},],
};
stun服务器负责尝试做NAT穿透,让2个设备可以点对点通讯,但大部分网络环境这个穿透会失败。
stun服务器的工作内容很简单,只管下发2个设备的信令信息,基本不占用资源。
在穿透失败后,webtrc会尝试通过turn服务器进行中继通讯,turn服务器此时做的事情类似路由器,通讯数据会先流经turn服务器,再中转,所以turn服务器需要消耗较多资源,特别是带宽资源
turn服务器搭建:
这里采用docker的coturn/coturn镜像
镜像地址:https://hub.docker.com/r/coturn/coturn
git地址:https://github.com/coturn/coturn
拉取镜像命令:
docker pull coturn/coturn
宿主机创建配置文件:/home/test/turnserver.conf
参考:https://www.wware.org/wide/yw/backups/turnserverconfig.html
内容如下,把ip给成自己的实际的ip:
#中继服务器监听的IP地址,直接写公网IP地址,可以指定多个IP
listening-ip=60.70.80.91
#中继服务器转发地址(本地IP地址将用于传递数据包的给每个端),和监听地址一样
relay-ip=60.70.80.91
#外部IP,直接写公网IP地址
external-ip=60.70.80.91
#打开fingerprint的注释,使用长期证书机制。
fingerprint
#打开密码验证,使用短期证书机制。
lt-cred-mech
#服务器名称,用于OAuth认证,默认和realm相同,直接填公网ip.部分浏览器本段不设可能会引发cors错误。
server-name=60.70.80.91
# TURN REST API的长期凭证机制范围,同样设为ip,同server-name.
realm=60.70.80.91
#移动的ICE(MICE)的规范支持。
mobility
#快捷的添加用户是使用user=XXX:XXXX的方式,可以添加多个。/var/db/turndb也工作,可以使用turnadmin来管理其中用户,可以添加多个。
user=admin:123456
启动命令:
docker run -d -v /home/test/turnserver.conf:/etc/coturn/turnserver.conf --network=host --name my-turn-server coturn/coturn
测试:
打开 :https://webrtc.github.io/samples/src/content/peerconnection/trickle-ice/
输入相应turn服务器信息
点击测试,如果有输出上面的srflx和relay 就说明这2个服务器都部署成功,coturn启动后会同时拥有stun和turn服务
也可以自己写个简单的html测试,双击打开即可
<!doctype html>
<html lang="en"><head><meta charset="UTF-8" /><title>TURN Server Test</title></head><body><h1>Testing TURN Server</h1><pre id="output"></pre><script>function testTurnServer(turnConfig) {const output = document.getElementById("output");const configuration = { iceServers: [turnConfig] };// 创建一个新的 RTCPeerConnectionconst pc = new RTCPeerConnection(configuration);// 当收集到新的 ICE 候选者时触发pc.onicecandidate = (event) => {if (event.candidate) {output.innerHTML += `ICE Candidate: ${JSON.stringify(event.candidate)}\n`;if (event.candidate.type === "relay") {output.innerHTML +="Relay candidate found. TURN server is working.\n";cleanup();}} else {output.innerHTML += "ICE gathering complete.\n";cleanup();}};// 当 ICE 状态改变时触发pc.oniceconnectionstatechange = () => {output.innerHTML += `ICE Connection State: ${pc.iceConnectionState}\n`;if (pc.iceConnectionState === "failed") {output.innerHTML +="ICE connection failed. Check TURN server configuration.\n";cleanup();}};function cleanup() {pc.close();//setTimeout(() => window.location.reload(), 2000); // 重新加载页面以重置状态}// 强制触发 ICE 候选者的收集setTimeout(() => {pc.createDataChannel("test"); // 创建一个数据通道来触发候选者收集pc.createOffer().then((offer) => {return pc.setLocalDescription(offer);}).catch((error) => {console.error("Error creating offer:", error);output.innerHTML += `Error: ${error}\n`;cleanup();});}, 1000);}// 定义要测试的 TURN 服务器配置const turnServerToTest = {urls: "turn:xxx.xxx.xxx.xxx:3478",username: "admin",credential: "123456",};// 开始测试testTurnServer(turnServerToTest);</script></body>
</html>
正常的输出结果:
其他:
查看coturn容器的信息
进入容器:
docker exec -it my-turn-server /bin/bash
执行turnserver命令命令查看一些信息,例如版本信息
turnserver
例如我这边镜像的版本是 Coturn Version Coturn-4.6.3 'Gorst'