Bug 801297: Fix PeerConnection.createAnswer API; r=jesup
authorAnant Narayanan <anant@kix.in>
Mon, 15 Oct 2012 11:35:21 -0700
changeset 110439 76c3e2baba712fd25b3fabc52c890b6c92364ad2
parent 110436 5f27ce421c8fcc8186823e362bce2318d6676355
child 110440 967fa8cc6213ac47ea11826e48be1e9d9d2d1ade
push id93
push usernmatsakis@mozilla.com
push dateWed, 31 Oct 2012 21:26:57 +0000
reviewersjesup
bugs801297
milestone19.0a1
Bug 801297: Fix PeerConnection.createAnswer API; r=jesup
dom/media/PeerConnection.js
dom/media/nsIDOMRTCPeerConnection.idl
--- a/dom/media/PeerConnection.js
+++ b/dom/media/PeerConnection.js
@@ -141,16 +141,17 @@ function PeerConnection() {
 
   // Public attributes.
   this.onaddstream = null;
   this.onremovestream = null;
   this.onicecandidate = null;
   this.onstatechange = null;
   this.ongatheringchange = null;
   this.onicechange = null;
+  this.remoteDescription = null;
 
   // Data channel.
   this.ondatachannel = null;
   this.onconnection = null;
   this.onclosedconnection = null;
 }
 PeerConnection.prototype = {
   classID: PC_CID,
@@ -243,60 +244,66 @@ PeerConnection.prototype = {
 
     this._queueOrRun({
       func: this._pc.createOffer,
       args: [constraints],
       wait: true
     });
   },
 
-  createAnswer: function(offer, onSuccess, onError, constraints, provisional) {
+  createAnswer: function(onSuccess, onError, constraints, provisional) {
     if (this._onCreateAnswerSuccess) {
       if (onError) {
-        onError.onCallback("createAnswer already called");
+        try {
+          onError.onCallback("createAnswer already called");
+        } catch(e) {}
       }
       return;
     }
 
+    if (!this.remoteDescription) {
+      if (onError) {
+        try {
+          onError.onCallback("setRemoteDescription not called");
+        } catch(e) {}
+      }
+    }
+
+    if (this.remoteDescription.type != "offer") {
+      if (onError) {
+        try {
+          onError.onCallback("No outstanding offer");
+        } catch(e) {}
+      }
+    }
+
     this._onCreateAnswerSuccess = onSuccess;
     this._onCreateAnswerFailure = onError;
 
-    if (offer.type != "offer") {
-      if (onError) {
-        onError.onCallback("Invalid type " + offer.type + " passed");
-      }
-      return;
-    }
-
-    if (!offer.sdp) {
-      if (onError) {
-        onError.onCallback("SDP not provided to createAnswer");
-      }
-      return;
-    }
-
     if (!constraints) {
       constraints = "";
     }
     if (!provisional) {
       provisional = false;
     }
 
     // TODO: Implement provisional answer & constraints.
     this._queueOrRun({
       func: this._pc.createAnswer,
-      args: ["", offer.sdp],
+      args: ["", this.remoteDescription.sdp],
       wait: true
     });
   },
 
   setLocalDescription: function(desc, onSuccess, onError) {
     if (this._onSetLocalDescriptionSuccess) {
       if (onError) {
-        onError.onCallback("setLocalDescription already called");
+        try {
+          onError.onCallback("setLocalDescription already called");
+        } catch(e) {}
       }
       return;
     }
 
     this._onSetLocalDescriptionSuccess = onSuccess;
     this._onSetLocalDescriptionFailure = onError;
 
     let type;
@@ -304,35 +311,39 @@ PeerConnection.prototype = {
       case "offer":
         type = Ci.IPeerConnection.kActionOffer;
         break;
       case "answer":
         type = Ci.IPeerConnection.kActionAnswer;
         break;
       default:
         if (onError) {
-          onError.onCallback(
-            "Invalid type " + desc.type + " provided to setLocalDescription"
-          );
+          try {
+            onError.onCallback(
+              "Invalid type " + desc.type + " provided to setLocalDescription"
+            );
+          } catch(e) {}
           return;
         }
         break;
     }
 
     this._queueOrRun({
       func: this._pc.setLocalDescription,
       args: [type, desc.sdp],
       wait: true
     });
   },
 
   setRemoteDescription: function(desc, onSuccess, onError) {
     if (this._onSetRemoteDescriptionSuccess) {
       if (onError) {
-        onError.onCallback("setRemoteDescription already called");
+        try {
+          onError.onCallback("setRemoteDescription already called");
+        } catch(e) {}
       }
       return;
     }
 
     this._onSetRemoteDescriptionSuccess = onSuccess;
     this._onSetRemoteDescriptionFailure = onError;
 
     let type;
@@ -340,24 +351,31 @@ PeerConnection.prototype = {
       case "offer":
         type = Ci.IPeerConnection.kActionOffer;
         break;
       case "answer":
         type = Ci.IPeerConnection.kActionAnswer;
         break;
       default:
         if (onError) {
-          onError.onCallback(
-            "Invalid type " + desc.type + " provided to setLocalDescription"
-          );
+          try {
+            onError.onCallback(
+              "Invalid type " + desc.type + " provided to setRemoteDescription"
+            );
+          } catch(e) {}
           return;
         }
         break;
     }
 
+    this.remoteDescription = {
+      type: desc.type, sdp: desc.sdp,
+      __exposedProps__: { type: "rw", sdp: "rw" }
+    };
+
     this._queueOrRun({
       func: this._pc.setRemoteDescription,
       args: [type, desc.sdp],
       wait: true
     });
   },
 
   updateIce: function(config, constraints, restart) {
--- a/dom/media/nsIDOMRTCPeerConnection.idl
+++ b/dom/media/nsIDOMRTCPeerConnection.idl
@@ -30,25 +30,24 @@ interface nsIDOMRTCSessionDescription : 
 interface nsIDOMRTCIceCandidate : nsISupports
 {
   attribute DOMString candidate;
   attribute DOMString sdpMid;
   attribute unsigned short sdpMLineIndex;
 };
 
 /* See http://dev.w3.org/2011/webrtc/editor/webrtc.html */
-[scriptable, uuid(807b9b54-25a1-421e-9133-27ae6efcfcfd)]
+[scriptable, uuid(f888648c-5e6b-4af9-91ad-a911e53d7a39)]
 interface nsIDOMRTCPeerConnection : nsISupports
 {
   void createOffer(in RTCPeerConnectionCallback successCallback,
     [optional] in RTCPeerConnectionCallback failureCallback,
     [optional] in jsval constraints);
 
-  void createAnswer(in nsIDOMRTCSessionDescription offer,
-    in RTCPeerConnectionCallback successCallback,
+  void createAnswer(in RTCPeerConnectionCallback successCallback,
     [optional] in RTCPeerConnectionCallback failureCallback,
     [optional] in jsval constraints,
     [optional] in bool createProvisionalAnswer);
 
   void setLocalDescription(in nsIDOMRTCSessionDescription desc,
     [optional] in RTCPeerConnectionCallback successCallback,
     [optional] in RTCPeerConnectionCallback failureCallback);