9

I want to return promises from my module/sdk to non-angular javascript. For example if I'm returning promise to a jquery, I should be probably sending jquery deferred object. How can I convert an Angular promise to a jquery promise/deferred obj.

Any suggestions are much appreciated.

Bergi
  • 630,263
  • 148
  • 957
  • 1,375
phani
  • 1,134
  • 1
  • 11
  • 24
  • Why? Have an example? – m.e.conroy Jul 07 '14 at 13:02
  • For example you can convert any third party promise to a $q/Q promise using $q.when(thirdPartyPromise). But should have that library to use my promise. I do not want to force my client to use Q or angular so that he can reuse my promise. If I could convert it to the compatible promise he wanted it would be less pain to use. – phani Jul 07 '14 at 13:11
  • You should consider using a minimalist promise library and not jQuery promises, jQuery promises are inherently problematic in error handling. – Benjamin Gruenbaum Jul 07 '14 at 13:21
  • @phani Promises are [designed to be interchangeable](https://promisesaplus.com/) between implementations, you're not forcing your client to anything. jQuery deferreds don't comform to the Promise spec, so you shouldn't use them outside of jQuery. – Kos Feb 26 '15 at 10:07

1 Answers1

21

Disclaimer: jQuery promises don't play nice with other libraries - at all. jQuery will not assimilate other third party promises on its own. Angular $q promises on the other hand - will, so whenever you have the choice, assimilate the jQuery promise into an Angular promise and not vice versa. (All this changes in jQuery 3.0, if you see this disclaimer and 3.0 has already been released - please leave a comment).

Converting a jQuery promise into an Angular promise:

var angularPromise = $q.when(jQueryPromise); // eg: $q.when($.get(...));

Converting a jQuery promise to a native or Bluebird promise:

var promise = Promise.resolve(jQueryPromise); // eg: Promise.resolve($.get(..));

Converting a Promises/A+ complaint promise like $q Angular promise or Bluebird promise or native promises into jQuery promises:

function convert(p){
    var d = $.Deferred();
    p.then(function(val){
       d.resolve(val);
    }, function(err){ 
       d.reject(err); 
    });
    return d.promise();
}

var jqPromise = convert($http.get(...)); // example usage

// you might be tempted to think you can easily do:
var jqPromise = $.when($http.get(...));
// however - this will will fail inconsistently due to differences between 
// jQuery and Angular promises

Also worth noting - Angular promises can consume jQuery promises:

$http.get(...).then(function(id){
    return $.get("http://..."+id); // will work, though pointless because $http.get
}).then(function(result){
     // contains result of $.get call here
});
Benjamin Gruenbaum
  • 270,886
  • 87
  • 504
  • 504