Angular Promises

Angular Promises

Promises are a pattern that helps with one particular kind of asynchronous programming: a function (or method) that returns a single result asynchronously. One popular way of receiving such a result is via a callback (“callbacks as continuations”):

asyncFunction(arg1, arg2,

result => {

console.log(result);

});

Promises are not actually complicated, they’re objects that contain a reference to functions to call when something fails or succeeds.

Under the hood, AngularJS actually wires up a promise for an HTTP request in a way a bit like this:

var request = new XMLHttpRequest();
request.addEventListener(“load”, function() {
// complete the promise
}, false);
request.addEventListener(“error”, function() {
// fail the promise
}, false);
request.open(“GET”, “/api/my/name”, true);
request.send();

this is pseudo-code, but the idea is that its the browser that calls us back, via the event listeners, then AngularJS can just call the appropriate method on the promise.

Now in AngularJS, the promises are created with the $q service (we’ll see exactly how to do this shortly), but why $q?

The reason the service is named $q is that AngularJS’ promise implementation is based on Kris Kowal’s promise mechanism, which is called ‘Q’. You can see the library at github.com/kristkowal/q.

This was a deliberate decision, as the Q library is widely used and well understood by the community. We’re going to see a little bit later what the future of promises is in AngularJS and actually in ECMAScript 6.
A Real World Example

In this example, we’ll create a service that gets the user’s name, just like in our examples. However, to make it interesting, we’ll set our service up so that the first time we get the name from the server, and then afterwards we’ll return a cached copy.

This means we’ll have to build our code to deal with the asynchronous case (the first one) and the more trivial synchronous case (getting the name from the cache).

Let’s look at a pure asynchronous implementation.

app.factory(‘NameService’, function($http, $q) {

// Create a class that represents our name service.
function NameService() {

var self = this;

// getName returns a promise which when
// fulfilled returns the name.
self.getName = function() {
return $http.get(‘/api/my/name’);
};
}

return new NameService();
});

Now let’s update our service so that we hit the server only if we haven’t already cached the name. I’ll build the service blow by blow, then we can see a fiddle of it working.

app.factory(‘NameService’, function($http, $q) {

// Create a class that represents our name service.
function NameService() {

var self = this;

// Initially the name is unknown….
self.name = null;

so first we create a service which is in the form of a class. It has a name field which is initially null.

self.getName = function() {
// Create a deferred operation.
var deferred = $q.defer();

Now in the getName function we start by creating a deferred object, using the $q service. This object contains the promise we’ll return, and has some helper functions to let us build the promise.

We create a deferred object because whether we use ajax or not, we want the consumer to use the promise – even if we can return straightaway in some circumstances (when we have the name) we can’t in all – so the caller must always expect a promise.

if(self.name !== null) {
deferred.resolve(self.name + ” (from Cache!)”);
}

If we already have the name, we can just resolve the deferred object immediately – this is the easy case. I’ve added ‘from cache’ to the name so we can see when it comes from the cache compared to the server.

Finally, we can handle the case if we don’t already have the name:

else {
// Get the name from the server.
$http.get(‘/api/my/name/’)
.success(function(name) {
self.name = name;
deferred.resolve(name + ” (from Server!)”);
})
.error(function(response) {
deferred.reject(response);
});
}

So if we get success from the server, we can resolve the promise. Otherwise, we reject it, which means failure.

IT Professionals, Web Developers, web programmers, IT students can Apply for the certification course and get ahead.

Angular 4 Tutorial IndexBack to Angular 4 Tutorial Main Page

Share this post
[social_warfare]
Angular 4 Promises, and Route Protection
Angular Observables

Get industry recognized certification – Contact us

keyboard_arrow_up