RTCRtpParameters-transactionId.html (7817B)
1 <!doctype html> 2 <meta charset=utf-8> 3 <title>RTCRtpParameters transactionId</title> 4 <script src="/resources/testharness.js"></script> 5 <script src="/resources/testharnessreport.js"></script> 6 <script src="dictionary-helper.js"></script> 7 <script src="RTCRtpParameters-helper.js"></script> 8 <script> 9 'use strict'; 10 11 // Test is based on the following editor draft: 12 // https://w3c.github.io/webrtc-pc/archives/20170605/webrtc.html 13 14 /* 15 5.1. RTCPeerConnection Interface Extensions 16 partial interface RTCPeerConnection { 17 RTCRtpTransceiver addTransceiver((MediaStreamTrack or DOMString) trackOrKind, 18 optional RTCRtpTransceiverInit init); 19 ... 20 }; 21 22 dictionary RTCRtpTransceiverInit { 23 RTCRtpTransceiverDirection direction = "sendrecv"; 24 sequence<MediaStream> streams; 25 sequence<RTCRtpEncodingParameters> sendEncodings; 26 }; 27 28 addTransceiver 29 2. If the dictionary argument is present, and it has a sendEncodings member, 30 let sendEncodings be that list of RTCRtpEncodingParameters objects, or an 31 empty list otherwise. 32 7. Create an RTCRtpSender with track, streams and sendEncodings and let 33 sender be the result. 34 35 5.2. RTCRtpSender Interface 36 interface RTCRtpSender { 37 Promise<void> setParameters(optional RTCRtpParameters parameters); 38 RTCRtpParameters getParameters(); 39 }; 40 41 dictionary RTCRtpParameters { 42 DOMString transactionId; 43 sequence<RTCRtpEncodingParameters> encodings; 44 sequence<RTCRtpHeaderExtensionParameters> headerExtensions; 45 RTCRtcpParameters rtcp; 46 sequence<RTCRtpCodecParameters> codecs; 47 }; 48 49 getParameters 50 - transactionId is set to a new unique identifier, used to match this 51 getParameters call to a setParameters call that may occur later. 52 */ 53 54 /* 55 5.2. getParameters 56 - transactionId is set to a new unique identifier, used to match this 57 getParameters call to a setParameters call that may occur later. 58 */ 59 promise_test(async t => { 60 const pc = new RTCPeerConnection(); 61 t.add_cleanup(() => pc.close()); 62 const { sender } = pc.addTransceiver('audio'); 63 64 const param1 = sender.getParameters(); 65 const param2 = sender.getParameters(); 66 assert_equals(typeof param1.transactionId, "string"); 67 assert_greater_than(param1.transactionId.length, 0); 68 assert_equals(typeof param2.transactionId, "string"); 69 assert_greater_than(param2.transactionId.length, 0); 70 // Don't assert_equals() because the transcation ID is different on each run 71 // which makes the -expected.txt baseline different each failed run. 72 assert_true(param1.transactionId == param2.transactionId); 73 74 await undefined; 75 const param3 = sender.getParameters(); 76 assert_equals(typeof param3.transactionId, "string"); 77 assert_greater_than(param3.transactionId.length, 0); 78 assert_equals(param1.transactionId, param3.transactionId); 79 }, `sender.getParameters() should return the same transaction ID if called back-to-back without relinquishing the event loop, even if the microtask queue runs`); 80 81 test(t => { 82 const pc = new RTCPeerConnection(); 83 t.add_cleanup(() => pc.close()); 84 const { sender } = pc.addTransceiver('audio'); 85 86 const param1 = sender.getParameters(); 87 sender.setParameters(param1); 88 const param2 = sender.getParameters(); 89 assert_equals(typeof param1.transactionId, "string"); 90 assert_greater_than(param1.transactionId.length, 0); 91 assert_equals(typeof param2.transactionId, "string"); 92 assert_greater_than(param2.transactionId.length, 0); 93 94 // Don't assert_equals() because the transcation ID is different on each run 95 // which makes the -expected.txt baseline different each failed run. 96 assert_true(param1.transactionId == param2.transactionId); 97 }, `sender.getParameters() should return the same transaction ID if called back-to-back without relinquishing the event loop, even if there is an intervening call to setParameters`); 98 99 promise_test(async t => { 100 const pc = new RTCPeerConnection(); 101 t.add_cleanup(() => pc.close()); 102 const { sender } = pc.addTransceiver('audio'); 103 104 const param1 = sender.getParameters(); 105 await pc.createOffer(); 106 const param2 = sender.getParameters(); 107 assert_equals(typeof param1.transactionId, "string"); 108 assert_greater_than(param1.transactionId.length, 0); 109 assert_equals(typeof param2.transactionId, "string"); 110 assert_greater_than(param2.transactionId.length, 0); 111 112 assert_not_equals(param1.transactionId, param2.transactionId); 113 }, `sender.getParameters() should return a different transaction ID if the event loop is relinquished between multiple calls`); 114 115 /* 116 5.2. setParameters 117 7. If parameters.encodings.length is different from N, or if any parameter 118 in the parameters argument, marked as a Read-only parameter, has a value 119 that is different from the corresponding parameter value returned from 120 sender.getParameters(), abort these steps and return a promise rejected 121 with a newly created InvalidModificationError. Note that this also applies 122 to transactionId. 123 */ 124 promise_test(async t => { 125 const pc = new RTCPeerConnection(); 126 t.add_cleanup(() => pc.close()); 127 const { sender } = pc.addTransceiver('audio'); 128 129 const param = sender.getParameters(); 130 131 const { transactionId } = param; 132 param.transactionId = `${transactionId}-modified`; 133 134 await promise_rejects_dom(t, 'InvalidModificationError', 135 sender.setParameters(param)); 136 }, `sender.setParameters() with transaction ID different from last getParameters() should reject with InvalidModificationError`); 137 138 promise_test(async t => { 139 const pc = new RTCPeerConnection(); 140 t.add_cleanup(() => pc.close()); 141 const { sender } = pc.addTransceiver('audio'); 142 143 const param = sender.getParameters(); 144 145 delete param.transactionId; 146 147 await promise_rejects_js(t, TypeError, 148 sender.setParameters(param)); 149 }, `sender.setParameters() with transaction ID unset should reject with TypeError`); 150 151 promise_test(async t => { 152 const pc = new RTCPeerConnection(); 153 t.add_cleanup(() => pc.close()); 154 const { sender } = pc.addTransceiver('audio'); 155 156 const param = sender.getParameters(); 157 158 await sender.setParameters(param); 159 await promise_rejects_dom(t, 'InvalidStateError', sender.setParameters(param)) 160 }, `setParameters() twice with the same parameters should reject with InvalidStateError`); 161 162 promise_test(async t => { 163 const pc = new RTCPeerConnection(); 164 t.add_cleanup(() => pc.close()); 165 const { sender } = pc.addTransceiver('audio'); 166 167 const param1 = sender.getParameters(); 168 // Queue a task, does not really matter what kind 169 await pc.createOffer(); 170 const param2 = sender.getParameters(); 171 172 assert_not_equals(param1.transactionId, param2.transactionId); 173 174 await promise_rejects_dom(t, 'InvalidModificationError', 175 sender.setParameters(param1)); 176 }, `setParameters() with parameters older than last getParameters() should reject with InvalidModificationError`); 177 178 promise_test(async t => { 179 const pc = new RTCPeerConnection(); 180 t.add_cleanup(() => pc.close()); 181 const { sender } = pc.addTransceiver('audio'); 182 183 const param1 = sender.getParameters(); 184 await pc.createOffer(); 185 186 await promise_rejects_dom(t, 'InvalidStateError', 187 sender.setParameters(param1)); 188 }, `setParameters() when the event loop has been relinquished since the last getParameters() should reject with InvalidStateError`); 189 190 </script>