I have only used simple callbacks, i.e. function that performs async AJAX call and calls back once done. Whenever things got anymore complicated I have used $.Deferred(). The problem is that handling promises is a lot of code every time, i would like to know how to use callbacks correctly instead.
Here is my example. (the problem arises in the return from secondary()):
function primary()
{
//call secondary with self as callback
var data = secondary("someStr", primary);
if (data !== false) {
//logic that uses data
}
}
function secondary(str, callback)
{
//call the third function. Since we need parameters
//on the callback, we create anon function
var returnFromThird = tertiary(function() {
secondary(str, callback);
});
if (returnFromThird !== false) {
//when we have data from third do someting....
//but here lies the problem, how do i callback primary()?
return returnFromThird + " " + str;
} else {
//third is not yet ready
return false;
}
}
var myVar3 = null;
function tertiary(callback)
{
if (myVar3 === null) {
//do async ajax call that sets myVar3 value
var ajaxRequest = $.ajax({
url: "/someUrl",
type: "POST",
data: {myData : "blabla"},
async: true,
});
ajaxRequest.done(function(data) {
myVar3 = data;
//issue the call back, so secondary() can come get myVar3
callback();
});
//we did not have the required data so we return false
return false;
} else {
return myVar3;
}
}
//execute
primary();
Here is how i would normally handle the issue using JQuery Deferred:
function primary()
{
var promise = secondary(str);
$.when(promise).then(
function (data) {
//logic that uses data
}
);
}
function secondary(str)
{
var dfd = $.Deferred();
var promise = tertiary();
$.when(promise).then(
function (data) {
dfd.resolve(data + " " + str);
}
);
return dfd.promise();
}
var myVar3 = null;
function tertiary()
{
var dfd = $.Deferred();
if (myVar3 === null) {
var ajaxRequest = $.ajax({
url: "/someUrl",
type: "POST",
data: {myData : "blabla"},
async: true,
});
ajaxRequest.done(function(data) {
myVar3 = data;
dfd.resolve(myVar3);
});
} else {
dfd.resolve(myVar3);
}
return dfd.promise();
}
primary();