Reputation: 301
I have an application that is sending a http request that returns a promise everytime the user types. I have it debouncing every 500ms. Sometimes the api I am requesting takes a long time to respond. For example, I make a search request for a
that takes a long time to respond but then the user continues typing to complete the query of a+x
which resolves almost immediately but the results of a+x
get overridden by the previous request of just a
.
TL;DR: if new promise is called before current resolves, how to cancel current
Upvotes: 0
Views: 1245
Reputation: 1074088
The way I usually handle overlapping queries where I only want the results of the last one is to remember something that I can check in the callback.
You haven't quoted any code which makes it tricky to help, but here's an example:
"use strict";
// NOTE: Will only run if your browser supports promises.
// Scoping function to avoid globals
(function() {
// We keep track of the most recent promise
var lastSomethingRequest = null;
// Our function that does something async
function doSomething(value) {
console.log("doing request for " + value);
// Start the async, remember the promise
var p = new Promise(function(resolve) {
setTimeout(function() {
resolve("resolve for " + value);
}, Math.floor(Math.random() * 500));
});
// Remember that as the most recent one
lastSomethingRequest = p;
p.then(function(result) {
// Use the result only if it's the most recent
if (lastSomethingRequest === p) {
console.log("Use this result: " + result);
lastSomethingRequest = null; // Release the promise object
} else {
console.log("Disregard outdated result: " + result);
}
});
}
// Generate 5 requests in a row that will complete in varying
// amounts of time, where we only want the result of the last one
for (var n = 0; n < 5; ++n) {
doSomething(n);
}
})();
Upvotes: 1
Reputation: 3474
Create a variable that counts your requests:
var effectiveRequestNumber = 0;
function asyncRequest() {
var requestNumber = ++effectiveRequestNumber; // storing our request number
doSomething().then(function(response) {
// if the function was invoked after this request, then these two won't match
if (effectiveRequestNumber !== requestNumber) {
return;
}
applyResponse(response); // we are fine - applying the response
});
}
Upvotes: 2