I am new to javascript and I need to chain functions execution, but function to react on success and failure different. Array of functions is get as parameter and result from previous is input parameter for next in chain in case of success, in error case I can define some alert/log behavior. I like how jquery has for exampel for GET ajax method success and failure. How to make that inner function fire those events, how is this implemented in javascript ?
I am new to javascript and I need to chain functions execution, but function to react on success and failure different. Array of functions is get as parameter and result from previous is input parameter for next in chain in case of success, in error case I can define some alert/log behavior. I like how jquery has for exampel for GET ajax method success and failure. How to make that inner function fire those events, how is this implemented in javascript ?
Share Improve this question edited Jan 26, 2014 at 2:34 m59 43.8k14 gold badges121 silver badges139 bronze badges asked Jan 26, 2014 at 0:43 PaolaJ.PaolaJ. 11.6k24 gold badges78 silver badges114 bronze badges 2- 1 At the basic level it's implemented with first-class functions (often closures) which are invoked when an asynchronous source has something important to say. Now, practically, this asynchronous behavior can often be managed through a Promises/A contract, such as that provided by jQuery's Deferred. – user2864740 Commented Jan 26, 2014 at 0:44
- @PaolaJ if you appreciate my answer, don't forget to click accept! – m59 Commented Jan 26, 2014 at 2:02
1 Answer
Reset to default 8Live demo of both solutions here (click).
Promises are now considered to be the best approach, rather than callbacks. I'll start with callbacks because they are easier to get started with and talk about promises afterwards.
Basic callbacks with object parameters:
//change this to true or false to make the function "succeed" or "fail"
//var flag = false;
var flag = true;
//this is the function that uses "success" and "error"
function foo(params) {
//some condition to determine success or failure
if (flag) {
//call the success function from the passed in object
params.success();
}
else {
//call the error function from the passed in object
params.error();
}
}
//function "foo" is called, passing in an object with success and error functions
foo({
success: function() {
console.log('success!');
},
error: function() {
console.log('error!');
}
});
Make sure a callback was passed in before firing it:
For a plete solution, you would also want to make sure those properties exist before calling them - only call the success and error functions if they were passed in.
Here's how I would do that:
if (flag) {
//the function is only fired if it exists
params.success && params.success();
}
Callbacks passed in as individual parameters:
You don't have to pass them in an object. You could just have the function accept individual parameters:
function foo(success, error) {
if (flag) {
success && success();
}
else {
error && error();
}
}
foo(
function() {
console.log('success!');
},
function() {
console.log('error!');
}
);
Callbacks passed in individually or in an object:
You can also have the function use individual parameters or functions from an object based on what was passed in. You would just check whether the first parameter is a function or object and use it accordingly:
function foo(success, error) {
if (arguments.length === 1 && typeof arguments[0] === 'object') {
var params = arguments[0];
success = params.success;
error = params.error;
}
if(flag) {
success && success();
}
else {
error && error();
}
}
foo(function() {
console.log('success');
});
foo({
success: function() {
console.log('success!');
}
});
Promises! Huzzah!
As I said, I greatly prefer to use promises, which are very nice for dealing with asynchronous functions. This will require a promise library or ES6 JavaScript. This is how it looks with jQuery. Most libraries are similar:
function bar() {
var deferred = new $.Deferred();
if (flag) {
//if you resolve then, the first "then" function will fire
deferred.resolve();
}
else {
//if you reject it, the second "then" function will fire
deferred.reject();
}
return deferred.promise();
}
//since "bar" returns a promise, you can attach a "then" function to it
//the first function will fire when the promise is resolved
//the second function will fire when the promise is rejected
bar().then(function() {
console.log('bar success!');
},
function() {
console.log('bar error!');
});
With JavaScript ES6 Promise:
function bar() {
return new Promise(function(resolve, reject) {
if (flag) {
resolve()
}
else {
reject();
}
})
}
Promises can be difficult to understand at first. There are plenty of good tutorials around to help you wrap your head around them.