Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add a TypeScript definition file #129

Merged
merged 1 commit into from
Aug 7, 2017
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 2 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -58,7 +58,8 @@ getPackageName('package.json')

### In ES6 or newer environments

The `package.json` sets a `module`-field for build-tools like [Rollup][].
The `package.json` sets a `module`-field for build-tools like [Rollup][]. The
module version also has TypeScript definitions.

```js
import {readFile} from 'fs';
Expand Down
320 changes: 320 additions & 0 deletions index.d.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,320 @@
declare module 'fluture' {

interface RejectFunction<L> {
(error: L): void
}

interface ResolveFunction<R> {
(value: R): void
}

interface Cancel {
(): void
}

interface Nodeback<E, R> {
(err: E | null, value?: R): void
}

interface Next<T> {
done: false
value: T
}

interface Done<T> {
done: true
value: T
}

interface Iterator<N, D> {
next(value?: N): Next<N> | Done<D>
}

interface Generator<Y, R> {
(): Iterator<Y, R>
}
Copy link
Contributor Author

@tusharmath tusharmath Aug 3, 2017

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

isn't Iterator and Generator already available inside lib.es6.d.ts ? Can't we use them instead?

screen shot 2017-08-03 at 10 51 08 pm

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't know. By the looks of that interface, Next<A> and Done<B> must be expressed as one IteratorResult<A|B>. I don't like that because it means we would have to relax the type signature for chainRec.


/** The function is waiting for two more arguments. */
interface AwaitingTwo<A, B, R> {
(a: A, b: B): R
(a: A): (b: B) => R
}

/** The function is waiting for three more arguments. */
interface AwaitingThree<A, B, C, R> {
(a: A, b: B, c: C): R
(a: A, b: B): (c: C) => R
(a: A): AwaitingTwo<B, C, R>
}

export interface ConcurrentFuture<L, R> {
sequential: Future<L, R>
}

export interface Future<L, R> {

/** Logical and for Futures. See https://github.com/fluture-js/Fluture#and */
and<RB>(right: Future<L, RB>): Future<L, RB>

/** Apply the function in this Future to the value in another. See https://github.com/fluture-js/Fluture#ap */
ap<A, B>(this: Future<L, (value: A) => B>, right: Future<L, A>): Future<L, B>

/** Map over both branches of the Future at once. See https://github.com/fluture-js/Fluture#bimap */
bimap<LB, RB>(lmapper: (reason: L) => LB, rmapper: (value: R) => RB): Future<LB, RB>

/** Wait for this Future and the given one in parallel. See https://github.com/fluture-js/Fluture#both */
both<RB>(right: Future<L, RB>): Future<L, [R, RB]>

/** Use the resolution value in this Future to create the next Future. See https://github.com/fluture-js/Fluture#chain */
chain<RB>(mapper: (value: R) => Future<L, RB>): Future<L, RB>

/** Use the rejection reason in this Future to create the next Future. See https://github.com/fluture-js/Fluture#chainrej */
chainRej<LB>(mapper: (reason: L) => Future<LB, R>): Future<LB, R>

/** The Future constructor */
constructor: Fluture

/** Fork the Future into a Node-style callback. See https://github.com/fluture-js/Fluture#done */
done(callback: Nodeback<L, R>): Cancel

/** Set up a cleanup Future to run after this one is done. See https://github.com/fluture-js/Fluture#finally */
finally(cleanup: Future<L, any>): Future<L, R>

/** Fold both branches into the resolution branch. See https://github.com/fluture-js/Fluture#fold */
fold<RB>(lmapper: (reason: L) => RB, rmapper: (value: R) => RB): Future<never, RB>

/** Fork the Future into the two given continuations. See https://github.com/fluture-js/Fluture#fork */
fork(reject: RejectFunction<L>, resolve: ResolveFunction<R>): Cancel

/** Set up a cleanup Future to run after this one is done. See https://github.com/fluture-js/Fluture#finally */
lastly(cleanup: Future<L, any>): Future<L, R>

/** Map over the resolution value in this Future. See https://github.com/fluture-js/Fluture#map */
map<RB>(mapper: (value: R) => RB): Future<L, RB>

/** Map over the rejection reason in this Future. See https://github.com/fluture-js/Fluture#maprej */
mapRej<LB>(mapper: (reason: L) => LB): Future<LB, R>

/** Logical or for Futures. See https://github.com/fluture-js/Fluture#or */
or(right: Future<L, R>): Future<L, R>

/** Fork the Future into a Promise. See https://github.com/fluture-js/Fluture#promise */
promise(): Promise<R>

/** Race this Future against another one. See https://github.com/fluture-js/Fluture#race */
race(right: Future<L, R>): Future<L, R>

/** Swap the rejection reason and the resolotion value. See https://github.com/fluture-js/Fluture#swap */
swap(): Future<R, L>

/** Fork this Future into the given continuation. See https://github.com/fluture-js/Fluture#value */
value(this: Future<never, R>, resolve: ResolveFunction<R>): Cancel

}

/** Creates a Future which resolves after the given duration with the given value. See https://github.com/fluture-js/Fluture#after */
export function after<R>(duration: number, value: R): Future<never, R>
export function after<R>(duration: number): (value: R) => Future<never, R>

/** Logical and for Futures. See https://github.com/fluture-js/Fluture#and */
export function and<L, R>(left: Future<L, any>, right: Future<L, R>): Future<L, R>
export function and<L, R>(left: Future<L, any>): (right: Future<L, R>) => Future<L, R>

/** Apply the function in the left Future to the value in the right Future. See https://github.com/fluture-js/Fluture#ap */
export function ap<L, RA, RB>(apply: Future<L, (value: RA) => RB>, value: Future<L, RA>): Future<L, RB>
export function ap<L, RA, RB>(apply: Future<L, (value: RA) => RB>): (value: Future<L, RA>) => Future<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#try */
export function attempt<L, R>(fn: () => R): Future<L, R>

/** Map over both branched of the given Bifunctor at once. See https://github.com/fluture-js/Fluture#bimap */
export function bimap<LA, LB, RA, RB>(lmapper: (reason: LA) => LB, rmapper: (value: RA) => RB, source: Future<LA, RA>): Future<LB, RB>
export function bimap<LA, LB, RA, RB>(lmapper: (reason: LA) => LB, rmapper: (value: RA) => RB): (source: Future<LA, RA>) => Future<LB, RB>
export function bimap<LA, LB, RA, RB>(lmapper: (reason: LA) => LB): (rmapper: (value: RA) => RB, source: Future<LA, RA>) => Future<LB, RB>
export function bimap<LA, LB, RA, RB>(lmapper: (reason: LA) => LB): (rmapper: (value: RA) => RB) => (source: Future<LA, RA>) => Future<LB, RB>

/** Wait for both Futures to resolve in parallel. See https://github.com/fluture-js/Fluture#both */
export function both<L, A, B>(left: Future<L, A>, right: Future<L, B>): Future<L, [A, B]>
export function both<L, A, B>(left: Future<L, A>): (right: Future<L, B>) => Future<L, [A, B]>

/** Cache the outcome of the given Future. See https://github.com/fluture-js/Fluture#cache */
export function cache<L, R>(source: Future<L, R>): Future<L, R>

/** Create a Future using the resolution value of the given Future. See https://github.com/fluture-js/Fluture#chain */
export function chain<L, RA, RB>(mapper: (value: RA) => Future<L, RB>, source: Future<L, RA>): Future<L, RB>
export function chain<L, RA, RB>(mapper: (value: RA) => Future<L, RB>): (source: Future<L, RA>) => Future<L, RB>

/** Create a Future using the rejection reason of the given Future. See https://github.com/fluture-js/Fluture#chain */
export function chainRej<LA, LB, R>(mapper: (reason: LA) => Future<LA, R>, source: Future<LA, R>): Future<LB, R>
export function chainRej<LA, LB, R>(mapper: (reason: LA) => Future<LA, R>): (source: Future<LA, R>) => Future<LB, R>

/** Fork the given Future into a Node-style callback. See https://github.com/fluture-js/Fluture#done */
export function done<L, R>(callback: Nodeback<L, R>, source: Future<L, R>): Cancel
export function done<L, R>(callback: Nodeback<L, R>): (source: Future<L, R>) => Cancel

/** Encase the given function such that it returns a Future of its return value. See https://github.com/fluture-js/Fluture#encase */
export function encase<L, R, A>(fn: (a: A) => R, a: A): Future<L, R>
export function encase<L, R, A>(fn: (a: A) => R): (a: A) => Future<L, R>

/** Encase the given function such that it returns a Future of its return value. See https://github.com/fluture-js/Fluture#encase */
export function encase2<L, R, A, B>(fn: (a: A, b: B) => R, a: A, b: B): Future<L, R>
export function encase2<L, R, A, B>(fn: (a: A, b: B) => R, a: A): (b: B) => Future<L, R>
export function encase2<L, R, A, B>(fn: (a: A, b: B) => R): AwaitingTwo<A, B, Future<L, R>>

/** Encase the given function such that it returns a Future of its return value. See https://github.com/fluture-js/Fluture#encase */
export function encase3<L, R, A, B, C>(fn: (a: A, b: B, c: C) => R, a: A, b: B, c: C): Future<L, R>
export function encase3<L, R, A, B, C>(fn: (a: A, b: B, c: C) => R, a: A, b: B): (c: C) => Future<L, R>
export function encase3<L, R, A, B, C>(fn: (a: A, b: B, c: C) => R, a: A): AwaitingTwo<B, C, Future<L, R>>
export function encase3<L, R, A, B, C>(fn: (a: A, b: B, c: C) => R): AwaitingThree<A, B, C, Future<L, R>>

/** Encase the given Node-style function such that it returns a Future of its result. See https://github.com/fluture-js/Fluture#encasen */
export function encaseN<L, R, A>(fn: (a: A, callback: Nodeback<L, R>) => void, a: A): Future<L, R>
export function encaseN<L, R, A>(fn: (a: A, callback: Nodeback<L, R>) => void): (a: A) => Future<L, R>

/** Encase the given Node-style function such that it returns a Future of its result. See https://github.com/fluture-js/Fluture#encasen */
export function encaseN2<L, R, A, B>(fn: (a: A, b: B, callback: Nodeback<L, R>) => void, a: A, b: B): Future<L, R>
export function encaseN2<L, R, A, B>(fn: (a: A, b: B, callback: Nodeback<L, R>) => void, a: A): (b: B) => Future<L, R>
export function encaseN2<L, R, A, B>(fn: (a: A, b: B, callback: Nodeback<L, R>) => void): AwaitingTwo<A, B, Future<L, R>>

/** Encase the given Node-style function such that it returns a Future of its result. See https://github.com/fluture-js/Fluture#encasen */
export function encaseN3<L, R, A, B, C>(fn: (a: A, b: B, c: C, callback: Nodeback<L, R>) => void, a: A, b: B, c: C): Future<L, R>
export function encaseN3<L, R, A, B, C>(fn: (a: A, b: B, c: C, callback: Nodeback<L, R>) => void, a: A, b: B): (c: C) => Future<L, R>
export function encaseN3<L, R, A, B, C>(fn: (a: A, b: B, c: C, callback: Nodeback<L, R>) => void, a: A): AwaitingTwo<B, C, Future<L, R>>
export function encaseN3<L, R, A, B, C>(fn: (a: A, b: B, c: C, callback: Nodeback<L, R>) => void): AwaitingThree<A, B, C, Future<L, R>>

/** Encase the given Promise-returning function such that it returns a Future of its resolution value. See https://github.com/fluture-js/Fluture#encasep */
export function encaseP<L, R, A>(fn: (a: A) => Promise<R>, a: A): Future<L, R>
export function encaseP<L, R, A>(fn: (a: A) => Promise<R>): (a: A) => Future<L, R>

/** Encase the given Promise-returning function such that it returns a Future of its resolution value. See https://github.com/fluture-js/Fluture#encasep */
export function encaseP2<L, R, A, B>(fn: (a: A, b: B) => Promise<R>, a: A, b: B): Future<L, R>
export function encaseP2<L, R, A, B>(fn: (a: A, b: B) => Promise<R>, a: A): (b: B) => Future<L, R>
export function encaseP2<L, R, A, B>(fn: (a: A, b: B) => Promise<R>): AwaitingTwo<A, B, Future<L, R>>

/** Encase the given Promise-returning function such that it returns a Future of its resolution value. See https://github.com/fluture-js/Fluture#encasep */
export function encaseP3<L, R, A, B, C>(fn: (a: A, b: B, c: C) => Promise<R>, a: A, b: B, c: C): Future<L, R>
export function encaseP3<L, R, A, B, C>(fn: (a: A, b: B, c: C) => Promise<R>, a: A, b: B): (c: C) => Future<L, R>
export function encaseP3<L, R, A, B, C>(fn: (a: A, b: B, c: C) => Promise<R>, a: A): AwaitingTwo<B, C, Future<L, R>>
export function encaseP3<L, R, A, B, C>(fn: (a: A, b: B, c: C) => Promise<R>): AwaitingThree<A, B, C, Future<L, R>>

/** Extract the rejection reason into an Array if it's present. See https://github.com/fluture-js/Fluture#extractleft */
export function extractLeft<L, R>(source: Future<L, R>): Array<L>

/** Extract the resolution value into an Array if it's present. See https://github.com/fluture-js/Fluture#extractright */
export function extractRight<L, R>(source: Future<L, R>): Array<R>

/** Fold both branches into the resolution branch. See https://github.com/fluture-js/Fluture#fold */
export function fold<LA, RA, RB>(lmapper: (left: LA) => RA, rmapper: (right: RA) => RB, source: Future<LA, RA>): Future<never, RB>
export function fold<LA, RA, RB>(lmapper: (left: LA) => RA, rmapper: (right: RA) => RB): (source: Future<LA, RA>) => Future<never, RB>
export function fold<LA, RA, RB>(lmapper: (left: LA) => RA): AwaitingTwo<(right: RA) => RB, Future<LA, RA>, Future<never, RB>>

/** Fork the given Future into the given continuations. See https://github.com/fluture-js/Fluture#fork */
export function fork<L, R>(reject: RejectFunction<L>, resolve: ResolveFunction<R>, source: Future<L, R>): Cancel
export function fork<L, R>(reject: RejectFunction<L>, resolve: ResolveFunction<R>): (source: Future<L, R>) => Cancel
export function fork<L, R>(reject: RejectFunction<L>): AwaitingTwo<ResolveFunction<R>, Future<L, R>, Cancel>

/** Build a coroutine using Futures. See https://github.com/fluture-js/Fluture#go */
export function go<L, R>(generator: Generator<Future<L, any>, R>): Future<L, R>

/** Manage resources before and after the computation that needs them. See https://github.com/fluture-js/Fluture#hook */
export function hook<L, H, R>(acquire: Future<L, H>, dispose: (handle: H) => Future<L, any>, consume: (handle: H) => Future<L, R>): Future<L, R>
export function hook<L, H, R>(acquire: Future<L, H>, dispose: (handle: H) => Future<L, any>): (consume: (handle: H) => Future<L, R>) => Future<L, R>
export function hook<L, H, R>(acquire: Future<L, H>): AwaitingTwo<(handle: H) => Future<L, any>, (handle: H) => Future<L, R>, Future<L, R>>

/** Returns true for Futures. See https://github.com/fluture-js/Fluture#isfuture */
export function isFuture(value: any): boolean

/** Returns true for Futures that will certainly never settle. See https://github.com/fluture-js/Fluture#isnever */
export function isNever(value: any): boolean

/** Set up a cleanup Future to run after the given action has settled. See https://github.com/fluture-js/Fluture#lastly */
export function lastly<L, R>(cleanup: Future<L, any>, action: Future<L, R>): Future<L, R>
export function lastly<L, R>(cleanup: Future<L, any>): (action: Future<L, R>) => Future<L, R>

/** Map over the resolution value of the given Future. See https://github.com/fluture-js/Fluture#map */
export function map<L, RA, RB>(mapper: (value: RA) => RB, source: Future<L, RA>): Future<L, RB>
export function map<L, RA, RB>(mapper: (value: RA) => RB): (source: Future<L, RA>) => Future<L, RB>

/** Map over the rejection reason of the given Future. See https://github.com/fluture-js/Fluture#maprej */
export function mapRej<LA, LB, R>(mapper: (reason: LA) => LB, source: Future<LA, R>): Future<LB, R>
export function mapRej<LA, LB, R>(mapper: (reason: LA) => LB): (source: Future<LA, R>) => Future<LB, R>

/** A Future that never settles. See https://github.com/fluture-js/Fluture#never */
export const never: Future<never, never>

/** Create a Future using a provided Node-style callback. See https://github.com/fluture-js/Fluture#node */
export function node<L, R>(fn: (done: Nodeback<L, R>) => void): Future<L, R>

/** Create a Future with the given resolution value. See https://github.com/fluture-js/Fluture#of */
export function of<R>(value: R): Future<never, R>

/** Logical or for Futures. See https://github.com/fluture-js/Fluture#or */
export function or<L, R>(left: Future<L, R>, right: Future<L, R>): Future<L, R>
export function or<L, R>(left: Future<L, R>): (right: Future<L, R>) => Future<L, R>

/** Run an Array of Futures in parallel, under the given concurrency limit. See https://github.com/fluture-js/Fluture#parallel */
export function parallel<L, R>(concurrency: number, futures: Array<Future<L, R>>): Future<L, Array<R>>
export function parallel<L, R>(concurrency: number): (futures: Array<Future<L, R>>) => Future<L, Array<R>>

/** Convert a Future to a Promise. See https://github.com/fluture-js/Fluture#promise */
export function promise<R>(source: Future<any, R>): Promise<R>

/** Race two Futures against one another. See https://github.com/fluture-js/Fluture#race */
export function race<L, R>(left: Future<L, R>, right: Future<L, R>): Future<L, R>
export function race<L, R>(left: Future<L, R>): (right: Future<L, R>) => Future<L, R>

/** Create a Future with the given rejection reason. See https://github.com/fluture-js/Fluture#reject */
export function reject<L>(reason: L): Future<L, never>

/** Creates a Future which rejects after the given duration with the given reason. See https://github.com/fluture-js/Fluture#rejectafter */
export function rejectAfter<L>(duration: number, reason: L): Future<L, never>
export function rejectAfter<L>(duration: number): (reason: L) => Future<L, never>

/** Convert a ConcurrentFuture to a regular Future. See https://github.com/fluture-js/Fluture#concurrentfuture */
export function seq<L, R>(source: ConcurrentFuture<L, R>): Future<L, R>

/** Swap the rejection reason and the resolution value. See https://github.com/fluture-js/Fluture#swap */
export function swap<L, R>(source: Future<L, R>): Future<R, L>

/** Convert a Promise-returning function to a Future. See https://github.com/fluture-js/Fluture#tryP */
export function tryP<L, R>(fn: () => Promise<R>): Future<L, R>

/** Fork the Future into the given continuation. See https://github.com/fluture-js/Fluture#value */
export function value<R>(resolve: ResolveFunction<R>, source: Future<never, R>): Cancel
export function value<R>(resolve: ResolveFunction<R>): (source: Future<never, R>) => Cancel

export interface Fluture {

/** Create a Future from a possibly cancellable computation. See https://github.com/fluture-js/Fluture#future */
<L, R>(computation: (
reject: RejectFunction<L>,
resolve: ResolveFunction<R>
) => Cancel | void): Future<L, R>

/** Create a Future from a possibly cancellable computation. See https://github.com/fluture-js/Fluture#future */
new <L, R>(computation: (
reject: RejectFunction<L>,
resolve: ResolveFunction<R>
) => Cancel | void): Future<L, R>

/** Implementation of Fantasy Land ChainRec. */
chainRec<L, I, R>(iterator: (next: (value: I) => Next<I>, done: (value: R) => Done<R>, value: I) => Future<L, Next<I> | Done<R>>, initial: I): Future<L, R>

ap: typeof ap
bimap: typeof bimap
chain: typeof chain
map: typeof map
of: typeof of
reject: typeof reject

'@@type': string

}

export const Future: Fluture
export default Fluture

/** Create a ConcurrentFuture using a Future. See https://github.com/fluture-js/Fluture#concurrentfuture */
export function Par<L, R>(source: Future<L, R>): ConcurrentFuture<L, R>

}
4 changes: 3 additions & 1 deletion package.json
Original file line number Diff line number Diff line change
Expand Up @@ -3,10 +3,12 @@
"version": "6.3.0",
"description": "FantasyLand compliant (monadic) alternative to Promises",
"main": "index.js",
"types": "index.d.ts",
"module": "index.es.js",
"files": [
"src",
"index.es.js"
"index.es.js",
"index.d.ts"
],
"repository": "https://github.com/fluture-js/Fluture.git",
"scripts": {
Expand Down