我目前正在将 Jitsi 作为 SFU 进行测试。我正在尝试使用 COLIBRI REST API 创建一个简单的测试。当前测试是一个 JavaScript 客户端,在两个选项卡中打开,每个选项卡通过 REST API 连接到 Jitsi Videobridge (JVB),并通过 JVB 显示通过另一个客户端发送的视频。
首先,好消息。我已成功配置我们的客户端以通过 REST API 连接到 JVB 并显示其他对等方的视频源。但是, chrome://webrtc-internals 只显示两个 ssrc_send 条目,没有 ssrc_recv 条目。我很好奇为什么我们在 webrtc-internals 中看到视频而没有看到任何 ssrc_recv 条目。
我们发现,通过将以下 ssrc 行添加到我们的 SDP 报价中,我们可以获得 webrtc-internals 来显示 src_recv 条目。但是,统计数据显示没有媒体流过这些 ssrc_recvs ,并且我们丢失了没有 ssrc 行的视频流。
a=ssrc:${info.contents[0].channels[0].sources[0]} cname:mixed
a=ssrc:${info.contents[0].channels[0].sources[0]} label:mixedlabelaudio0${sessionId}
a=ssrc:${info.contents[0].channels[0].sources[0]} msid:mixedmslabel${sessionId} mixedlabelaudio0${sessionId}
a=ssrc:${info.contents[0].channels[0].sources[0]} mslabel:mixedmslabel${sessionId}
a=ssrc:${info.contents[1].channels[0].sources[0]} cname:mixed
a=ssrc:${info.contents[1].channels[0].sources[0]} label:mixedlabelvideo0${sessionId}
a=ssrc:${info.contents[1].channels[0].sources[0]} msid:mixedmslabel mixedlabelvideo0${sessionId}
a=ssrc:${info.contents[1].channels[0].sources[0]} mslabel:mixedmslabel${sessionId}
我们的主要问题是为什么我们没有看到任何 ssrc_recv 条目——即使我们可以看到视频流正在流动——以及我们如何修改/修复我们的代码以在 webrtc-internals 中显示这些 ssrc_recv 条目。我们担心看不到这些条目表明我们在实施过程中遗漏了一些更大的东西。但是,我们是否可能只是遇到了 Chrome 错误?
非常感谢您对此问题的任何帮助。
我在下面包含了相关的代码片段:
初始会议创建电话
POST {} 到 /colibri/conferences
频道分配调用
下面的补丁到 /colibri/conferences/9ad7d1fe11a85c1a
{
"id": "9ad7d1fe11a85c1a",
"contents": [
{
"name": "audio",
"channels": [
{
"expire": 60,
"initiator": true,
"endpoint": 1490294249498,
"direction": "sendrecv",
"channel-bundle-id": 1490294249498,
"rtp-level-relay-type": "mixer"
}
]
},
{
"name": "video",
"channels": [
{
"expire": 60,
"initiator": true,
"endpoint": 1490294249498,
"direction": "sendrecv",
"channel-bundle-id": 1490294249498,
"last-n": 2
}
]
}
],
"channel-bundles": [
{
"id": 1490294249498,
"transport": {
"xmlns": "urn:xmpp:jingle:transports:ice-udp:1",
"rtcp-mux": true,
"fingerprint": {
"xmlns": "urn:xmpp:jingle:apps:dtls:0",
"required": false
}
}
}
]
}
SDP 优惠
v=0
o=- 1490294249719 2 IN IP4 0.0.0.0
s=-
t=0 0
a=group:BUNDLE audio video
m=audio 1 RTP/SAVPF 111 103 104 126
c=IN IP4 0.0.0.0
a=rtpmap:111 opus/48000/2
a=rtpmap:103 ISAC/16000
a=rtpmap:104 ISAC/32000
a=rtpmap:126 telephone-event/8000
a=fmtp:111 minptime=10; useinbandfec=1
a=rtcp:1 IN IP4 0.0.0.0
a=extmap:1 urn:ietf:params:rtp-hdrext:ssrc-audio-level
a=extmap:3 http://www.webrtc.org/experiments/rtp-hdrext/abs-send-time
a=setup:actpass
a=mid:audio
a=sendrecv
a=ice-ufrag:ere4l1bbu7bbf8
a=ice-pwd:79r5i3snbhbrca0735vs3v30q4
a=fingerprint:sha-1 C2:FF:06:CD:0D:6C:EF:6E:CC:54:CE:2D:F1:68:34:DB:06:B8:79:6A
a=candidate:9ad7d1fe11a85c1a70d346f625a464501524626b 1 tcp 2130706431 172.31.54.51 4443 typ host generation 0
a=candidate:9ad7d1fe11a85c1a70d346f625a4645015247820 1 udp 2130706431 172.31.54.51 10000 typ host generation 0
a=candidate:9ad7d1fe11a85c1a70d346f625a46450ffffffff9d5ff4a9 1 tcp 1694498815 52.90.200.113 4443 typ srflx raddr 172.31.54.51 rport 4443 generation 0
a=candidate:9ad7d1fe11a85c1a70d346f625a46450ffffffff9d600a5e 1 udp 1677724415 52.90.200.113 10000 typ srflx raddr 172.31.54.51 rport 10000 generation 0
a=rtcp-mux
m=video 1 RTP/SAVPF 100
c=IN IP4 0.0.0.0
a=rtpmap:100 VP8/90000
a=fmtp:100 x-google-start-bitrate=800
a=rtcp:1 IN IP4 0.0.0.0
a=rtcp-fb:100 ccm fir
a=rtcp-fb:100 nack
a=rtcp-fb:100 nack pli
a=rtcp-fb:100 goog-remb
a=extmap:3 http://www.webrtc.org/experiments/rtp-hdrext/abs-send-time
a=setup:actpass
a=mid:video
a=sendrecv
a=ice-ufrag:ere4l1bbu7bbf8
a=ice-pwd:79r5i3snbhbrca0735vs3v30q4
a=fingerprint:sha-1 C2:FF:06:CD:0D:6C:EF:6E:CC:54:CE:2D:F1:68:34:DB:06:B8:79:6A
a=candidate:9ad7d1fe11a85c1a70d346f625a464501524626b 1 tcp 2130706431 172.31.54.51 4443 typ host generation 0
a=candidate:9ad7d1fe11a85c1a70d346f625a4645015247820 1 udp 2130706431 172.31.54.51 10000 typ host generation 0
a=candidate:9ad7d1fe11a85c1a70d346f625a46450ffffffff9d5ff4a9 1 tcp 1694498815 52.90.200.113 4443 typ srflx raddr 172.31.54.51 rport 4443 generation 0
a=candidate:9ad7d1fe11a85c1a70d346f625a46450ffffffff9d600a5e 1 udp 1677724415 52.90.200.113 10000 typ srflx raddr 172.31.54.51 rport 10000 generation 0
a=rtcp-mux
JSON/COLIBRI 答案
下面的补丁到 /colibri/conferences/9ad7d1fe11a85c1a
{
"id": "9ad7d1fe11a85c1a",
"contents": [
{
"name": "audio",
"channels": [
{
"id": "b2c29ad1f4555d04",
"expire": 30,
"initiator": true,
"endpoint": "1490294249498",
"direction": "sendrecv",
"channel-bundle-id": "1490294249498",
"sources": [
1274366703
],
"ssrc-groups": [
{
"semantics": "SIM",
"sources": [
1274366703
]
}
],
"rtp-level-relay-type": "translator",
"payload-types": [
{
"id": 111,
"name": "opus",
"clockrate": 48000,
"channels": 2,
"parameters": {
"fmtp": [
"minptime=10;useinbandfec=1"
]
}
},
{
"id": 103,
"name": "ISAC",
"clockrate": 16000,
"channels": 1
},
{
"id": 104,
"name": "ISAC",
"clockrate": 32000,
"channels": 1
},
{
"id": 126,
"name": "telephone-event",
"clockrate": 8000,
"channels": 1
}
],
"rtp-hdrexts": [
{
"id": 1,
"uri": "urn:ietf:params:rtp-hdrext:ssrc-audio-level"
},
{
"id": 3,
"uri": "http://www.webrtc.org/experiments/rtp-hdrext/abs-send-time"
}
],
"transport": {
"xmlns": "urn:xmpp:jingle:transports:ice-udp:1",
"rtcp-mux": true,
"pwd": "2u1eHOiv1Sc3dF4bEeVM0CP4",
"ufrag": "NJe9",
"fingerprints": [
{
"fingerprint": "71:05:78:40:20:F0:F7:AD:DA:89:D6:F6:22:17:AC:FC:97:2B:1C:25:9A:D1:B6:E7:80:91:C7:72:A6:DE:2C:D3",
"hash": "sha-256",
"setup": "active"
}
],
"candidates": [
{
"foundation": 3031090232,
"component": 1,
"transport": "udp",
"priority": 2122260223,
"ip": "192.168.1.20",
"port": 53868,
"type": "host",
"generation": 0,
"network-id": 1,
"network-cost": 10,
"id": 3031090232,
"network": 1,
"protocol": "udp"
},
{
"foundation": 1119534572,
"component": 1,
"transport": "udp",
"priority": 1686052607,
"ip": "71.229.240.22",
"port": 53868,
"type": "srflx",
"raddr": "192.168.1.20",
"rport": 53868,
"generation": 0,
"network-id": 1,
"network-cost": 10,
"id": 1119534572,
"network": 1,
"protocol": "udp"
},
{
"foundation": 4197005512,
"component": 1,
"transport": "tcp",
"priority": 1518280447,
"ip": "192.168.1.20",
"port": 9,
"type": "host",
"tcptype": "active",
"generation": 0,
"network-id": 1,
"network-cost": 10,
"id": 4197005512,
"network": 1,
"protocol": "tcp"
}
]
}
}
],
"sctpconnections": []
},
{
"name": "video",
"channels": [
{
"id": "d4782a7f74565a42",
"expire": 30,
"initiator": true,
"endpoint": "1490294249498",
"direction": "sendrecv",
"channel-bundle-id": "1490294249498",
"sources": [
1305961943
],
"rtp-level-relay-type": "translator",
"ssrc-groups": [
{
"semantics": "SIM",
"sources": [
1305961943
]
}
],
"last-n": 2,
"payload-types": [
{
"id": 100,
"name": "VP8",
"clockrate": 90000,
"channels": 2,
"parameters": {
"rtcp-fb": [
"ccm fir",
"nack",
"nack pli",
"goog-remb"
]
}
}
],
"rtp-hdrexts": [
{
"id": 3,
"uri": "http://www.webrtc.org/experiments/rtp-hdrext/abs-send-time"
}
],
"transport": {
"xmlns": "urn:xmpp:jingle:transports:ice-udp:1",
"rtcp-mux": true,
"pwd": "2u1eHOiv1Sc3dF4bEeVM0CP4",
"ufrag": "NJe9",
"fingerprints": [
{
"fingerprint": "71:05:78:40:20:F0:F7:AD:DA:89:D6:F6:22:17:AC:FC:97:2B:1C:25:9A:D1:B6:E7:80:91:C7:72:A6:DE:2C:D3",
"hash": "sha-256",
"setup": "active"
}
],
"candidates": [
{
"foundation": 3031090232,
"component": 1,
"transport": "udp",
"priority": 2122260223,
"ip": "192.168.1.20",
"port": 53868,
"type": "host",
"generation": 0,
"network-id": 1,
"network-cost": 10,
"id": 3031090232,
"network": 1,
"protocol": "udp"
},
{
"foundation": 1119534572,
"component": 1,
"transport": "udp",
"priority": 1686052607,
"ip": "71.229.240.22",
"port": 53868,
"type": "srflx",
"raddr": "192.168.1.20",
"rport": 53868,
"generation": 0,
"network-id": 1,
"network-cost": 10,
"id": 1119534572,
"network": 1,
"protocol": "udp"
},
{
"foundation": 4197005512,
"component": 1,
"transport": "tcp",
"priority": 1518280447,
"ip": "192.168.1.20",
"port": 9,
"type": "host",
"tcptype": "active",
"generation": 0,
"network-id": 1,
"network-cost": 10,
"id": 4197005512,
"network": 1,
"protocol": "tcp"
}
]
}
}
],
"sctpconnections": []
}
],
"channel-bundles": [
{
"id": "1490294224066",
"transport": {
"candidates": [
{
"generation": 0,
"component": 1,
"protocol": "tcp",
"port": 4443,
"ip": "172.31.54.51",
"tcptype": "passive",
"foundation": "1",
"id": "9ad7d1fe11a85c1a5ec5e04d36669ed805534db8",
"priority": 2130706431,
"type": "host",
"network": 0
},
{
"generation": 0,
"component": 1,
"protocol": "udp",
"port": 10000,
"ip": "172.31.54.51",
"foundation": "3",
"id": "9ad7d1fe11a85c1a5ec5e04d36669ed80553636d",
"priority": 2130706431,
"type": "host",
"network": 0
},
{
"generation": 0,
"rel-port": 4443,
"ip": "52.90.200.113",
"foundation": "2",
"rel-addr": "172.31.54.51",
"priority": 1694498815,
"type": "srflx",
"network": 0,
"component": 1,
"protocol": "tcp",
"port": 4443,
"tcptype": "passive",
"id": "9ad7d1fe11a85c1a5ec5e04d36669ed80ffffffff8d8edff6"
},
{
"generation": 0,
"rel-port": 10000,
"component": 1,
"protocol": "udp",
"port": 10000,
"ip": "52.90.200.113",
"foundation": "4",
"id": "9ad7d1fe11a85c1a5ec5e04d36669ed80ffffffff8d8ef5ab",
"rel-addr": "172.31.54.51",
"priority": 1677724415,
"type": "srflx",
"network": 0
}
],
"xmlns": "urn:xmpp:jingle:transports:ice-udp:1",
"ufrag": "8hvaa1bbu7airb",
"rtcp-mux": true,
"pwd": "187sh2bf3dl0lfola6goifb988",
"fingerprints": [
{
"fingerprint": "C2:FF:06:CD:0D:6C:EF:6E:CC:54:CE:2D:F1:68:34:DB:06:B8:79:6A",
"setup": "actpass",
"hash": "sha-1"
}
]
}
},
{
"id": "1490294249498",
"transport": {
"candidates": [
{
"generation": 0,
"component": 1,
"protocol": "tcp",
"port": 4443,
"ip": "172.31.54.51",
"tcptype": "passive",
"foundation": "1",
"id": "9ad7d1fe11a85c1a70d346f625a464501524626b",
"priority": 2130706431,
"type": "host",
"network": 0
},
{
"generation": 0,
"component": 1,
"protocol": "udp",
"port": 10000,
"ip": "172.31.54.51",
"foundation": "3",
"id": "9ad7d1fe11a85c1a70d346f625a4645015247820",
"priority": 2130706431,
"type": "host",
"network": 0
},
{
"generation": 0,
"rel-port": 4443,
"ip": "52.90.200.113",
"foundation": "2",
"rel-addr": "172.31.54.51",
"priority": 1694498815,
"type": "srflx",
"network": 0,
"component": 1,
"protocol": "tcp",
"port": 4443,
"tcptype": "passive",
"id": "9ad7d1fe11a85c1a70d346f625a46450ffffffff9d5ff4a9"
},
{
"generation": 0,
"rel-port": 10000,
"component": 1,
"protocol": "udp",
"port": 10000,
"ip": "52.90.200.113",
"foundation": "4",
"id": "9ad7d1fe11a85c1a70d346f625a46450ffffffff9d600a5e",
"rel-addr": "172.31.54.51",
"priority": 1677724415,
"type": "srflx",
"network": 0
}
],
"xmlns": "urn:xmpp:jingle:transports:ice-udp:1",
"ufrag": "ere4l1bbu7bbf8",
"rtcp-mux": true,
"pwd": "79r5i3snbhbrca0735vs3v30q4",
"fingerprints": [
{
"fingerprint": "C2:FF:06:CD:0D:6C:EF:6E:CC:54:CE:2D:F1:68:34:DB:06:B8:79:6A",
"setup": "actpass",
"hash": "sha-1"
}
]
}
}
],
"channel-bundlesFOO": [
{
"id": 1490294249498,
"transport": {
"xmlns": "urn:xmpp:jingle:transports:ice-udp:1",
"rtcp-mux": true,
"pwd": "2u1eHOiv1Sc3dF4bEeVM0CP4",
"ufrag": "NJe9",
"fingerprints": [
{
"fingerprint": "71:05:78:40:20:F0:F7:AD:DA:89:D6:F6:22:17:AC:FC:97:2B:1C:25:9A:D1:B6:E7:80:91:C7:72:A6:DE:2C:D3",
"hash": "sha-256",
"setup": "actpass"
}
],
"candidates": [
{
"foundation": 3031090232,
"component": 1,
"transport": "udp",
"priority": 2122260223,
"ip": "192.168.1.20",
"port": 53868,
"type": "host",
"generation": 0,
"network-id": 1,
"network-cost": 10,
"id": 3031090232,
"network": 1,
"protocol": "udp"
},
{
"foundation": 1119534572,
"component": 1,
"transport": "udp",
"priority": 1686052607,
"ip": "71.229.240.22",
"port": 53868,
"type": "srflx",
"raddr": "192.168.1.20",
"rport": 53868,
"generation": 0,
"network-id": 1,
"network-cost": 10,
"id": 1119534572,
"network": 1,
"protocol": "udp"
},
{
"foundation": 4197005512,
"component": 1,
"transport": "tcp",
"priority": 1518280447,
"ip": "192.168.1.20",
"port": 9,
"type": "host",
"tcptype": "active",
"generation": 0,
"network-id": 1,
"network-cost": 10,
"id": 4197005512,
"network": 1,
"protocol": "tcp"
}
]
}
}
]
}
Chrome WebRTC 内部结构
测试浏览器选项卡