fluture
Advanced tools
Comparing version 12.0.2 to 12.1.0
@@ -67,8 +67,11 @@ /// <reference lib="es2015.generator" /> | ||
/** Apply the function in the left Future to the value in the right Future. See https://github.com/fluture-js/Fluture#ap */ | ||
/** Apply the function in the right Future to the value in the left Future. See https://github.com/fluture-js/Fluture#ap */ | ||
export function ap<L, RA>(value: FutureInstance<L, RA>): <RB>(apply: FutureInstance<L, (value: RA) => RB>) => FutureInstance<L, RB> | ||
/** Apply the function in the left ConcurrentFuture to the value in the right ConcurrentFuture. See https://github.com/fluture-js/Fluture#ap */ | ||
/** Apply the function in the right ConcurrentFuture to the value in the left ConcurrentFuture. See https://github.com/fluture-js/Fluture#ap */ | ||
export function ap<L, RA>(value: ConcurrentFutureInstance<L, RA>): <RB>(apply: ConcurrentFutureInstance<L, (value: RA) => RB>) => ConcurrentFutureInstance<L, RB> | ||
/** Apply the function in the right Future to the value in the left Future in parallel. See https://github.com/fluture-js/Fluture#pap */ | ||
export function pap<L, RA>(value: FutureInstance<L, RA>): <RB>(apply: FutureInstance<L, (value: RA) => RB>) => FutureInstance<L, RB> | ||
/** Create a Future which resolves with the return value of the given function, or rejects with the error it throws. See https://github.com/fluture-js/Fluture#attempt */ | ||
@@ -80,3 +83,3 @@ export function attempt<L, R>(fn: () => R): FutureInstance<L, R> | ||
/** Map over both branched of the given Bifunctor at once. See https://github.com/fluture-js/Fluture#bimap */ | ||
/** Map over both branches of the given Bifunctor at once. See https://github.com/fluture-js/Fluture#bimap */ | ||
export function bimap<LA, LB>(lmapper: (reason: LA) => LB): <RA, RB>(rmapper: (value: RA) => RB) => (source: FutureInstance<LA, RA>) => FutureInstance<LB, RB> | ||
@@ -83,0 +86,0 @@ |
@@ -36,3 +36,3 @@ export { | ||
export {node} from './src/node.js'; | ||
export {parallelAp} from './src/parallel-ap.js'; | ||
export {pap} from './src/pap.js'; | ||
export {parallel} from './src/parallel.js'; | ||
@@ -39,0 +39,0 @@ export {Par} from './src/par.js'; |
{ | ||
"name": "fluture", | ||
"version": "12.0.2", | ||
"version": "12.1.0", | ||
"description": "FantasyLand compliant (monadic) alternative to Promises", | ||
@@ -63,3 +63,2 @@ "main": "index.cjs", | ||
"dependencies": { | ||
"concurrify": "^2.0.0", | ||
"sanctuary-show": "^1.0.0", | ||
@@ -69,3 +68,3 @@ "sanctuary-type-identifiers": "^2.0.0" | ||
"devDependencies": { | ||
"c8": "^6.0.0", | ||
"c8": "^7.0.0", | ||
"chai": "^4.1.2", | ||
@@ -72,0 +71,0 @@ "codecov": "^3.6.1", |
@@ -94,3 +94,3 @@ # [![Fluture](logo.png)](#butterfly) | ||
Fluture is hosted in full with all of its dependencies at | ||
https://cdn.jsdelivr.net/gh/fluture-js/Fluture@12.0.2/dist/bundle.js | ||
https://cdn.jsdelivr.net/gh/fluture-js/Fluture@12.1.0/dist/bundle.js | ||
@@ -180,2 +180,3 @@ This script will add `Fluture` to the global scope. | ||
- [`ap`: Combine the success values of multiple Futures using a function](#ap) | ||
- [`pap`: Combine the success values of multiple Futures in parallel using a function](#pap) | ||
- [`and`: Logical *and* for Futures](#and) | ||
@@ -202,2 +203,3 @@ - [`alt`: Logical *or* for Futures](#alt) | ||
- [`pap`: Combine the success values of multiple Futures in parallel using a function](#pap) | ||
- [`race`: Race two Futures against each other](#race) | ||
@@ -256,3 +258,3 @@ - [`both`: Await both success values from two Futures](#both) | ||
- **Future** - Instances of Future provided by [compatible versions](#casting-futures) of Fluture. | ||
- **ConcurrentFuture** - [Concurrified][concurrify] Futures ([`Future.Par`](#concurrentfuture)). | ||
- **ConcurrentFuture** - Futures wrapped with ([`Future.Par`](#concurrentfuture)). | ||
- **Promise a b** - Values which conform to the [Promises/A+ specification][7] | ||
@@ -345,5 +347,5 @@ and have a rejection reason of type `a` and a resolution value of type `b`. | ||
> const m = resolve (1) | ||
> let m = resolve (1) | ||
> for (const i = 0; i < 100000; i++) { | ||
> for (let i = 0; i < 100000; i++) { | ||
. m = map (add1) (m) | ||
@@ -995,6 +997,6 @@ . } | ||
\* If you'd like to use a parallel implementation of `ap`, you need to use a | ||
non-monadic type. Fluture provides this through [`Par`](#concurrentfuture). | ||
Wrapping your Future instances with `Par` before passing them to `ap` will | ||
cause them to run in parallel! | ||
\* Have a look at [`pap`](#pap) for an `ap` function that runs its arguments | ||
in parallel. If you must use `ap` (because you're creating a generalized | ||
function), but still want Futures passed into it to run in parallel, then | ||
you could use [ConcurrentFuture](#concurrentfuture) instead. | ||
@@ -1008,2 +1010,19 @@ ```js | ||
#### pap | ||
```hs | ||
pap :: Future a b -> Future a (b -> c) -> Future a c | ||
``` | ||
Has the same signature and function as [`ap`](#ap), but runs the two Futures | ||
given to it in parallel. See also [ConcurrentFuture](#concurrentfuture) for a | ||
more general way to achieve this. | ||
```js | ||
> fork (log ('rejection')) | ||
. (log ('resolution')) | ||
. (pap (resolve (7)) (pap (resolve (49)) (resolve (x => y => x - y)))) | ||
[resolution]: 42 | ||
``` | ||
#### alt | ||
@@ -1306,8 +1325,16 @@ | ||
The `ConcurrentFuture` type is the result of applying | ||
[`concurrify`][concurrify] to `Future`. It provides a mechanism for | ||
constructing a [Fantasy Land `Alternative`][FL:alternative] from a member of | ||
`Future`. This allows Futures to benefit from the Alternative Interface, which | ||
includes parallel `ap`, `zero` and `alt`. | ||
The `ConcurrentFuture` type is very similar to the `Future` type, except that | ||
it has *parallel* semantics where `Future` has *sequential* semantics. | ||
These sematics are most notable in the implementation of Applicative for | ||
`ConcurrentFuture`. When using [`ap`](#ap) on two ConcurrentFutures, they | ||
run parallely, whereas regular `Future` instances would've run sequentially. | ||
This means that `ConcurrentFuture` cannot be a Monad, which is why we have | ||
it as a separate type. | ||
The implementation of Alternative on `ConcurrentFuture` has parallel semantics | ||
as well. Whereas [`alt`](#alt) on regular Futures uses the failure effect to | ||
determine a winner, on ConcurrentFutures *timing* is used, and the winner will | ||
be whichever ConcurrentFuture settled first. | ||
The idea is that we can switch back and forth between `Future` and | ||
@@ -1319,4 +1346,2 @@ `ConcurrentFuture`, using [`Par`](#par) and [`seq`](#seq), to get sequential or | ||
See also [`ap`](#ap) and [`alt`](#alt). | ||
```js | ||
@@ -1603,4 +1628,2 @@ //Some dummy values | ||
[concurrify]: https://github.com/fluture-js/concurrify | ||
[Rollup]: https://rollupjs.org/ | ||
@@ -1607,0 +1630,0 @@ [esm]: https://github.com/standard-things/esm |
@@ -1,18 +0,79 @@ | ||
import concurrify from 'concurrify'; | ||
import type from 'sanctuary-type-identifiers'; | ||
import {Future, never} from './future.js'; | ||
import {parallelAp} from './parallel-ap.js'; | ||
import {race} from './race.js'; | ||
import {FL, namespace, version} from './internal/const.js'; | ||
import {invalidFutureArgument} from './internal/error.js'; | ||
import {captureContext} from './internal/debug.js'; | ||
import {nil} from './internal/list.js'; | ||
function uncurry(f){ | ||
return function(a, b){ | ||
return f(a)(b); | ||
}; | ||
import {never, resolve, isFuture, MapTransformation} from './future.js'; | ||
import {ParallelApTransformation} from './pap.js'; | ||
import {RaceTransformation} from './race.js'; | ||
export function ConcurrentFuture (sequential){ | ||
this.sequential = sequential; | ||
} | ||
export var Par = concurrify(Future, never, uncurry(race), uncurry(parallelAp)); | ||
ConcurrentFuture.prototype = Object.create(Par.prototype); | ||
export function Par (sequential){ | ||
if(!isFuture(sequential)) throw invalidFutureArgument(Par.name, 0, sequential); | ||
return new ConcurrentFuture(sequential); | ||
} | ||
var $$type = namespace + '/ConcurrentFuture@' + version; | ||
var zeroInstance = new ConcurrentFuture(never); | ||
Par['@@type'] = $$type; | ||
Par[FL.of] = function Par$of(x){ | ||
return new ConcurrentFuture(resolve(x)); | ||
}; | ||
Par[FL.zero] = function Par$zero(){ | ||
return zeroInstance; | ||
}; | ||
Par.prototype['@@type'] = $$type; | ||
Par.prototype['@@show'] = function Par$show(){ | ||
return this.toString(); | ||
}; | ||
Par.prototype.toString = function Par$toString(){ | ||
return 'Par (' + this.sequential.toString() + ')'; | ||
}; | ||
Par.prototype[FL.map] = function Par$FL$map(f){ | ||
var context = captureContext( | ||
nil, | ||
'a Fantasy Land dispatch to map via ConcurrentFuture', | ||
Par$FL$map | ||
); | ||
return new ConcurrentFuture(this.sequential._transform(new MapTransformation(context, f))); | ||
}; | ||
Par.prototype[FL.ap] = function Par$FL$ap(other){ | ||
var context = captureContext( | ||
nil, | ||
'a Fantasy Land dispatch to ap via ConcurrentFuture', | ||
Par$FL$ap | ||
); | ||
return new ConcurrentFuture(other.sequential._transform( | ||
new ParallelApTransformation(context, this.sequential) | ||
)); | ||
}; | ||
Par.prototype[FL.alt] = function Par$FL$alt(other){ | ||
var context = captureContext( | ||
nil, | ||
'a Fantasy Land dispatch to alt via ConcurrentFuture', | ||
Par$FL$alt | ||
); | ||
return new ConcurrentFuture(other.sequential._transform( | ||
new RaceTransformation(context, this.sequential) | ||
)); | ||
}; | ||
export function isParallel(x){ | ||
return x instanceof Par || type(x) === Par['@@type']; | ||
return x instanceof ConcurrentFuture || type(x) === $$type; | ||
} |
@@ -51,3 +51,3 @@ import show from 'sanctuary-show'; | ||
inequivalent( | ||
'One Future ' + states[astate] + ', and the other Future' + states[bstate] | ||
'One Future ' + states[astate] + ', and the other Future ' + states[bstate] | ||
); | ||
@@ -54,0 +54,0 @@ } |
Sorry, the diff of this file is not supported yet
182503
2
3515
1633
- Removedconcurrify@^2.0.0
- Removedconcurrify@2.0.0(transitive)