| <html> |
| <head> |
| <script type="text/javascript" src="webrtc_test_utilities.js"></script> |
| <script type="text/javascript" src="webrtc_test_common.js"></script> |
| <script type="text/javascript"> |
| $ = function(id) { |
| return document.getElementById(id); |
| }; |
| |
| window.onerror = function(errorMsg, url, lineNumber, column, errorObj) { |
| failTest('Error: ' + errorMsg + '\nScript: ' + url + |
| '\nLine: ' + lineNumber + '\nColumn: ' + column + |
| '\nStackTrace: ' + errorObj); |
| } |
| |
| var gPeerConnection = null; |
| var gCertificate = null; |
| |
| // This test creates and sets three offers, calling setConfiguration in |
| // between each offer, expecting an ICE restart to be triggered by the next |
| // offer. |
| function testSetConfiguration() { |
| gPeerConnection = new RTCPeerConnection( |
| {iceServers:[], iceTransportPolicy:'all', bundlePolicy:'balanced', |
| rtcpMuxPolicy:'require', certificates:[]}); |
| // Now test successful cases of setConfiguration. Changes should trigger an |
| // ICE restart in the next offer. To do this, first we need to trigger an |
| // initial ICE gathering phase and wait until it completes. |
| // TODO(deadbeef): Once onicegatheringstatechange is implemented, use that |
| // instead of a "null" candidate. |
| gPeerConnection.onicecandidate = iceCandidateCallback1; |
| createOfferAndSetLocalDescription(); |
| } |
| |
| function iceCandidateCallback1(candidate) { |
| if (gPeerConnection.iceGatheringState === 'complete') { |
| gPeerConnection.onicecandidate = iceCandidateCallback2; |
| // Policy changed. |
| gPeerConnection.setConfiguration( |
| {iceServers:[], iceTransportPolicy:'relay', bundlePolicy:'balanced', |
| rtcpMuxPolicy:'require', certificates:[]}); |
| createOfferAndSetLocalDescription(); |
| } |
| } |
| |
| function iceCandidateCallback2(candidate) { |
| if (gPeerConnection.iceGatheringState === 'complete') { |
| gPeerConnection.onicecandidate = iceCandidateCallback3; |
| // Servers changed. |
| gPeerConnection.setConfiguration( |
| {iceServers:[{urls:'stun:foo.invalid'}], iceTransportPolicy:'all', |
| bundlePolicy:'balanced', rtcpMuxPolicy:'require', certificates:[]}); |
| createOfferAndSetLocalDescription(); |
| } |
| } |
| |
| function iceCandidateCallback3(candidate) { |
| // Only wait for 'gathering', since it will take a while for the requests to |
| // 'foo.invalid' to time out. |
| if (gPeerConnection.iceGatheringState === 'gathering') { |
| reportTestSuccess(); |
| } |
| } |
| |
| function testSetConfigurationErrors() { |
| // Generate certificate so we can test the InvalidModificationError from |
| // attempting to change certificates. |
| RTCPeerConnection.generateCertificate({ name:'ECDSA', namedCurve:'P-256' }) |
| .then(function(certificate) { |
| gCertificate = certificate; |
| continueTestSetConfigurationErrors(); |
| }, |
| function() { |
| failTest('Failed to generate certificate.'); |
| } |
| ); |
| } |
| |
| // Continued after certificate generated. |
| function continueTestSetConfigurationErrors() { |
| gPeerConnection = new RTCPeerConnection( |
| {iceServers:[], iceTransportPolicy:'all', bundlePolicy:'balanced', |
| rtcpMuxPolicy:'require', certificates:[]}); |
| // If bundlePolicy, rtcpMuxPolicy or certificates are changed, an |
| // InvalidModificationError should be thrown. |
| assertThrows(gPeerConnection.setConfiguration, |
| {iceServers:[], iceTransportPolicy:'all', |
| bundlePolicy:'max-bundle', rtcpMuxPolicy:'require', |
| certificates:[]}); |
| assertThrows(gPeerConnection.setConfiguration, |
| {iceServers:[], iceTransportPolicy:'all', |
| bundlePolicy:'balanced', rtcpMuxPolicy:'negotiate', |
| certificates:[]}); |
| assertThrows(gPeerConnection.setConfiguration, |
| {iceServers:[], iceTransportPolicy:'all', |
| bundlePolicy:'balanced', rtcpMuxPolicy:'require', |
| certificates:[gCertificate]}); |
| // Failure to parse URL should result in SyntaxError. |
| assertThrows(gPeerConnection.setConfiguration, |
| {iceServers:[{url:'stunnnn:foo.invalid'}], |
| iceTransportPolicy:'all', bundlePolicy:'max-bundle', |
| rtcpMuxPolicy:'require', certificates:[]}); |
| // TURN server with missing username should result in InvalidAccessError. |
| assertThrows(gPeerConnection.setConfiguration, |
| {iceServers:[{url:'turn:foo.invalid'}], |
| iceTransportPolicy:'all', bundlePolicy:'max-bundle', |
| rtcpMuxPolicy:'require', certificates:[]}); |
| // Sanity check that a configuration can be successfully set, and thus |
| // there's not something unexpected causing the above exceptions. |
| gPeerConnection.setConfiguration( |
| {iceServers:[], iceTransportPolicy:'all', bundlePolicy:'balanced', |
| rtcpMuxPolicy:'require', certificates:[]}); |
| reportTestSuccess(); |
| } |
| |
| function assertThrows(func) { |
| try { |
| func.apply(arguments.slice(start=1)); |
| failTest('Expected exception to be thrown by: ' + code); |
| } catch (e) { |
| } |
| } |
| |
| // Helper function to create and apply offer. |
| function createOfferAndSetLocalDescription() { |
| gPeerConnection.createOffer({offerToReceiveAudio:1}) |
| .then(function(offer) { |
| console.log("Setting offer:\n" + offer.sdp); |
| gPeerConnection.setLocalDescription(offer).then( |
| function() {}, |
| function() { failTest('Failed to set local description.') } |
| ); |
| }, |
| function() { |
| failTest('Failed to generate offer.') |
| } |
| ); |
| } |
| |
| </script> |
| </head> |
| <body> |
| </body> |
| </html> |