Skip to content

Instantly share code, notes, and snippets.

Embed
What would you like to do?
Here's another chaining example on using q.js. This doesn't have any error handling, as I just want to demonstrate the chaining concept. Please read the comments carefully, as I start out with a non-q example, to show the order of flow. Please post comments if there's anything that isn't clear and I'll try to revise it as needed.
// Q sample by Jeff Cogswell
/*===========
We want to call these three functions in sequence, one after the other:
First we want to call one, which initiates an ajax call. Once that
ajax call is complete, we want to call two. Once two's ajax call is
complete, we want to call three.
BUT, we don't want to just call our three functions in sequence, as this quick
demo will show. Look at this sample function and think about what order
the console.log calls will happen:
===========*/
function demo() {
$.ajax( {
url: '/',
success: function() {
console.log('AJAX FINISHED');
}
});
}
console.log('Calling demo');
demo();
console.log('Finished calling demo');
/*====
The function returns almost immediately, before the ajax call is complete.
That means we will likely see 'Finished calling demo' before we see the
results of the ajax call:
====*/
//Calling demo
//Finished calling demo
//AJAX FINISHED
/*====
If we want to chain a following function, when do we call it?
We call it from inside the success function:
====*/
function demo() {
$.ajax( {
url: '/',
success: function() {
console.log('AJAX FINISHED');
// >>>> THIS IS WHEN you would call another function <<<<<
}
});
}
/* ==============
Now let's try using q.
=============*/
function one() {
var deferred = Q.defer(); // Don't worry yet what this is
// until after you understand the flow
console.log("Starting one's ajax");
$.ajax( {
url: '/',
success: function() {
// Here's where you want to call the next function in the
// list if there is one. To do it, call deferred.resolve()
console.log('Finished with one. Ready to call next.');
deferred.resolve();
}
});
// The deferred object has a "promise" member,
// which has a "then" function
return deferred.promise;
}
function two() {
var deferred = Q.defer();
console.log("Starting two's ajax");
$.ajax( {
url: '/',
success: function() {
// Again, this is where you want to call the next function
// in the list if there is one.
console.log('Finished with two. Ready to call next.');
deferred.resolve();
}
});
// The deferred object has a "promise" member,
// which has a "then" function
return deferred.promise;
}
function three() {
var deferred = Q.defer();
console.log("Starting three's ajax");
$.ajax( {
url: '/',
success: function() {
// Again, this is where you want to call the next function
// in the list if there is one.
console.log('Finished with three. Ready to call next if there is one.');
deferred.resolve();
}
});
// The deferred object has a "promise" member, which has a "then" function
return deferred.promise;
}
// Test it out. Call the first. Pass the functions
// (without calling them, so no parentheses) into the then calls.
one()
.then(two)
.then(three);
/* =====
Think about where the "then" function comes from. Each function
creates a new defer instance and returns that object's promise
member. That promise object has a "then" function. On return
from the first function, you get back a defer function, and
call the "then" function, passing the *next* function that is
to be called. Internally, Q stores that function. When your
ajax call returns, in your "success" function, you call the
next function by calling deferred.resolve().
======*/
@ajijohn

This comment has been minimized.

Copy link

ajijohn commented Jan 28, 2014

great example

@sysnajar

This comment has been minimized.

Copy link

sysnajar commented Jan 30, 2014

great! thanks.

@dhaval-shownkani

This comment has been minimized.

Copy link

dhaval-shownkani commented Feb 28, 2014

thanks a lott :)

@dandoyon

This comment has been minimized.

Copy link

dandoyon commented Mar 1, 2014

now that is a sweet example

@aradnom

This comment has been minimized.

Copy link

aradnom commented Mar 5, 2014

Very instructive. Thank you.

@Heshyo

This comment has been minimized.

Copy link

Heshyo commented Mar 5, 2014

Nice example. I just thought passing some argument to the different methods could be interesting (for ex two will work on the value from one, three from two, ...).

https://gist.github.com/Heshyo/9364276#file-q_example-js

@jeffcogswell

This comment has been minimized.

Copy link
Owner Author

jeffcogswell commented Apr 14, 2014

@Heshyo -- Excellent!

@kbgould

This comment has been minimized.

Copy link

kbgould commented May 16, 2014

Great example -- thank you.

@jeffcogswell

This comment has been minimized.

Copy link
Owner Author

jeffcogswell commented Jul 1, 2014

Check out the forks for some good updates to this example.

@jordanbtucker

This comment has been minimized.

Copy link

