102 lines
3.7 KiB
HTML
102 lines
3.7 KiB
HTML
<!doctype html>
|
|
<meta charset=utf-8>
|
|
<script src="/resources/testharness.js"></script>
|
|
<script src="/resources/testharnessreport.js"></script>
|
|
<script src="RTCPeerConnection-helper.js"></script>
|
|
<script>
|
|
'use strict';
|
|
|
|
async function hasStats(pc, type) {
|
|
const report = await pc.getStats();
|
|
for (const stats of report.values()) {
|
|
if (stats.type == type) {
|
|
return true;
|
|
}
|
|
}
|
|
return false;
|
|
}
|
|
|
|
async function getInboundRtpPollUntilItExists(pc, kTimeoutMs = 10000) {
|
|
const t0 = performance.now();
|
|
while (performance.now() - t0 < kTimeoutMs) {
|
|
const report = await pc.getStats();
|
|
for (const stats of report.values()) {
|
|
if (stats.type == 'inbound-rtp') {
|
|
return stats;
|
|
}
|
|
}
|
|
}
|
|
return null;
|
|
}
|
|
|
|
promise_test(async t => {
|
|
const pc = new RTCPeerConnection();
|
|
t.add_cleanup(() => pc.close());
|
|
|
|
pc.addTransceiver('video');
|
|
assert_false(await hasStats(pc, 'outbound-rtp'),
|
|
'outbound-rtp does not exist after addTransceiver');
|
|
await pc.setLocalDescription();
|
|
assert_false(await hasStats(pc, 'outbound-rtp'),
|
|
'outbound-rtp does not exist in have-local-offer');
|
|
}, `RTCOutboundRtpStreamStats does not exist as early as have-local-offer`);
|
|
|
|
// This test does not exchange ICE candidates, meaning no packets are sent.
|
|
// We should still see outbound-rtp stats because they are created by the O/A.
|
|
promise_test(async t => {
|
|
const pc1 = new RTCPeerConnection();
|
|
t.add_cleanup(() => pc1.close());
|
|
const pc2 = new RTCPeerConnection();
|
|
t.add_cleanup(() => pc1.close());
|
|
|
|
// Offer to send. See previous test for assertions that the outbound-rtp is
|
|
// not created this early, which this test does not care about.
|
|
pc1.addTransceiver('video');
|
|
await pc1.setLocalDescription();
|
|
|
|
// Answer to send.
|
|
await pc2.setRemoteDescription(pc1.localDescription);
|
|
const [transceiver] = pc2.getTransceivers();
|
|
transceiver.direction = 'sendrecv';
|
|
assert_false(await hasStats(pc2, 'outbound-rtp'),
|
|
'outbound-rtp does not exist in has-remote-offer');
|
|
await pc2.setLocalDescription();
|
|
assert_true(await hasStats(pc2, 'outbound-rtp'),
|
|
'outbound-rtp exists after answerer returns to stable');
|
|
|
|
// Complete offerer negotiation.
|
|
await pc1.setRemoteDescription(pc2.localDescription);
|
|
assert_true(await hasStats(pc1, 'outbound-rtp'),
|
|
'outbound-rtp exists after offerer returns to stable');
|
|
}, `RTCOutboundRtpStreamStats exists after returning to stable`);
|
|
|
|
promise_test(async t => {
|
|
const pc1 = new RTCPeerConnection();
|
|
t.add_cleanup(() => pc1.close());
|
|
const pc2 = new RTCPeerConnection();
|
|
t.add_cleanup(() => pc1.close());
|
|
pc1.onicecandidate = e => pc2.addIceCandidate(e.candidate);
|
|
pc2.onicecandidate = e => pc1.addIceCandidate(e.candidate);
|
|
|
|
// Negotaite to send, but don't send anything yet (track is null).
|
|
const {sender} = pc1.addTransceiver('video');
|
|
await pc1.setLocalDescription();
|
|
await pc2.setRemoteDescription(pc1.localDescription);
|
|
await pc2.setLocalDescription();
|
|
await pc1.setRemoteDescription(pc2.localDescription);
|
|
assert_false(await hasStats(pc2, 'inbound-rtp'),
|
|
'inbound-rtp does not exist before packets are received');
|
|
|
|
// Start sending. This results in inbound-rtp being created.
|
|
const stream = await getNoiseStream({video:true});
|
|
const [track] = stream.getTracks();
|
|
await sender.replaceTrack(track);
|
|
const inboundRtp = await getInboundRtpPollUntilItExists(pc2);
|
|
assert_not_equals(
|
|
inboundRtp, null,
|
|
'inbound-rtp should be created in response to the sender having a track');
|
|
assert_greater_than(
|
|
inboundRtp.packetsReceived, 0,
|
|
'inbound-rtp must only exist after packets have been received');
|
|
}, `RTCInboundRtpStreamStats are created by packet reception`);
|
|
</script>
|