Skip to content

Commit 6ce39af

Browse files
author
Jason Walton
committed
Add 'map'
1 parent 6b251e6 commit 6ce39af

File tree

3 files changed

+55
-0
lines changed

3 files changed

+55
-0
lines changed

README.md

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -32,6 +32,10 @@ Then somewhere in your node.js application:
3232

3333
# API
3434

35+
## Collections
36+
37+
* [`map`](#map)
38+
3539
## Utilities
3640

3741
* [`defer`](#defer)
@@ -44,6 +48,14 @@ Then somewhere in your node.js application:
4448
* [`whilst`](#whilst), `doWhilst`
4549
* [`retry`](#retry)
4650

51+
# Collections
52+
53+
<a name="map"/>
54+
### map(arr, iterator, limit)
55+
56+
Calls `iterator(item, index)` for every item in `map`, which should return a Promise. If `limit` is specified,
57+
then at most `limit` calls to iterator will be started at a time. Resolves to an array of items (the resolved
58+
value of each promise returned by `iterator()`). If any iterator rejects, this will reject immediately.
4759

4860
# Utilities
4961

src/index.js

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -118,6 +118,21 @@ exports.parallel = exports.parallelLimit = (tasks, limit) => {
118118
});
119119
};
120120

121+
/*
122+
* Given an array `arr` of items, calls `iter(item, index)` for every item in `arr`. `iter()` should return a
123+
* Promise. Up to `limit` items will be called in parallel (defaults to 1.)
124+
*/
125+
exports.map = (arr, iter, limit) => {
126+
let taskLimit = limit;
127+
if (!limit || limit < 1) {taskLimit = 1;}
128+
if (limit >= arr.length) {taskLimit = arr.length;}
129+
130+
let tasks = arr.map((item, index) => (() => iter(item, index)));
131+
return exports.parallel(tasks, taskLimit);
132+
};
133+
134+
135+
121136
/*
122137
* Add a timeout to an existing Promise.
123138
*

test/map.js

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
"use strict"
2+
3+
let chai = require('chai');
4+
chai.use(require('chai-as-promised'));
5+
let expect = chai.expect;
6+
let promiseTools = require('../src');
7+
8+
describe('map', () => {
9+
it('should map an array of values', () => {
10+
let arr = ['a', 'b', 'c'];
11+
let iter = (value, index) => Promise.resolve(value + index);
12+
return expect(promiseTools.map(arr, iter)).to.eventually.eql(['a0', 'b1', 'c2']);
13+
});
14+
15+
it('should map an array of values without using promises', () => {
16+
let arr = ['a', 'b', 'c'];
17+
let iter = (value, index) => value + index;
18+
return expect(promiseTools.map(arr, iter)).to.eventually.eql(['a0', 'b1', 'c2']);
19+
});
20+
21+
it('should work if the limit is 0, or too large', () => {
22+
let arr = ['a', 'b', 'c'];
23+
let iter = (value, index) => value + index;
24+
return expect(promiseTools.map(arr, iter, 0)).to.eventually.eql(['a0', 'b1', 'c2'])
25+
.then(() => expect(promiseTools.map(arr, iter, 100)).to.eventually.eql(['a0', 'b1', 'c2']));
26+
});
27+
28+
});

0 commit comments

Comments
 (0)