Ecosyste.ms: Awesome
An open API service indexing awesome lists of open source software.
https://github.com/jsdario/promise-unmap
Wait for all promises to fulfill, and throw if some fail, after all have fulfilled
https://github.com/jsdario/promise-unmap
bluebird execution lightweight map parallel promises serial
Last synced: 16 days ago
JSON representation
Wait for all promises to fulfill, and throw if some fail, after all have fulfilled
- Host: GitHub
- URL: https://github.com/jsdario/promise-unmap
- Owner: jsdario
- Created: 2018-04-10T11:26:18.000Z (over 6 years ago)
- Default Branch: master
- Last Pushed: 2018-06-05T10:10:49.000Z (over 6 years ago)
- Last Synced: 2024-11-18T19:03:39.225Z (about 1 month ago)
- Topics: bluebird, execution, lightweight, map, parallel, promises, serial
- Language: JavaScript
- Size: 4.15 MB
- Stars: 1
- Watchers: 2
- Forks: 1
- Open Issues: 0
-
Metadata Files:
- Readme: README.md
Awesome Lists containing this project
README
# promiseUnmap
[![CircleCI](https://circleci.com/gh/jsdario/promise-unmap.svg?style=svg)](https://circleci.com/gh/jsdario/promise-unmap)
Similar to [Promise.map(ary)](http://bluebirdjs.com/docs/api/promise.map.html) with some connotations:
1. If all promises resolve, the global promise resolves,
that is identical.
2. All promises are going to be started, unmap won'tfulfill until all of them resolve or reject.
3. If any promises reject, promiseUnmap will reject
with an Error containing all errors in its body
as `err.errors: Array`. The message of the global
error will be: "One or more tasks failed". Any fulfillments
will also be inside `err.fulfillments: Array`
4. If it fulfills, it will resolve the map of fulfillments.## Usage
Either `const {promiseUnmap} = require('promise-unmap')` or `import {promiseUnmap} from 'promise-unmap'`
It accepts an array of **promises** or **functions that return promises**.
```javascript
const {promiseUnmap} = require('../')// ...
const ops = [
async () => 'resolves 1',
async () => { throw new Error('fails 2') },
Promise.resolve('resolves 3'),
async () => 'resolves 4',
Promise.reject(new Error('fails 5')),
async () => 'resolves 6',
]promiseUnmap(ops)
.catch(err => {
expect(err.errors.length).to.equal(2)
expect(err.fulfillments.length).to.equal(4)
})
})
```### promiseUnmapSerial
Chain calls, return all results, throw if any errors.
```javascript
it('should fail with mixed requests in serial', function(done) {
promiseUnmapSerial(ops)
.catch(err => {
expect(err.errors.length).to.equal(2)
expect(err.fulfillments.length).to.equal(4)
done()
})
})t('should not fail if all are passing in serial', function(done) {
promiseUnmapSerial(passingOps)
.then(results => {
expect(results.length).to.equal(2)
done()
})
.catch(done)
})
```## Implementation
It is pretty obscure, read with caution. Basically consists
on wrapping all promises with a safe catch, to later processing
the results.It is written in typescript. A type `Future` is defined as a promise
or an async function (something that returns a promise). This way
we can warrantee that promises are not started until they are called.```javascript
type Future = Promise | () => Promise
```A `typeof` check is performed to know whether the future should
begin or it is an unfulfilled promise that we must await.```javascript
export function promiseUnmap (futures: Array) {
return Promise.all(futures.map(f => {
return typeof f === 'function'
? f().catch((err: Error) => err)
: f.catch((err: Error) => err)
})).then((results: Array) => {
if (results.some(r => r instanceof Error)) {
throw new PromiseUnmapError(results)
}
return results
})
}
```The following method, `promiseUnmapSerial` has been defined to enqueue such futures,
to safely execute a number of asynchronous functions, without interfering one another
(or await serially for promises to finish, but for that we already have
[bluebird's `mapSeries`](http://bluebirdjs.com/docs/api/promise.mapseries.html))```javascript
export function promiseUnmapSerial (futures: Array) {
const safePromises = futures.map(f => {
const p = typeof f === 'function' ? f() : f
return p.catch(err => err)
})return safePromises.reduce((accPromises, currPromise) =>
accPromises.then(accResults =>
currPromise.then(currResult => [...accResults, currResult])
)
, Promise.resolve([]))
.then(results => {
if (results.some((r: any) => r instanceof Error)) {
return Promise.reject(new PromiseUnmapError(results))
}
return results
})
}
```