Click here to Skip to main content
13,146,365 members (44,111 online)
Click here to Skip to main content
Add your own
alternative version

Tagged as

Stats

4.8K views
12 bookmarked
Posted 13 Apr 2017

Waiting For Multiple Ajax Requests - jQuery

, 13 Apr 2017
Rate this:
Please Sign up or sign in to vote.
Write jQuery code to wait for multiple Ajax requests

Introduction

Usually, jQuery function ajax is used to make an Ajax call. Function ajax can only make one Ajax call. A callback function is executed when the Ajax call is successful. Optionally, another callback function is called when the Ajax call returns an error. However, this function can not make multiple Ajax requests and register callback functions based on the outcome of these requests. One scenario is that a web page makes multiple Ajax requests to gather data for different sections of the page while disabling user interaction. The page enables user interaction only after the page gets all data. This article describes a method provided by jQuery to register a callback function based on multiple Ajax requests. This method is based on the concept of Deferred object.

Using the code

First, two ASP.NET Web API functions are used to accept server Ajax calls.

public class ValuesController : ApiController
{
    // GET api/values
    public IEnumerable<string> Get()
    {
        return new string[] { "value1", "value2" };
    }

    // GET api/values/5
    public string Get(int id)
    {
        string s = "Id is " + Convert.ToString(id);
        return s;
    }
}

To make a single Ajax call, jQuery function ajax can be used. Here is a simple example.

$.ajax({
    url: 'api/values',
    dataType: 'json',
    type: 'GET',
    success: function (data) {
        alert(data[0]);
    },
    error: function () {
        alert('Error!');
    }
});

The success and error callback functions are waiting for a single Ajax call.

The jQuery library provides a way to make any callback function waiting for multiple Ajax calls. This method is based on an object called Deferred.

A Deferred object can register callback functions based on whether the Deferrred object is resolved or rejected. Here is an example of the Deferred object.

// Create a Deferred object.
var def1 = $.Deferred();
// Add a function to be called when the Deferred object is resolved.
def1.done(function (data) {
    alert(data);
});
// Resolve the Deferrd object.
def1.resolve('Resolved!');

// Create a Deferred object.
var def2 = $.Deferred();
// Add a function to be called when the Deferred object is rejected.
def2.fail(function (data) {
    alert(data);
});
// Reject the Deferrd object.
def2.reject('Rejected!');

Note the Deferred object can be chained. Here is an example of the Deferred object chain.

var def = $.Deferred();
def.done(function (data) {
    alert(data);
}).fail(function (data) {
    alert(data);
});
// Reject the Deferrd object.
def.reject('Rejected!');

The Deferred object has a method called promise. It returns a Promise object. A Promise object exposes a subset of Deferred methods to prevent its state to be changed. That means, to prevent the Deferred object to be resolved or rejected manually. A Promise object exposes the following Deferred methods:

then, done, fail, always, pipe, progress, state and promise.

It does not expose the following Deferred methods:

resolve, reject, notify, resolveWith, rejectWith and notifyWith.

A Promise object can be treated as a Deferred object which state cannot be manually changed.

The jQuery ajax function returns a jqXHR object. There are two important facts about this jqXHR object.

First, a jqXHR object is a superset of XMLHTTPRequest object. For example, a jqXHR object can query the state of the XMLHTTPRequest by referring its readyState property. If its readyState is 4, the Ajax request is completed.

Second, a jqXHR object implements the Promise interface and exposes all Promise methods. Basically, a jqXHR oject can be treated as a Promise object. For example, the done method can be used as the success callback function for a jqXHR object.

The jQuery library provides a function called when to accept multiple Deferred objects and returns a Promise object. The returned Promise object will be resolved when all Deferred objects are resolved. It will be rejected when any Deferred object is rejected. The Deferred objects passed to function when can be Deferred objects, Promise objects or jqXHR objects.

Here is an example of code waiting for multiple Ajax requests.

$(document).ready(function () {
    var j1 = $.ajax({
        url: 'api/values',
        dataType: 'json',
        type: 'GET'
    });

    var j2 = $.ajax({
        url: 'api/values',
        dataType: 'json',
        data: { id: 5 },
        type: 'GET'
    });

    $.when(j1, j2).then(function (a1, a2) {
        alert('Both j1 and j2 succeedeed!');
    }, function (jqXHR, textStatus, errorThrown) {
        var x1 = j1;
        var x2 = j2;
        if (x1.readyState != 4) {
            x1.abort();
        }
        if (x2.readyState != 4) {
            x2.abort();
        }
       alert('Either j1 or j2 failed!');
    });
});

First, two variables store the jqXHR objects returned from two jQuery Ajax calls. Then the two objects are passed to function when. The Promise object returned from when is chained to function then. Function then adds handlers for the Promise object. The first parameter of function then is a success function which is called when the Promise is resolved. The second parameter of function then is a fail function which is called when the Promise is rejected. The fail function checks the state of each Ajax call. If the Ajax call is not completed, it is aborted. Note the fail function can still access variable j1 and j2 which are out of scope since the document ready function has been
executed and closed. This is because of JavaScript closures. A closure is an inner function which has access to variables in outer function even the outer function is closed. In other words, the inner function can keep the environment in which it is first defined.

License

This article, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)

Share

About the Author

George MVC Study
Software Developer
Canada Canada
I am working with ASP.NET related technologies.

You may also be interested in...

Comments and Discussions

 
-- There are no messages in this forum --
Permalink | Advertise | Privacy | Terms of Use | Mobile
Web01 | 2.8.170915.1 | Last Updated 14 Apr 2017
Article Copyright 2017 by George MVC Study
Everything else Copyright © CodeProject, 1999-2017
Layout: fixed | fluid