Skip to content

Commit 6e1afab

Browse files
committed
Add branch awareness and tests for the type of 'and'
1 parent 7072818 commit 6e1afab

File tree

2 files changed

+45
-1
lines changed

2 files changed

+45
-1
lines changed

index.d.ts

+11-1
Original file line numberDiff line numberDiff line change
@@ -83,7 +83,17 @@ export interface FutureInstance<L, R> extends Functor<R> {
8383
export function after(duration: number): <R>(value: R) => Resolved<R>
8484

8585
/** Logical and for Futures. See https://github.com/fluture-js/Fluture#and */
86-
export function and<L, R>(left: FutureInstance<L, R>): (right: FutureInstance<L, any>) => FutureInstance<L, R>
86+
export const and: {
87+
<F extends AnyFuture, S extends AnyFuture>(second: F extends Never ? S : never): (first: F) => Never
88+
<F extends AnyFuture, S extends AnyFuture>(second: F extends Resolved<unknown> ? S : never): (first: F) => S
89+
<F extends AnyFuture, S extends AnyFuture>(second: F extends Rejected<unknown> ? S : never): (first: F) => F
90+
91+
<L, R>(second: Uncertain<L, R>): {
92+
<T>(first: Rejected<T>): Rejected<T>
93+
(first: Resolved<any>): Uncertain<L, R>
94+
(first: Uncertain<L, any>): Uncertain<L, R>
95+
}
96+
}
8797

8898
/** Logical or for Futures. See https://github.com/fluture-js/Fluture#alt */
8999
export const alt: {

test/types/and.test-d.ts

+34
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,34 @@
1+
import {expectType, expectError} from 'tsd';
2+
3+
import * as fl from '../../index.js';
4+
5+
const fsn: fl.Uncertain<string, number> = fl.resolve (42);
6+
const fns: fl.Uncertain<number, string> = fl.resolve ('a');
7+
8+
// Standard usage on Future instances.
9+
expectType<fl.Never> (fl.and (fl.never) (fl.never));
10+
expectType<fl.Never> (fl.and (fl.never) (fl.resolve ('a')));
11+
expectType<fl.Never> (fl.and (fl.reject ('a')) (fl.never));
12+
expectType<fl.Never> (fl.and (fl.resolve ('a')) (fl.never));
13+
expectType<fl.Rejected<string>> (fl.and (fl.reject ('a')) (fl.resolve (42)));
14+
expectType<fl.Resolved<number>> (fl.and (fl.resolve (42)) (fl.resolve (42)));
15+
expectType<fl.Rejected<number>> (fl.and (fl.reject (42)) (fl.reject (42)));
16+
expectType<fl.Uncertain<string, number>> (fl.and (fsn) (fsn));
17+
expectType<fl.Rejected<string>> (fl.and (fl.never) (fl.reject ('a')));
18+
expectType<fl.Rejected<string>> (fl.and (fl.resolve (42)) (fl.reject ('a')));
19+
expectType<fl.Rejected<number>> (fl.and (fl.reject ('a')) (fl.reject (42)));
20+
expectError (fl.and (fsn) (fns));
21+
22+
// Usage with pipe on Future instances (https://git.io/JLx3F).
23+
expectType<fl.Never> ((fl.never) .pipe (fl.and (fl.never)));
24+
const workaround = (fl.resolve ('a')) .pipe (fl.and (fl.never)); expectType<fl.Never> (workaround);
25+
expectType<fl.Never> ((fl.never) .pipe (fl.and (fl.reject ('a'))));
26+
expectType<fl.Never> ((fl.never) .pipe (fl.and (fl.resolve ('a'))));
27+
expectType<fl.Rejected<string>> ((fl.resolve (42)) .pipe (fl.and (fl.reject ('a'))));
28+
expectType<fl.Resolved<number>> ((fl.resolve (42)) .pipe (fl.and (fl.resolve (42))));
29+
expectType<fl.Rejected<number>> ((fl.reject (42)) .pipe (fl.and (fl.reject (42))));
30+
expectType<fl.Uncertain<string, number>> ((fsn) .pipe (fl.and (fsn)));
31+
expectType<fl.Rejected<string>> ((fl.reject ('a')) .pipe (fl.and (fl.never)));
32+
expectType<fl.Rejected<string>> ((fl.reject ('a')) .pipe (fl.and (fl.resolve (42))));
33+
expectType<fl.Rejected<number>> ((fl.reject (42)) .pipe (fl.and (fl.reject ('a'))));
34+
expectError ((fns) .pipe (fl.and (fsn)));

0 commit comments

Comments
 (0)