jordanbtucker commented Jul 22, 2014

Finally, an example that actually makes sense to me.

@sandeshdshetty

This comment has been minimized.

Copy link

sandeshdshetty commented Aug 1, 2014

thanks ... good example

@mbayopanda

This comment has been minimized.

Copy link

mbayopanda commented Aug 20, 2014

Merci beaucoup pour votre exemple, ca m'a vraiment aidé.... thanks

@Vayvala

This comment has been minimized.

Copy link

Vayvala commented Aug 27, 2014

I got it now, thanks!

@nuklehed

This comment has been minimized.

Copy link

nuklehed commented Oct 12, 2014

Excellent description!

@wyqydsyq

This comment has been minimized.

Copy link

wyqydsyq commented Nov 7, 2014

👍 The first Q (or promises in general) example that actually helped me understand how it works

@limsim

This comment has been minimized.

Copy link

limsim commented Jan 13, 2015

A much better example for beginners than the one given in the project. And I totally agree that non working examples are not helpful.

@sertugkaya

This comment has been minimized.

Copy link

sertugkaya commented Jan 26, 2015

Really explanatory, thanks!

@gerardocamilo

This comment has been minimized.

Copy link

gerardocamilo commented Feb 6, 2015

This example really got me on board, thanks!

@caseybbrumbaugh

This comment has been minimized.

Copy link

caseybbrumbaugh commented Feb 17, 2015

Finally a practical and well documented example. Thanks for your efforts!

@freeslugs

This comment has been minimized.

Copy link

freeslugs commented Feb 22, 2015

awesome

@csparpa

This comment has been minimized.

Copy link

csparpa commented May 25, 2015

super!

@lorenzoongithub

This comment has been minimized.

Copy link

lorenzoongithub commented Jun 22, 2015

@stianSjoli

This comment has been minimized.

Copy link

stianSjoli commented Jul 10, 2015

I liked this example - can you show one with passing return values between three function too?

@stianSjoli

This comment has been minimized.

Copy link

stianSjoli commented Jul 10, 2015

is this a right way to do it? we can imagine that this works for async functions, right?
var Q = require("q");

function one(){
var deferred = Q.defer();
console.log("I am one");
deferred.resolve("hello");
return deferred.promise;
}

function two(test){
var deferred = Q.defer();
console.log("I am two " + test);
deferred.resolve();
return deferred.promise;
}

function three(){
var deferred = Q.defer();
console.log("I am three");
deferred.resolve();
return deferred.promise;
}

one()
.then(two)
.then(three)

@jaconstantine

This comment has been minimized.

Copy link

jaconstantine commented Aug 7, 2015

If I want to introduce a delay between lets say two and three, I create:

function delay(ms) {
    var deferred = Q.defer();
    console.log("starting delay");
    setTimeout(deferred.resolve, ms);
    return deferred.promise;
}

And then I call:

one()
.then(two)
.then(delay(2000))
.then(three)

I don't see the delay occuring until after three runs. I see:

Starting one's ajax
starting delay
Finished with one. Ready to call next.
Starting two's ajax
Finished with two. Ready to call next.
Starting three's ajax
Finished with three. Ready to call next if there is one.

What's going wrong?

@GasCreature

This comment has been minimized.

Copy link

GasCreature commented Aug 26, 2015

Even this example is not clear. For one thing, what is the $ variable? Is it the jQuery handle? If so, where is the require statement for jQuery? Is this only for the browser? Where is the script tag to load jQuery or Q? I tried running it in NodeJS (since that's what I want Q for). Is there a $.ajax function for the server side?

@wimvanleuven

This comment has been minimized.

Copy link

wimvanleuven commented Sep 28, 2015

Wouldn't it be much clearer/respresentative to rewrite the example as

one()
.then(new function() {
    return two();
})
.then(new function() {
    return delay(2000);
})
.then(new function() {
    return three();
})
.fail(new function(err) {
  console.log("Something went terribly wrong between 1, 2 and 3! " + err);
});
@josephpconley

This comment has been minimized.

Copy link

josephpconley commented Jun 3, 2016

Thanks for the great example! Here's a JSFiddle for experimenting: https://jsfiddle.net/josepi08/0nevk0a9/

@galendog

This comment has been minimized.

Copy link

galendog commented Jun 4, 2017

New to Q and it's Promise API's,
one()
.then(two)
.then(three);
.done // Looking at the doc's https://github.com/kriskowal/q/wiki/API-Reference should you call "done" at the end?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
You can’t perform that action at this time.