slandau
slandau

Reputation: 24052

Javascript method chaining

Didn't know how else to put this.

Say I have a JavaScript method that makes some AJAX calls:

function makeAJAXCalls()
{
    // who knows how long this will take
}

And I don't want the next function to execute until all the AJAX calls are complete. I also don't want to put the next function call into the success callback for the AJAX call.

Is there a way I can like chain these, so the next function doesn't get called until makeAJAXCalls() is done everything it needs to do?

Upvotes: 3

Views: 368

Answers (6)

John Green
John Green

Reputation: 13435

var queueCount =0;
function makeAjaxCalls()
{
    queueCount+=7; // or however many calls you need to make.
    // make your ajax calls. onSuccess (or failure), call checkQueue();
}
function checkQueue()
{
    queueCount--;
    if (queueCount <=0)
    {
       doNext();
    }
}

This leaves the calls asynchronous, which may be the intent here.

Upvotes: 2

Matt Ball
Matt Ball

Reputation: 359826

You can make chained ajax calls if you're using jQuery 1.5+. This works because $.ajax() returns a jqXHR which is also a Deferred Object.

function makeAjaxCalls()
{
    return $.ajax(/* snip options */);
}

function handleSuccess(data)
{
    // do something with the data
}

function nextAjax()
{
    return $.ajax(/* snip other options */);
}

// then...
makeAjaxCalls().success(handleSuccess).complete(nextAjax);

Upvotes: 1

SLaks
SLaks

Reputation: 887453

You should take your own callback as a parameter to the function.
This way, the caller can decide what to do next.

You could also return a Deferred object.

Upvotes: 0

Quintin Robinson
Quintin Robinson

Reputation: 82335

You could, by making your calls synchronous.

Example: Synchronous request

Although you might want to take note that this will probably cause an undesired blocking effect on the rest of your application that might call into question the reason for using synchronous xhr.

Upvotes: 1

Mike Fielden
Mike Fielden

Reputation: 10153

You could use jQuery's $.when() functionality.

$.when(makeAjaxCalls()).done(function () { 
   // Do other things here 
});

You can even add multiple functions to the when if you wanted all of those to be completed first. These are all called Deferred Objects.

Upvotes: 3

hvgotcodes
hvgotcodes

Reputation: 120198

You are really limiting your options. AJAX is asynchronous by nature (unless you use synchronized xhrs, which you don't want because they freeze the browser). So your only option is to handle it in the callback, because the callbacks are the only way you know the request has completed, and where the data from the requests gets passed when they complete.

Because you have multiple callbacks, and you want to wait till they are all done, you can put the same function call in all the callbacks, and that function can track which responses have come back, and only proceed if all responses are there.

so you can do something like

var resultsHolder = [];
var syncer = function(response){
    // add results to resultsHolder on call

    if (resultsHolder.lengh === numberExpected) {
     //proceed
    }
}

then use syncer in your makeAllRequests method

Upvotes: 1

Related Questions