@typed/guard 0.7.2 → 1.0.0-beta.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +98 -0
- package/dist/index.d.ts +247 -3
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +176 -4
- package/dist/index.test.d.ts +2 -0
- package/dist/index.test.d.ts.map +1 -0
- package/dist/index.test.js +314 -0
- package/package.json +18 -24
- package/src/index.test.ts +370 -0
- package/src/index.ts +661 -3
- package/tsconfig.json +4 -26
- package/.nvmrc +0 -1
- package/biome.json +0 -36
- package/dist/ExtensibleFunction.d.ts +0 -1
- package/dist/ExtensibleFunction.js +0 -7
- package/dist/ExtensibleFunction.js.map +0 -1
- package/dist/Guard.d.ts +0 -143
- package/dist/Guard.js +0 -95
- package/dist/Guard.js.map +0 -1
- package/dist/Guardable.d.ts +0 -10
- package/dist/Guardable.js +0 -13
- package/dist/Guardable.js.map +0 -1
- package/dist/index.js.map +0 -1
- package/readme.md +0 -199
- package/src/ExtensibleFunction.test.ts +0 -102
- package/src/ExtensibleFunction.ts +0 -8
- package/src/Guard.test.ts +0 -189
- package/src/Guard.ts +0 -536
- package/src/Guardable.test.ts +0 -18
- package/src/Guardable.ts +0 -22
package/biome.json
DELETED
|
@@ -1,36 +0,0 @@
|
|
|
1
|
-
{
|
|
2
|
-
"organizeImports": {
|
|
3
|
-
"enabled": true
|
|
4
|
-
},
|
|
5
|
-
"linter": {
|
|
6
|
-
"enabled": true,
|
|
7
|
-
"rules": {
|
|
8
|
-
"recommended": true,
|
|
9
|
-
"suspicious": {
|
|
10
|
-
"noExplicitAny": "off",
|
|
11
|
-
"noAssignInExpressions": "off",
|
|
12
|
-
"noShadowRestrictedNames": "off"
|
|
13
|
-
},
|
|
14
|
-
"style": {
|
|
15
|
-
"noParameterAssign": "off",
|
|
16
|
-
"noUselessElse": "off"
|
|
17
|
-
},
|
|
18
|
-
"complexity": {
|
|
19
|
-
"noBannedTypes": "off"
|
|
20
|
-
}
|
|
21
|
-
}
|
|
22
|
-
},
|
|
23
|
-
"formatter": {
|
|
24
|
-
"enabled": true,
|
|
25
|
-
"indentStyle": "space",
|
|
26
|
-
"indentWidth": 2,
|
|
27
|
-
"lineWidth": 100
|
|
28
|
-
},
|
|
29
|
-
"javascript": {
|
|
30
|
-
"formatter": {
|
|
31
|
-
"quoteStyle": "single",
|
|
32
|
-
"trailingCommas": "all",
|
|
33
|
-
"semicolons": "asNeeded"
|
|
34
|
-
}
|
|
35
|
-
}
|
|
36
|
-
}
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
export declare const ExtensibleFunction: new <F extends (...inputs: readonly any[]) => any>(f: F) => F;
|
|
@@ -1,7 +0,0 @@
|
|
|
1
|
-
function Extensible(f) {
|
|
2
|
-
return Object.setPrototypeOf(f, new.target.prototype);
|
|
3
|
-
}
|
|
4
|
-
Extensible.prototype = Function.prototype;
|
|
5
|
-
// Hack to make the type inference work
|
|
6
|
-
export const ExtensibleFunction = Extensible;
|
|
7
|
-
//# sourceMappingURL=ExtensibleFunction.js.map
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"ExtensibleFunction.js","sourceRoot":"","sources":["../src/ExtensibleFunction.ts"],"names":[],"mappings":"AAAA,SAAS,UAAU,CAAO,CAAkB;IAC1C,OAAO,MAAM,CAAC,cAAc,CAAC,CAAC,EAAE,GAAG,CAAC,MAAM,CAAC,SAAS,CAAC,CAAA;AACvD,CAAC;AACD,UAAU,CAAC,SAAS,GAAG,QAAQ,CAAC,SAAS,CAAA;AAEzC,uCAAuC;AACvC,MAAM,CAAC,MAAM,kBAAkB,GAC7B,UAAiB,CAAA"}
|
package/dist/Guard.d.ts
DELETED
|
@@ -1,143 +0,0 @@
|
|
|
1
|
-
import { type Cause, type Context, Effect, type Layer, Option, Pipeable, type Predicate, type Runtime, Schema } from 'effect';
|
|
2
|
-
export type Guard<I, O = never, E = never, R = never> = (input: I) => Effect.Effect<Option.Option<O>, E, R>;
|
|
3
|
-
export declare namespace Guard {
|
|
4
|
-
type Input<T> = [T] extends [Guard<infer I, infer _R, infer _E, infer _O>] ? I : never;
|
|
5
|
-
type Output<T> = [T] extends [Guard<infer _I, infer O, infer _E, infer _R>] ? O : never;
|
|
6
|
-
type Error<T> = [T] extends [Guard<infer _I, infer _O, infer E, infer _R>] ? E : never;
|
|
7
|
-
type Context<T> = [T] extends [Guard<infer _I, infer _O, infer _E, infer R>] ? R : never;
|
|
8
|
-
}
|
|
9
|
-
export declare const identity: <A>(a: A) => Effect.Effect<Option.Option<A>>;
|
|
10
|
-
export declare const compose: {
|
|
11
|
-
<O, B, E2, R2>(output: Guard<O, B, E2, R2>): <I, R, E>(input: Guard<I, O, E, R>) => Guard<I, B, E | E2, R | R2>;
|
|
12
|
-
<I, O, E, R, B, E2, R2>(input: Guard<I, O, E, R>, output: Guard<O, B, E2, R2>): Guard<I, B, E | E2, R | R2>;
|
|
13
|
-
};
|
|
14
|
-
export declare const mapEffect: {
|
|
15
|
-
<O, B, E2, R2>(f: (o: O) => Effect.Effect<B, E2, R2>): <I, R, E>(guard: Guard<I, O, E, R>) => Guard<I, B, E | E2, R | R2>;
|
|
16
|
-
<I, O, E, R, B, E2, R2>(guard: Guard<I, O, E, R>, f: (o: O) => Effect.Effect<B, E2, R2>): Guard<I, B, E | E2, R | R2>;
|
|
17
|
-
};
|
|
18
|
-
export declare const map: {
|
|
19
|
-
<O, B>(f: (o: O) => B): <I, R, E>(guard: Guard<I, O, E, R>) => Guard<I, B, E, R>;
|
|
20
|
-
<I, O, E, R, B>(guard: Guard<I, O, E, R>, f: (o: O) => B): Guard<I, B, E, R>;
|
|
21
|
-
};
|
|
22
|
-
export declare const tap: {
|
|
23
|
-
<O, B, E2, R2>(f: (o: O) => Effect.Effect<B, E2, R2>): <I, R, E>(guard: Guard<I, O, E, R>) => Guard<I, O, E | E2, R | R2>;
|
|
24
|
-
<I, O, E, R, B, E2, R2>(guard: Guard<I, O, E, R>, f: (o: O) => Effect.Effect<B, E2, R2>): Guard<I, O, E | E2, R | R2>;
|
|
25
|
-
};
|
|
26
|
-
export declare const filterMap: {
|
|
27
|
-
<O, B>(f: (o: O) => Option.Option<B>): <I, R, E>(guard: Guard<I, O, E, R>) => Guard<I, B, E, R>;
|
|
28
|
-
<I, O, E, R, B>(guard: Guard<I, O, E, R>, f: (o: O) => Option.Option<B>): Guard<I, B, E, R>;
|
|
29
|
-
};
|
|
30
|
-
export declare const filter: {
|
|
31
|
-
<O, O2 extends O>(predicate: (o: O) => o is O2): <I, R, E>(guard: Guard<I, O, E, R>) => Guard<I, O, E, R>;
|
|
32
|
-
<O>(predicate: (o: O) => boolean): <I, R, E>(guard: Guard<I, O, E, R>) => Guard<I, O, E, R>;
|
|
33
|
-
<I, O, E, R, O2 extends O>(guard: Guard<I, O, E, R>, predicate: (o: O) => o is O2): Guard<I, O, E, R>;
|
|
34
|
-
<I, O, E, R>(guard: Guard<I, O, E, R>, predicate: (o: O) => boolean): Guard<I, O, E, R>;
|
|
35
|
-
};
|
|
36
|
-
export declare function any<const GS extends Readonly<Record<string, Guard<any, any, any, any>>>>(guards: GS): Guard<AnyInput<GS>, AnyOutput<GS>, Guard.Error<GS[keyof GS]>, Guard.Context<GS[keyof GS]>>;
|
|
37
|
-
export type AnyInput<GS extends Readonly<Record<string, Guard<any, any, any, any>>>> = Guard.Input<GS[keyof GS]>;
|
|
38
|
-
export type AnyOutput<GS extends Readonly<Record<string, Guard<any, any, any, any>>>> = [
|
|
39
|
-
{
|
|
40
|
-
[K in keyof GS]: {
|
|
41
|
-
readonly _tag: K;
|
|
42
|
-
readonly value: Guard.Output<GS[K]>;
|
|
43
|
-
};
|
|
44
|
-
}[keyof GS]
|
|
45
|
-
] extends [infer R] ? R : never;
|
|
46
|
-
export declare function liftPredicate<A, B extends A>(predicate: Predicate.Refinement<A, B>): Guard<A, B>;
|
|
47
|
-
export declare function liftPredicate<A>(predicate: Predicate.Predicate<A>): Guard<A, A>;
|
|
48
|
-
export declare const catchAllCause: {
|
|
49
|
-
<E = never, O2 = never, E2 = never, R2 = never>(f: (e: Cause.Cause<E>) => Effect.Effect<O2, E2, R2>): <I = never, O = never, R = never>(guard: Guard<I, O, E, R>) => Guard<I, O | O2, E2, R | R2>;
|
|
50
|
-
<I = never, O = never, E = never, R = never, O2 = never, E2 = never, R2 = never>(guard: Guard<I, O, E, R>, f: (e: Cause.Cause<E>) => Effect.Effect<O2, E2, R2>): Guard<I, O | O2, E2, R | R2>;
|
|
51
|
-
};
|
|
52
|
-
export declare const catchAll: {
|
|
53
|
-
<E = never, O2 = never, E2 = never, R2 = never>(f: (e: E) => Effect.Effect<O2, E2, R2>): <I = never, O = never, R = never>(guard: Guard<I, O, E, R>) => Guard<I, O | O2, E2, R | R2>;
|
|
54
|
-
<I = never, O = never, E = never, R = never, O2 = never, E2 = never, R2 = never>(guard: Guard<I, O, E, R>, f: (e: E) => Effect.Effect<O2, E2, R2>): Guard<I, O | O2, E2, R | R2>;
|
|
55
|
-
};
|
|
56
|
-
export declare const catchTag: {
|
|
57
|
-
<E = never, K extends E extends {
|
|
58
|
-
_tag: string;
|
|
59
|
-
} ? E['_tag'] : never = never, O2 = never, E2 = never, R2 = never>(tag: K, f: (e: Extract<E, {
|
|
60
|
-
_tag: K;
|
|
61
|
-
}>) => Effect.Effect<O2, E2, R2>): <I = never, O = never, R = never>(guard: Guard<I, O, E, R>) => Guard<I, O | O2, E2 | Exclude<E, {
|
|
62
|
-
_tag: K;
|
|
63
|
-
}>, R | R2>;
|
|
64
|
-
<I = never, O = never, E = never, R = never, K extends E extends {
|
|
65
|
-
_tag: string;
|
|
66
|
-
} ? E['_tag'] : never = never, O2 = never, E2 = never, R2 = never>(guard: Guard<I, O, E, R>, tag: K, f: (e: Extract<E, {
|
|
67
|
-
_tag: K;
|
|
68
|
-
}>) => Effect.Effect<O2, E2, R2>): Guard<I, O | O2, E2 | Exclude<E, {
|
|
69
|
-
_tag: K;
|
|
70
|
-
}>, R | R2>;
|
|
71
|
-
};
|
|
72
|
-
export declare const provide: {
|
|
73
|
-
<R2>(provided: Context.Context<R2>): <I, O, E, R>(guard: Guard<I, O, E, R>) => Guard<I, O, E, Exclude<R, R2>>;
|
|
74
|
-
<R2>(provided: Runtime.Runtime<R2>): <I, O, E, R>(guard: Guard<I, O, E, R>) => Guard<I, O, E, Exclude<R, R2>>;
|
|
75
|
-
<R2, E2, R3>(provided: Layer.Layer<R2, E2, R3>): <I, O, E, R>(guard: Guard<I, O, E, R>) => Guard<I, O, E | E2, Exclude<R, R2> | R3>;
|
|
76
|
-
<I, O, E, R, R2>(guard: Guard<I, O, E, R>, provided: Context.Context<R2>): Guard<I, O, E, Exclude<R, R2>>;
|
|
77
|
-
<I, O, E, R, R2>(guard: Guard<I, O, E, R>, provided: Runtime.Runtime<R2>): Guard<I, O, E, Exclude<R, R2>>;
|
|
78
|
-
<I, O, E, R, R2, E2, R3>(guard: Guard<I, O, E, R>, provided: Layer.Layer<R2, E2, R3>): Guard<I, O, E | E2, Exclude<R, R2> | R3>;
|
|
79
|
-
};
|
|
80
|
-
export declare const provideService: {
|
|
81
|
-
<Id, S>(tag: Context.Tag<Id, S>, service: S): <I, O, E, R>(guard: Guard<I, O, E, R>) => Guard<I, O, E, Exclude<R, Id>>;
|
|
82
|
-
<I, O, E, R, Id, S>(guard: Guard<I, O, E, R>, tag: Context.Tag<Id, S>, service: S): Guard<I, O, E, Exclude<R, Id>>;
|
|
83
|
-
};
|
|
84
|
-
export declare const provideServiceEffect: {
|
|
85
|
-
<Id, S, E2, R2>(tag: Context.Tag<Id, S>, service: Effect.Effect<S, E2, R2>): <I, O, E, R>(guard: Guard<I, O, E, R>) => Guard<I, O, E | E2, Exclude<R, Id> | R2>;
|
|
86
|
-
<I, O, E, R, Id, S, E2, R2>(guard: Guard<I, O, E, R>, tag: Context.Tag<Id, S>, service: Effect.Effect<S, E2, R2>): Guard<I, O, E | E2, Exclude<R, Id> | R2>;
|
|
87
|
-
};
|
|
88
|
-
export declare function fromSchemaDecode<A, I, R>(schema: Schema.Schema<A, I, R>): Guard<I, A, never, R>;
|
|
89
|
-
export declare function fromSchemaDecodeUnknown<A, I, R>(schema: Schema.Schema<A, I, R>): Guard<unknown, A, never, R>;
|
|
90
|
-
export declare function fromSchemaEncode<A, I, R>(schema: Schema.Schema<A, I, R>): Guard<A, I, never, R>;
|
|
91
|
-
export declare const decode: {
|
|
92
|
-
<A, O, R2>(schema: Schema.Schema<A, O, R2>): <I, E = never, R = never>(guard: Guard<I, O, E, R>) => Guard<I, A, E, R | R2>;
|
|
93
|
-
<I, O, E, R, A, R2>(guard: Guard<I, O, E, R>, schema: Schema.Schema<A, O, R2>): Guard<I, A, E, R | R2>;
|
|
94
|
-
};
|
|
95
|
-
export declare const encode: {
|
|
96
|
-
<O, A, R2>(schema: Schema.Schema<O, A, R2>): <I, E = never, R = never>(guard: Guard<I, O, E, R>) => Guard<I, A, E, R | R2>;
|
|
97
|
-
<I, O, E, R, A, R2>(guard: Guard<I, O, E, R>, schema: Schema.Schema<O, A, R2>): Guard<I, A, E, R | R2>;
|
|
98
|
-
};
|
|
99
|
-
declare const let_: {
|
|
100
|
-
<O, K extends PropertyKey, B>(key: K, value: (o: O) => B): <I, E = never, R = never>(guard: Guard<I, O, E, R>) => Guard<I, O & {
|
|
101
|
-
[k in K]: B;
|
|
102
|
-
}, E, R>;
|
|
103
|
-
<I, O, E, R, K extends PropertyKey, B>(guard: Guard<I, O, E, R>, key: K, value: (o: O) => B): Guard<I, O & {
|
|
104
|
-
[k in K]: B;
|
|
105
|
-
}, E, R>;
|
|
106
|
-
};
|
|
107
|
-
export { let_ as let };
|
|
108
|
-
export declare const attachProperty: {
|
|
109
|
-
<K extends PropertyKey, B>(key: K, value: B): <I, O, E, R>(guard: Guard<I, O, E, R>) => Guard<I, O & {
|
|
110
|
-
readonly [k in K]: B;
|
|
111
|
-
}, E, R>;
|
|
112
|
-
<I, O, E, R, K extends PropertyKey, B>(guard: Guard<I, O, E, R>, key: K, value: B): Guard<I, O & {
|
|
113
|
-
readonly [k in K]: B;
|
|
114
|
-
}, E, R>;
|
|
115
|
-
};
|
|
116
|
-
export declare const addTag: {
|
|
117
|
-
<B>(value: B): <I, O, E = never, R = never>(guard: Guard<I, O, E, R>) => Guard<I, O & {
|
|
118
|
-
readonly _tag: B;
|
|
119
|
-
}, E, R>;
|
|
120
|
-
<I, O, E, R, B>(guard: Guard<I, O, E, R>, value: B): Guard<I, O & {
|
|
121
|
-
readonly _tag: B;
|
|
122
|
-
}, E, R>;
|
|
123
|
-
};
|
|
124
|
-
export declare const bindTo: {
|
|
125
|
-
<K extends PropertyKey>(key: K): <I, O, E, R>(guard: Guard<I, O, E, R>) => Guard<I, {
|
|
126
|
-
[k in K]: O;
|
|
127
|
-
}, E, R>;
|
|
128
|
-
<I, O, E, R, K extends PropertyKey>(guard: Guard<I, O, E, R>, key: K): Guard<I, {
|
|
129
|
-
[k in K]: O;
|
|
130
|
-
}, E, R>;
|
|
131
|
-
};
|
|
132
|
-
export declare const bind: {
|
|
133
|
-
<I, O, E, R, K extends PropertyKey, B, E2, R2>(key: K, f: Guard<O, B, E2, R2>): (guard: Guard<I, O, E, R>) => Guard<I, O & {
|
|
134
|
-
[k in K]: B;
|
|
135
|
-
}, E | E2, R | R2>;
|
|
136
|
-
<I, O, E, R, K extends PropertyKey, B, E2, R2>(guard: Guard<I, O, E, R>, key: K, f: Guard<O, B, E2, R2>): Guard<I, O & {
|
|
137
|
-
[k in K]: B;
|
|
138
|
-
}, E | E2, R | R2>;
|
|
139
|
-
};
|
|
140
|
-
declare global {
|
|
141
|
-
interface Function extends Pipeable.Pipeable {
|
|
142
|
-
}
|
|
143
|
-
}
|
package/dist/Guard.js
DELETED
|
@@ -1,95 +0,0 @@
|
|
|
1
|
-
import { Effect, Option, Pipeable, Schema, } from 'effect';
|
|
2
|
-
import { dual } from 'effect/Function';
|
|
3
|
-
export const identity = Effect.succeedSome;
|
|
4
|
-
export const compose = dual(2, function flatMap(input, output) {
|
|
5
|
-
return (i) => Effect.flatMap(input(i), Option.match({
|
|
6
|
-
onNone: () => Effect.succeedNone,
|
|
7
|
-
onSome: output,
|
|
8
|
-
}));
|
|
9
|
-
});
|
|
10
|
-
export const mapEffect = dual(2, function mapEffect(guard, f) {
|
|
11
|
-
return compose(guard, (o) => Effect.asSome(f(o)));
|
|
12
|
-
});
|
|
13
|
-
export const map = dual(2, function map(guard, f) {
|
|
14
|
-
return mapEffect(guard, (o) => Effect.sync(() => f(o)));
|
|
15
|
-
});
|
|
16
|
-
export const tap = dual(2, function tap(guard, f) {
|
|
17
|
-
return compose(guard, (o) => Effect.as(f(o), Option.some(o)));
|
|
18
|
-
});
|
|
19
|
-
export const filterMap = dual(2, (guard, f) => {
|
|
20
|
-
return (i) => Effect.map(guard(i), Option.filterMap(f));
|
|
21
|
-
});
|
|
22
|
-
export const filter = dual(2, (guard, predicate) => {
|
|
23
|
-
return (i) => Effect.map(guard(i), Option.filter(predicate));
|
|
24
|
-
});
|
|
25
|
-
export function any(guards) {
|
|
26
|
-
return (i) => Effect.gen(function* () {
|
|
27
|
-
for (const [_tag, guard] of Object.entries(guards)) {
|
|
28
|
-
const match = yield* guard(i);
|
|
29
|
-
if (Option.isSome(match)) {
|
|
30
|
-
return Option.some({ _tag, value: match.value });
|
|
31
|
-
}
|
|
32
|
-
}
|
|
33
|
-
return Option.none();
|
|
34
|
-
});
|
|
35
|
-
}
|
|
36
|
-
export function liftPredicate(predicate) {
|
|
37
|
-
return (a) => Effect.sync(() => (predicate(a) ? Option.some(a) : Option.none()));
|
|
38
|
-
}
|
|
39
|
-
export const catchAllCause = dual(2, function catchAllCause(guard, f) {
|
|
40
|
-
return (i) => Effect.catchAllCause(guard(i), (a) => Effect.asSome(f(a)));
|
|
41
|
-
});
|
|
42
|
-
export const catchAll = dual(2, function catchAll(guard, f) {
|
|
43
|
-
return (i) => Effect.catchAll(guard(i), (a) => Effect.asSome(f(a)));
|
|
44
|
-
});
|
|
45
|
-
export const catchTag = dual(3, function catchTag(guard, tag, f) {
|
|
46
|
-
return (i) => Effect.catchTag(guard(i), tag, (e) => Effect.asSome(f(e)));
|
|
47
|
-
});
|
|
48
|
-
export const provide = dual(2, function provide(guard, provided) {
|
|
49
|
-
return (i) => Effect.provide(guard(i), provided);
|
|
50
|
-
});
|
|
51
|
-
export const provideService = dual(3, function provideService(guard, tag, service) {
|
|
52
|
-
return (i) => Effect.provideService(guard(i), tag, service);
|
|
53
|
-
});
|
|
54
|
-
export const provideServiceEffect = dual(3, function provideServiceEffect(guard, tag, service) {
|
|
55
|
-
return (i) => Effect.provideServiceEffect(guard(i), tag, service);
|
|
56
|
-
});
|
|
57
|
-
const parseOptions = { errors: 'all', onExcessProperty: 'ignore' };
|
|
58
|
-
export function fromSchemaDecode(schema) {
|
|
59
|
-
const decode_ = Schema.decode(schema);
|
|
60
|
-
return (i) => decode_(i, parseOptions).pipe(Effect.asSome, Effect.catchTag('ParseError', (e) => Effect.succeedNone));
|
|
61
|
-
}
|
|
62
|
-
export function fromSchemaDecodeUnknown(schema) {
|
|
63
|
-
const decode_ = Schema.decodeUnknown(schema);
|
|
64
|
-
return (i) => decode_(i, parseOptions).pipe(Effect.asSome, Effect.catchTag('ParseError', () => Effect.succeedNone));
|
|
65
|
-
}
|
|
66
|
-
export function fromSchemaEncode(schema) {
|
|
67
|
-
const encode_ = Schema.encode(schema);
|
|
68
|
-
return (a) => encode_(a, parseOptions).pipe(Effect.asSome, Effect.catchTag('ParseError', () => Effect.succeedNone));
|
|
69
|
-
}
|
|
70
|
-
export const decode = dual(2, function decode(guard, schema) {
|
|
71
|
-
return compose(guard, fromSchemaDecode(schema));
|
|
72
|
-
});
|
|
73
|
-
export const encode = dual(2, function encode(guard, schema) {
|
|
74
|
-
return compose(guard, fromSchemaEncode(schema));
|
|
75
|
-
});
|
|
76
|
-
const let_ = dual(3, function let_(guard, key, value) {
|
|
77
|
-
return map(guard, (a) => ({ ...a, [key]: value(a) }));
|
|
78
|
-
});
|
|
79
|
-
export { let_ as let };
|
|
80
|
-
export const attachProperty = dual(3, function attachProperty(guard, key, value) {
|
|
81
|
-
return map(guard, (a) => ({ ...a, [key]: value }));
|
|
82
|
-
});
|
|
83
|
-
export const addTag = dual(2, function addTag(guard, value) {
|
|
84
|
-
return map(guard, (a) => ({ ...a, _tag: value }));
|
|
85
|
-
});
|
|
86
|
-
export const bindTo = dual(2, (guard, key) => map(guard, (a) => ({ [key]: a })));
|
|
87
|
-
export const bind = dual(3, function bind(guard, key, f) {
|
|
88
|
-
const f_ = bindTo(f, key);
|
|
89
|
-
return compose(guard, (o) => Effect.map(f_(o), Option.map((b) => ({ ...o, ...b }))));
|
|
90
|
-
});
|
|
91
|
-
Function.prototype.pipe = function pipe() {
|
|
92
|
-
// biome-ignore lint/style/noArguments: This is a pipeable function
|
|
93
|
-
return Pipeable.pipeArguments(this, arguments);
|
|
94
|
-
};
|
|
95
|
-
//# sourceMappingURL=Guard.js.map
|
package/dist/Guard.js.map
DELETED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"Guard.js","sourceRoot":"","sources":["../src/Guard.ts"],"names":[],"mappings":"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"}
|
package/dist/Guardable.d.ts
DELETED
|
@@ -1,10 +0,0 @@
|
|
|
1
|
-
import { Pipeable } from 'effect';
|
|
2
|
-
import { ExtensibleFunction } from './ExtensibleFunction.js';
|
|
3
|
-
import type { Guard } from './Guard.js';
|
|
4
|
-
export declare const GUARDABLE: unique symbol;
|
|
5
|
-
export type GUARDABLE = typeof GUARDABLE;
|
|
6
|
-
export declare abstract class Guardable<I, O, E = never, R = never> extends ExtensibleFunction<Guard<I, O, E, R>> implements Pipeable.Pipeable {
|
|
7
|
-
constructor();
|
|
8
|
-
abstract readonly [GUARDABLE]: Guard<I, O, E, R>;
|
|
9
|
-
pipe(): unknown;
|
|
10
|
-
}
|
package/dist/Guardable.js
DELETED
|
@@ -1,13 +0,0 @@
|
|
|
1
|
-
import { Pipeable } from 'effect';
|
|
2
|
-
import { ExtensibleFunction } from './ExtensibleFunction.js';
|
|
3
|
-
export const GUARDABLE = Symbol.for('@typed/guard/Guardable');
|
|
4
|
-
export class Guardable extends ExtensibleFunction {
|
|
5
|
-
constructor() {
|
|
6
|
-
super((input) => this[GUARDABLE](input));
|
|
7
|
-
}
|
|
8
|
-
pipe() {
|
|
9
|
-
// biome-ignore lint/style/noArguments: This is a pipeable function
|
|
10
|
-
return Pipeable.pipeArguments(this, arguments);
|
|
11
|
-
}
|
|
12
|
-
}
|
|
13
|
-
//# sourceMappingURL=Guardable.js.map
|
package/dist/Guardable.js.map
DELETED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"Guardable.js","sourceRoot":"","sources":["../src/Guardable.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,MAAM,QAAQ,CAAA;AACjC,OAAO,EAAE,kBAAkB,EAAE,MAAM,yBAAyB,CAAA;AAG5D,MAAM,CAAC,MAAM,SAAS,GAAG,MAAM,CAAC,GAAG,CAAC,wBAAwB,CAAC,CAAA;AAG7D,MAAM,OAAgB,SACpB,SAAQ,kBAAqC;IAG7C;QACE,KAAK,CAAC,CAAC,KAAK,EAAE,EAAE,CAAC,IAAI,CAAC,SAAS,CAAC,CAAC,KAAK,CAAC,CAAC,CAAA;IAC1C,CAAC;IAID,IAAI;QACF,mEAAmE;QACnE,OAAO,QAAQ,CAAC,aAAa,CAAC,IAAI,EAAE,SAAS,CAAC,CAAA;IAChD,CAAC;CACF"}
|
package/dist/index.js.map
DELETED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,cAAc,yBAAyB,CAAA;AACvC,cAAc,YAAY,CAAA;AAC1B,cAAc,gBAAgB,CAAA"}
|
package/readme.md
DELETED
|
@@ -1,199 +0,0 @@
|
|
|
1
|
-
# @typed/guard
|
|
2
|
-
|
|
3
|
-
[](https://badge.fury.io/js/%40typed%2Fguard)
|
|
4
|
-
[](https://opensource.org/licenses/MIT)
|
|
5
|
-
|
|
6
|
-
A powerful, type-safe runtime validation library built on top of [Effect](https://effect.website/). `@typed/guard` provides a flexible and composable way to validate and transform data with full type inference and runtime safety.
|
|
7
|
-
|
|
8
|
-
## Features
|
|
9
|
-
|
|
10
|
-
- 🛡️ **Type-safe Guards**: Runtime validation with complete type inference
|
|
11
|
-
- 🔄 **Effect Integration**: Seamless integration with Effect's ecosystem
|
|
12
|
-
- 🎯 **Composable**: Rich set of combinators for building complex validations
|
|
13
|
-
- 🌳 **Tree-shakeable**: Only import what you need
|
|
14
|
-
- 🔍 **Schema Integration**: First-class support for Effect's Schema
|
|
15
|
-
- ⚡ **Zero Dependencies**: Only requires Effect as a peer dependency
|
|
16
|
-
|
|
17
|
-
## Installation
|
|
18
|
-
|
|
19
|
-
```bash
|
|
20
|
-
# Using npm
|
|
21
|
-
npm install @typed/guard effect
|
|
22
|
-
|
|
23
|
-
# Using yarn
|
|
24
|
-
yarn add @typed/guard effect
|
|
25
|
-
|
|
26
|
-
# Using pnpm
|
|
27
|
-
pnpm add @typed/guard effect
|
|
28
|
-
```
|
|
29
|
-
|
|
30
|
-
## Quick Start
|
|
31
|
-
|
|
32
|
-
```typescript
|
|
33
|
-
import * as Guard from '@typed/guard'
|
|
34
|
-
import { Effect, Option } from 'effect'
|
|
35
|
-
|
|
36
|
-
// Simple number validation
|
|
37
|
-
const isPositive = Guard.liftPredicate((n: number) => n > 0)
|
|
38
|
-
|
|
39
|
-
// Usage
|
|
40
|
-
const result = Effect.runSync(isPositive(5)) // Option.some(5)
|
|
41
|
-
const invalid = Effect.runSync(isPositive(-1)) // Option.none()
|
|
42
|
-
|
|
43
|
-
// Composing guards
|
|
44
|
-
const toString = Guard.map(isPositive, n => n.toString())
|
|
45
|
-
const result2 = Effect.runSync(toString(5)) // Option.some("5")
|
|
46
|
-
```
|
|
47
|
-
|
|
48
|
-
## Core Concepts
|
|
49
|
-
|
|
50
|
-
### Guards
|
|
51
|
-
|
|
52
|
-
A Guard is a function that takes an input and returns an `Effect` containing an `Option` of the output:
|
|
53
|
-
|
|
54
|
-
```typescript
|
|
55
|
-
type Guard<I, O = never, E = never, R = never> =
|
|
56
|
-
(input: I) => Effect.Effect<Option.Option<O>, E, R>
|
|
57
|
-
```
|
|
58
|
-
|
|
59
|
-
- `I`: Input type
|
|
60
|
-
- `O`: Output type
|
|
61
|
-
- `E`: Error type
|
|
62
|
-
- `R`: Required context
|
|
63
|
-
|
|
64
|
-
### Key Operations
|
|
65
|
-
|
|
66
|
-
#### Composition
|
|
67
|
-
|
|
68
|
-
```typescript
|
|
69
|
-
const numberToString = (n: number) =>
|
|
70
|
-
Effect.succeed(n > 5 ? Option.some(n.toString()) : Option.none())
|
|
71
|
-
|
|
72
|
-
const stringToLength = (s: string) =>
|
|
73
|
-
Effect.succeed(s.length > 1 ? Option.some(s.length) : Option.none())
|
|
74
|
-
|
|
75
|
-
// Compose them together
|
|
76
|
-
const composed: Guard<number, number> = Guard.compose(numberToString, stringLength)
|
|
77
|
-
```
|
|
78
|
-
|
|
79
|
-
#### Filtering and Mapping
|
|
80
|
-
|
|
81
|
-
```typescript
|
|
82
|
-
// Filter values
|
|
83
|
-
const evenNumbers = Guard.filter(isPositive, n => n % 2 === 0)
|
|
84
|
-
|
|
85
|
-
// Map values with effects
|
|
86
|
-
const asyncTransform = Guard.mapEffect(isPositive, n =>
|
|
87
|
-
Effect.promise(() => Promise.resolve(n * 2))
|
|
88
|
-
)
|
|
89
|
-
```
|
|
90
|
-
|
|
91
|
-
#### Error Handling
|
|
92
|
-
|
|
93
|
-
```typescript
|
|
94
|
-
const withRecovery = Guard.catchAll(
|
|
95
|
-
failingGuard,
|
|
96
|
-
error => Effect.succeed(`Recovered from: ${error}`)
|
|
97
|
-
)
|
|
98
|
-
|
|
99
|
-
const withTaggedRecovery = Guard.catchTag(
|
|
100
|
-
failingGuard,
|
|
101
|
-
'ValidationError',
|
|
102
|
-
error => Effect.succeed(`Invalid input: ${error.message}`)
|
|
103
|
-
)
|
|
104
|
-
```
|
|
105
|
-
|
|
106
|
-
#### Schema Integration
|
|
107
|
-
|
|
108
|
-
```typescript
|
|
109
|
-
import { Schema } from 'effect'
|
|
110
|
-
|
|
111
|
-
const PersonSchema = Schema.Struct({
|
|
112
|
-
name: Schema.string,
|
|
113
|
-
age: Schema.number
|
|
114
|
-
})
|
|
115
|
-
|
|
116
|
-
const personGuard = Guard.fromSchemaDecode(PersonSchema)
|
|
117
|
-
const personGuard = Guard.fromSchemaDecodeUnknown(PersonSchema)
|
|
118
|
-
const personGuard = Guard.fromSchemaEncode(PersonSchema)
|
|
119
|
-
```
|
|
120
|
-
|
|
121
|
-
## Advanced Usage
|
|
122
|
-
|
|
123
|
-
### Pattern Matching with `any`
|
|
124
|
-
|
|
125
|
-
```typescript
|
|
126
|
-
const numberOrString = Guard.any({
|
|
127
|
-
number: Guard.liftPredicate((n): n is number => typeof n === 'number'),
|
|
128
|
-
string: Guard.liftPredicate((s): s is string => typeof s === 'string')
|
|
129
|
-
})
|
|
130
|
-
|
|
131
|
-
// Returns: { _tag: 'number', value: 123 }
|
|
132
|
-
Effect.runSync(numberOrString(123))
|
|
133
|
-
|
|
134
|
-
// Returns: { _tag: 'string', value: 'hello' }
|
|
135
|
-
Effect.runSync(numberOrString('hello'))
|
|
136
|
-
```
|
|
137
|
-
|
|
138
|
-
### Property Binding
|
|
139
|
-
|
|
140
|
-
```typescript
|
|
141
|
-
import { pipe } from 'effect'
|
|
142
|
-
|
|
143
|
-
const complexGuard = pipe(
|
|
144
|
-
Guard.identity<number>,
|
|
145
|
-
Guard.bindTo('value'),
|
|
146
|
-
Guard.bind('asString', ({ value }) =>
|
|
147
|
-
Effect.succeedSome(value.toString())
|
|
148
|
-
),
|
|
149
|
-
Guard.let('asBigInt', ({ asString }) =>
|
|
150
|
-
BigInt(asString)
|
|
151
|
-
)
|
|
152
|
-
)
|
|
153
|
-
|
|
154
|
-
// Returns: { value: 123, asString: '123', asBigInt: 123n }
|
|
155
|
-
Effect.runSync(complexGuard(123))
|
|
156
|
-
```
|
|
157
|
-
|
|
158
|
-
### Creating Reusable Guards with `Guardable`
|
|
159
|
-
|
|
160
|
-
The `Guardable` class allows you to create reusable guards as classes. This is particularly useful when you need to create guards that are also data structures
|
|
161
|
-
|
|
162
|
-
```typescript
|
|
163
|
-
import { Guardable, GUARDABLE } from '@typed/guard'
|
|
164
|
-
import { Effect } from 'effect'
|
|
165
|
-
|
|
166
|
-
// Create a guard that multiplies numbers by a configurable value
|
|
167
|
-
class MultiplyGuard extends Guardable<number, number> {
|
|
168
|
-
constructor(readonly multiplier: number) {
|
|
169
|
-
super()
|
|
170
|
-
}
|
|
171
|
-
|
|
172
|
-
// Implement the GUARDABLE symbol to define the guard's behavior
|
|
173
|
-
[GUARDABLE] = (input: number) =>
|
|
174
|
-
Effect.succeedSome(input * this.multiplier)
|
|
175
|
-
}
|
|
176
|
-
|
|
177
|
-
// Create an instance with a specific multiplier
|
|
178
|
-
const multiplyByThree = new MultiplyGuard(3)
|
|
179
|
-
|
|
180
|
-
// Use it like a regular guard function
|
|
181
|
-
Effect.runSync(multiplyByThree(4)) // Option.some(12)
|
|
182
|
-
|
|
183
|
-
// It's pipeable too!
|
|
184
|
-
|
|
185
|
-
const guard = multiplyByThree.pipe(
|
|
186
|
-
Guard.map(n => n.toString()),
|
|
187
|
-
)
|
|
188
|
-
|
|
189
|
-
Effect.runSync(guard(4)) // Option.some("12")
|
|
190
|
-
```
|
|
191
|
-
|
|
192
|
-
## Contributing
|
|
193
|
-
|
|
194
|
-
Contributions are welcome! Please feel free to submit a Pull Request.
|
|
195
|
-
|
|
196
|
-
## License
|
|
197
|
-
|
|
198
|
-
MIT © [Tylor Steinberger](https://github.com/TylorS)
|
|
199
|
-
|
|
@@ -1,102 +0,0 @@
|
|
|
1
|
-
import { describe, expect, it } from '@effect/vitest'
|
|
2
|
-
import { ExtensibleFunction } from './ExtensibleFunction.js'
|
|
3
|
-
|
|
4
|
-
describe('ExtensibleFunction', () => {
|
|
5
|
-
it('should create a function that can be called normally', () => {
|
|
6
|
-
const add = new ExtensibleFunction((x: number) => x + 1)
|
|
7
|
-
expect(add(1)).toBe(2)
|
|
8
|
-
})
|
|
9
|
-
|
|
10
|
-
it('should allow extending the function with additional properties', () => {
|
|
11
|
-
class EnhancedFunction extends ExtensibleFunction<(x: number) => number> {
|
|
12
|
-
description: string
|
|
13
|
-
|
|
14
|
-
constructor(fn: (x: number) => number, description: string) {
|
|
15
|
-
super(fn)
|
|
16
|
-
this.description = description
|
|
17
|
-
}
|
|
18
|
-
}
|
|
19
|
-
|
|
20
|
-
const add = new EnhancedFunction((x: number) => x + 1, 'adds one')
|
|
21
|
-
expect(add(1)).toBe(2)
|
|
22
|
-
expect(add.description).toBe('adds one')
|
|
23
|
-
})
|
|
24
|
-
|
|
25
|
-
it('should maintain function properties like length and name', () => {
|
|
26
|
-
const namedFn = function addOne(x: number) {
|
|
27
|
-
return x + 1
|
|
28
|
-
}
|
|
29
|
-
const add = new ExtensibleFunction(namedFn)
|
|
30
|
-
expect(add.length).toBe(1)
|
|
31
|
-
expect(add.name).toBe('addOne')
|
|
32
|
-
})
|
|
33
|
-
|
|
34
|
-
it('should work with async functions', async () => {
|
|
35
|
-
const asyncAdd = new ExtensibleFunction(async (x: number) => {
|
|
36
|
-
return x + 1
|
|
37
|
-
})
|
|
38
|
-
expect(await asyncAdd(1)).toBe(2)
|
|
39
|
-
})
|
|
40
|
-
|
|
41
|
-
it('should preserve this context in methods', () => {
|
|
42
|
-
class Calculator extends ExtensibleFunction<(x: number) => number> {
|
|
43
|
-
private multiplier: number
|
|
44
|
-
|
|
45
|
-
constructor(multiplier: number) {
|
|
46
|
-
super((x: number) => this.multiply(x))
|
|
47
|
-
this.multiplier = multiplier
|
|
48
|
-
}
|
|
49
|
-
|
|
50
|
-
private multiply(x: number): number {
|
|
51
|
-
return x * this.multiplier
|
|
52
|
-
}
|
|
53
|
-
}
|
|
54
|
-
|
|
55
|
-
const calc = new Calculator(2)
|
|
56
|
-
expect(calc(3)).toBe(6)
|
|
57
|
-
})
|
|
58
|
-
|
|
59
|
-
it('should handle multiple arguments correctly', () => {
|
|
60
|
-
const add = new ExtensibleFunction((a: number, b: number) => a + b)
|
|
61
|
-
expect(add(1, 2)).toBe(3)
|
|
62
|
-
})
|
|
63
|
-
|
|
64
|
-
it('should work with generic functions', () => {
|
|
65
|
-
const identity = new ExtensibleFunction(<T>(x: T) => x)
|
|
66
|
-
expect(identity(42)).toBe(42)
|
|
67
|
-
expect(identity('test')).toBe('test')
|
|
68
|
-
})
|
|
69
|
-
|
|
70
|
-
it('should throw when constructed without arguments', () => {
|
|
71
|
-
expect(() => new ExtensibleFunction(undefined as any)).toThrow()
|
|
72
|
-
})
|
|
73
|
-
|
|
74
|
-
it('should maintain proper error stack traces', () => {
|
|
75
|
-
class Throws<E> extends ExtensibleFunction<(cause: E) => never> {
|
|
76
|
-
constructor() {
|
|
77
|
-
super((cause) => {
|
|
78
|
-
throw cause
|
|
79
|
-
})
|
|
80
|
-
}
|
|
81
|
-
}
|
|
82
|
-
|
|
83
|
-
const throws = new Throws<Error>()
|
|
84
|
-
|
|
85
|
-
try {
|
|
86
|
-
throws(new Error('test error'))
|
|
87
|
-
} catch (e) {
|
|
88
|
-
expect(e instanceof Error).toBe(true)
|
|
89
|
-
expect(e.stack).toBeDefined()
|
|
90
|
-
expect(e.message).toBe('test error')
|
|
91
|
-
}
|
|
92
|
-
})
|
|
93
|
-
|
|
94
|
-
it('should allow function composition', () => {
|
|
95
|
-
const add1 = new ExtensibleFunction((x: number) => x + 1)
|
|
96
|
-
const multiply2 = new ExtensibleFunction((x: number) => x * 2)
|
|
97
|
-
const composed = new ExtensibleFunction((x: number) => multiply2(add1(x)))
|
|
98
|
-
expect(composed(3)).toBe(8) // (3 + 1) * 2
|
|
99
|
-
})
|
|
100
|
-
|
|
101
|
-
it('should allow class decorator', () => {})
|
|
102
|
-
})
|
|
@@ -1,8 +0,0 @@
|
|
|
1
|
-
function Extensible<I, O>(f: (input: I) => O): (input: I) => O {
|
|
2
|
-
return Object.setPrototypeOf(f, new.target.prototype)
|
|
3
|
-
}
|
|
4
|
-
Extensible.prototype = Function.prototype
|
|
5
|
-
|
|
6
|
-
// Hack to make the type inference work
|
|
7
|
-
export const ExtensibleFunction: new <F extends (...inputs: readonly any[]) => any>(f: F) => F =
|
|
8
|
-
Extensible as any
|