1 var async = require('./async.js')
2 , abort = require('./abort.js')
6 module.exports = iterate;
9 * Iterates over each job object
11 * @param {array|object} list - array or object (named list) to iterate over
12 * @param {function} iterator - iterator to run
13 * @param {object} state - current job status
14 * @param {function} callback - invoked when all elements processed
16 function iterate(list, iterator, state, callback)
18 // store current index
19 var key = state['keyedList'] ? state['keyedList'][state.index] : state.index;
21 state.jobs[key] = runJob(iterator, key, list[key], function(error, output)
23 // don't repeat yourself
24 // skip secondary callbacks
25 if (!(key in state.jobs))
31 delete state.jobs[key];
35 // don't process rest of the results
36 // stop still active jobs
42 state.results[key] = output;
45 // return salvaged results
46 callback(error, state.results);
51 * Runs iterator over provided job element
53 * @param {function} iterator - iterator to invoke
54 * @param {string|number} key - key/index of the element in the list of jobs
55 * @param {mixed} item - job description
56 * @param {function} callback - invoked after iterator is done with the job
57 * @returns {function|mixed} - job abort function or something else
59 function runJob(iterator, key, item, callback)
63 // allow shortcut if iterator expects only two arguments
64 if (iterator.length == 2)
66 aborter = iterator(item, async(callback));
68 // otherwise go with full three arguments
71 aborter = iterator(item, key, async(callback));