How to destroy unresolved promise

7.7k views Asked by At

Have a look into the code snippet

$scope.getSongs = function(keyword){
     songServices.getSongList(keyword).then(
         function(resp){
             $scope.songList = resp.data.songList;
         }
     );
}

Here getSongList simply returns list of songs from server by an HTTP request.

And in my HTML:

<input auto-focus type="text" placeholder="Enter song ID/Keyword" ng-model="keyword" ng-change="getSongs()">

The problem here is with behaviour of promises, sometimes if some promise takes more time(even in ms.) to get resolved then it shows false data. when you search for 'AKON' lets say promise with first strike 'A' returns last then it refreshes the scope with false data, Is there any way to stop or discard promise which have not been resolved before sending another promise to server, or how can I handle such kind of scenario.

Thanks in advance.

3

There are 3 answers

0
JB Nizet On BEST ANSWER

$http calls can be cancelled, by passing a promise in the 'timeout' config option, and resolving that promise.

From the documentation:

timeout – {number|Promise} – timeout in milliseconds, or promise that should abort the request when resolved.

Example:

var canceler = $q.defer();
$http.get(someUrl, { timeout: canceler.promise });

// later: cancel the http request

canceler.resolve();
2
Kent Cooper On

Rather than destroy the promise it might be better not to make a call until the user has stopped typing. you can use the ng-options directive to set a debounce timer. That way the action will only get executed once the user has stopped typing.

<input auto-focus type="text" placeholder="Enter song ID/Keyword" ng-model="keyword" ng-change="getSongs" ng-model-options="{ debounce: 500}">

2
Michael Lorton On

You could create a destroyable promise from an ordinary promise easily enough:

var destroyablePromise = function(p) {
  var r = $q.defer();

  p.then(function(a) { if (p) { r.resolve(a); }}, 
         function(a) { if (p) { r.reject(a); }},
         function(a) { if (p) { r.notify(a); }});

  r.promise.destroy = function() {
    p = null;
  };
  return r.promise;
}

Et voilà!