Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to use jQuery when function with more postJSON queries?

I have a problem at work: I have a section of installations which are dependent on servers. I want to do this: When a user deletes a server, it loops through installations collection and deletes all dependent installations. For that I use jQuery 'when' function, which is said to wait for a response from the server and then move on to 'then' function. It works flawlessly when there is only one dependent installation. A problem occurs when there are more installations, however, because it moves to the 'then' function immediately after receiving a JSON response.

The question is: How do I make 'when' function wait for all server responses? Eg. I send out three delete requests through $.postJSON and want to move on after I get all three responses. If it's not possible with 'when', what should I use to make it happen? If it helps, I maintain all my entities collections with KnockoutJS. Thanks!

EDIT: I have it like this:

$.when(DeleteDependentInstallations())
.then (function() {
   ...
});

DeleteDependentInstallations looks like (pseudocode):

Search the installations collection;
If installation.ID equals server.InstallationID
{
  Add to dependent installations collection;
}
Repeat until the whole collection is searched;

for (i = 0; i < dependentInstallations.length; i++)
{
  DeleteInstallation(dependentInstallations[i]);
}

DeleteInstallations is a simple function using $.postJSON function.

The problem is the .then function executes immediately after the first JSON response.

like image 713
Filip Vondrášek Avatar asked Feb 12 '26 08:02

Filip Vondrášek


1 Answers

I think you need to have DeleteDependentInstallations return an array of JQuery deferreds. $.when allows you to pass multiple arguments to it in order to let it know it has to wait for each one.

I don't know the whole context of what you're doing, but I think something like this might work:

function DeleteDependentInstallations() {
     var installations = getDependantInstallations();
     var promises = [];
     for (var i = 0; i < installations.length; i++) {
         var installation = installations[i];
         promises.push(DeleteInstallation(installation));
     }
     return promises;
}

function DeleteInstallation(installation) {
      //do whatever here, but return the result of $.ajaxPost
      return $.post('/foo', installation);
}

Now when you use that method, it should wait for all returned promises to complete.

$.when.apply(null, DeleteDependentInstallations()).then(function() { alert('wee!'); });

The .apply() is so we can pass an array as an arguments collection.

EDIT: I was confusing "deferreds" and promises in my head. Deferreds are what the $.ajax calls return, and a promise is what the $.when() function returns.

EDIT2: You might also want to look at the .done() method, if the behavior of .then() doesn't suit your needs.

like image 188
Ben Lesh Avatar answered Feb 14 '26 22:02

Ben Lesh



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!