Node.js
async.js
Ricerca…
Sintassi
Ogni callback deve essere scritto con questa sintassi:
funzione callback (err, risultato [, arg1 [, ...]])
In questo modo, sei costretto a restituire prima l'errore, e non puoi ignorarne la gestione in seguito.
null
è la convenzione in assenza di erroricallback (null, myResult);
Le tue callback possono contenere più argomenti di err e result , ma è utile solo per un set specifico di funzioni (cascata, seq, ...)
callback (null, myResult, myCustomArgument);
E, naturalmente, inviare errori. È necessario farlo e gestire gli errori (o almeno registrarli).
callback (err);
Parallelo: multi-tasking
async.parallel (tasks, afterTasksCallback) eseguirà una serie di attività in parallelo e attenderà la fine di tutte le attività (segnalate dalla chiamata della funzione di callback ).
Al termine delle attività, async chiama il callback principale con tutti gli errori e tutti i risultati delle attività.
function shortTimeFunction(callback) {
setTimeout(function() {
callback(null, 'resultOfShortTime');
}, 200);
}
function mediumTimeFunction(callback) {
setTimeout(function() {
callback(null, 'resultOfMediumTime');
}, 500);
}
function longTimeFunction(callback) {
setTimeout(function() {
callback(null, 'resultOfLongTime');
}, 1000);
}
async.parallel([
shortTimeFunction,
mediumTimeFunction,
longTimeFunction
],
function(err, results) {
if (err) {
return console.error(err);
}
console.log(results);
});
Risultato: ["resultOfShortTime", "resultOfMediumTime", "resultOfLongTime"]
.
Chiama async.parallel()
con un oggetto
È possibile sostituire il parametro dell'array tasks con un oggetto. In questo caso, i risultati saranno anche un oggetto con le stesse chiavi delle attività .
È molto utile calcolare alcune attività e trovare facilmente ogni risultato.
async.parallel({
short: shortTimeFunction,
medium: mediumTimeFunction,
long: longTimeFunction
},
function(err, results) {
if (err) {
return console.error(err);
}
console.log(results);
});
Risultato: {short: "resultOfShortTime", medium: "resultOfMediumTime", long: "resultOfLongTime"}
.
Risoluzione di più valori
Ogni funzione parallela è passata a un callback. Questo callback può restituire un errore come primo argomento o valore successivo. Se un callback viene passato a diversi valori di successo, questi risultati vengono restituiti come array.
async.parallel({
short: function shortTimeFunction(callback) {
setTimeout(function() {
callback(null, 'resultOfShortTime1', 'resultOfShortTime2');
}, 200);
},
medium: function mediumTimeFunction(callback) {
setTimeout(function() {
callback(null, 'resultOfMediumTime1', 'resultOfMeiumTime2');
}, 500);
}
},
function(err, results) {
if (err) {
return console.error(err);
}
console.log(results);
});
Risultato:
{
short: ["resultOfShortTime1", "resultOfShortTime2"],
medium: ["resultOfMediumTime1", "resultOfMediumTime2"]
}
.
Serie: mono-tasking indipendente
async.series (tasks, afterTasksCallback) eseguirà una serie di attività. Ogni attività viene eseguita dopo l'altra . Se un'attività non riesce, async interrompe immediatamente l'esecuzione e passa al callback principale .
Quando le attività sono terminate con successo, async chiama il callback "master" con tutti gli errori e tutti i risultati delle attività.
function shortTimeFunction(callback) {
setTimeout(function() {
callback(null, 'resultOfShortTime');
}, 200);
}
function mediumTimeFunction(callback) {
setTimeout(function() {
callback(null, 'resultOfMediumTime');
}, 500);
}
function longTimeFunction(callback) {
setTimeout(function() {
callback(null, 'resultOfLongTime');
}, 1000);
}
async.series([
mediumTimeFunction,
shortTimeFunction,
longTimeFunction
],
function(err, results) {
if (err) {
return console.error(err);
}
console.log(results);
});
Risultato: ["resultOfMediumTime", "resultOfShortTime", "resultOfLongTime"]
.
Chiama async.series()
con un oggetto
È possibile sostituire il parametro dell'array tasks con un oggetto. In questo caso, i risultati saranno anche un oggetto con le stesse chiavi delle attività .
È molto utile calcolare alcune attività e trovare facilmente ogni risultato.
async.series({
short: shortTimeFunction,
medium: mediumTimeFunction,
long: longTimeFunction
},
function(err, results) {
if (err) {
return console.error(err);
}
console.log(results);
});
Risultato: {short: "resultOfShortTime", medium: "resultOfMediumTime", long: "resultOfLongTime"}
.
Cascata: mono-tasking dipendente
async.waterfall (tasks, afterTasksCallback) eseguirà una serie di attività. Ogni attività viene eseguita dopo l'altra e il risultato di un'attività viene passato all'attività successiva . As async.series () , se un'attività non riesce, async interrompe l'esecuzione e chiama immediatamente il callback principale.
Quando le attività sono terminate con successo, async chiama il callback "master" con tutti gli errori e tutti i risultati delle attività.
function getUserRequest(callback) {
// We simulate the request with a timeout
setTimeout(function() {
var userResult = {
name : 'Aamu'
};
callback(null, userResult);
}, 500);
}
function getUserFriendsRequest(user, callback) {
// Another request simulate with a timeout
setTimeout(function() {
var friendsResult = [];
if (user.name === "Aamu"){
friendsResult = [{
name : 'Alice'
}, {
name: 'Bob'
}];
}
callback(null, friendsResult);
}, 500);
}
async.waterfall([
getUserRequest,
getUserFriendsRequest
],
function(err, results) {
if (err) {
return console.error(err);
}
console.log(JSON.stringify(results));
});
Risultato: i results
contengono il secondo parametro di callback dell'ultima funzione della cascata, che in questo caso è friendsResult
.
async.times (Per gestire il ciclo in modo migliore)
Per eseguire una funzione all'interno di un ciclo di node.js, è bene utilizzare una for
ciclo per brevi cicli. Ma il ciclo è lungo, l'uso for
ciclo for
aumenta il tempo di elaborazione che potrebbe causare il blocco del processo del nodo. In tali scenari, è possibile utilizzare: asycn.times
function recursiveAction(n, callback)
{
//do whatever want to do repeatedly
callback(err, result);
}
async.times(5, function(n, next) {
recursiveAction(n, function(err, result) {
next(err, result);
});
}, function(err, results) {
// we should now have 5 result
});
Questo è chiamato in parallelo. Quando vogliamo chiamarlo uno alla volta, utilizzare: async.timesSeries
async.each (Per gestire in modo efficiente l'array di dati)
Quando vogliamo gestire una matrice di dati, è meglio usare async.each . Quando vogliamo eseguire qualcosa con tutti i dati e vogliamo ottenere il callback finale una volta che tutto è stato fatto, allora questo metodo sarà utile. Questo è gestito in modo parallelo.
function createUser(userName, callback)
{
//create user in db
callback(null)//or error based on creation
}
var arrayOfData = ['Ritu', 'Sid', 'Tom'];
async.each(arrayOfData, function(eachUserName, callback) {
// Perform operation on each user.
console.log('Creating user '+eachUserName);
//Returning callback is must. Else it wont get the final callback, even if we miss to return one callback
createUser(eachUserName, callback);
}, function(err) {
//If any of the user creation failed may throw error.
if( err ) {
// One of the iterations produced an error.
// All processing will now stop.
console.log('unable to create user');
} else {
console.log('All user created successfully');
}
});
Per eseguire uno alla volta è possibile utilizzare async.eachSeries
async.series (per gestire gli eventi uno per uno)
/ In async.series, tutte le funzioni vengono eseguite in serie e gli output consolidati di ciascuna funzione vengono passati al callback finale. ad esempio /
var async = require ('async'); async.series ([function (callback) {console.log ('First Execute ..'); callback (null, 'userPersonalData');}, function (callback) {console.log ('Second Execute ..'); callback (null, 'userDependentData');}], function (err, result) {console.log (risultato);});
//Produzione:
First Execute .. Second Execute .. ['userPersonalData', 'userDependentData'] // result