schematch 0.0.1

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/dist/errors.js ADDED
@@ -0,0 +1,149 @@
1
+ import { prettifyStandardSchemaError } from './standard-schema/errors.js';
2
+ import { validateSync } from './standard-schema/validation.js';
3
+ /**
4
+ * Error thrown (or returned) when no case in a match expression matched the input.
5
+ *
6
+ * Implements {@link StandardSchemaV1.FailureResult} so it can be used directly as a
7
+ * standard-schema failure result — the `.issues` array contains per-case validation details.
8
+ */
9
+ export class NonExhaustiveError extends Error {
10
+ constructor(input, options) {
11
+ const issues = buildIssues(input, options);
12
+ const message = buildErrorMessage(input, issues, options);
13
+ super(message);
14
+ this.input = input;
15
+ this.issues = issues;
16
+ this.schemas = options?.schemas;
17
+ this.discriminator = options?.discriminator;
18
+ }
19
+ }
20
+ /** Build standard-schema issues from the match failure. */
21
+ function buildIssues(input, options) {
22
+ const issues = [];
23
+ const schemas = options?.schemas;
24
+ if (!schemas || schemas.length === 0) {
25
+ issues.push({ message: formatNoMatchMessage(input) });
26
+ return issues;
27
+ }
28
+ const disc = options?.discriminator;
29
+ if (disc && !disc.matched) {
30
+ // Discriminator miss — the discriminator value wasn't one of the expected values.
31
+ // Single issue is sufficient.
32
+ let discValueStr;
33
+ try {
34
+ discValueStr = JSON.stringify(disc.value);
35
+ }
36
+ catch {
37
+ discValueStr = String(disc.value);
38
+ }
39
+ const expectedStr = disc.expected.map(v => {
40
+ try {
41
+ return JSON.stringify(v);
42
+ }
43
+ catch {
44
+ return String(v);
45
+ }
46
+ }).join(', ');
47
+ issues.push({
48
+ message: `Discriminator '${disc.key}' has value ${discValueStr} but expected one of: ${expectedStr}`,
49
+ path: [disc.key],
50
+ });
51
+ return issues;
52
+ }
53
+ // Collect per-case issues
54
+ for (let i = 0; i < schemas.length; i += 1) {
55
+ try {
56
+ const result = validateSync(schemas[i], input);
57
+ if ('issues' in result && result.issues) {
58
+ for (const issue of result.issues) {
59
+ issues.push({
60
+ message: `Case ${i + 1}: ${issue.message}`,
61
+ path: issue.path,
62
+ });
63
+ }
64
+ }
65
+ }
66
+ catch {
67
+ // Validation threw (e.g. async schema used in sync context) — skip
68
+ }
69
+ }
70
+ if (issues.length === 0) {
71
+ issues.push({ message: formatNoMatchMessage(input) });
72
+ }
73
+ return issues;
74
+ }
75
+ function formatNoMatchMessage(input) {
76
+ let displayedValue;
77
+ try {
78
+ displayedValue = JSON.stringify(input);
79
+ }
80
+ catch {
81
+ displayedValue = String(input);
82
+ }
83
+ return `No schema matches value ${displayedValue}`;
84
+ }
85
+ function buildErrorMessage(input, issues, options) {
86
+ let displayedValue;
87
+ try {
88
+ displayedValue = JSON.stringify(input);
89
+ }
90
+ catch {
91
+ displayedValue = String(input);
92
+ }
93
+ const lines = [`Schema matching error: no schema matches value ${displayedValue}`];
94
+ const disc = options?.discriminator;
95
+ if (disc) {
96
+ let discValueStr;
97
+ try {
98
+ discValueStr = JSON.stringify(disc.value);
99
+ }
100
+ catch {
101
+ discValueStr = String(disc.value);
102
+ }
103
+ const expectedStr = disc.expected.map(v => {
104
+ try {
105
+ return JSON.stringify(v);
106
+ }
107
+ catch {
108
+ return String(v);
109
+ }
110
+ }).join(', ');
111
+ if (disc.matched) {
112
+ // Discriminator value was found in the dispatch table but full validation failed.
113
+ // Show the matched value and per-case issues for just the matched branch.
114
+ lines.push(` Discriminator '${disc.key}' matched ${discValueStr} (options: ${expectedStr}) but failed validation:`);
115
+ appendPerCaseIssues(lines, options?.schemas, input);
116
+ }
117
+ else {
118
+ // Discriminator value was not in the dispatch table — that's the whole story.
119
+ lines.push(` Discriminator '${disc.key}' has value ${discValueStr} but expected one of: ${expectedStr}`);
120
+ }
121
+ }
122
+ else {
123
+ // No discriminator — show per-case issues for all schemas
124
+ appendPerCaseIssues(lines, options?.schemas, input);
125
+ }
126
+ return lines.join('\n');
127
+ }
128
+ function appendPerCaseIssues(lines, schemas, input) {
129
+ if (!schemas || schemas.length === 0)
130
+ return;
131
+ for (let i = 0; i < schemas.length; i += 1) {
132
+ try {
133
+ const result = validateSync(schemas[i], input);
134
+ if ('issues' in result && result.issues) {
135
+ const pretty = prettifyStandardSchemaError(result);
136
+ if (pretty) {
137
+ lines.push(` Case ${i + 1}:`);
138
+ for (const line of pretty.split('\n')) {
139
+ lines.push(` ${line}`);
140
+ }
141
+ }
142
+ }
143
+ }
144
+ catch {
145
+ // Validation threw (e.g. async schema used in sync context) — skip
146
+ }
147
+ }
148
+ }
149
+ //# sourceMappingURL=errors.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"errors.js","sourceRoot":"","sources":["../src/errors.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,7 @@
1
+ export { match, matchAsync } from './match.js';
2
+ export { isMatching, isMatchingAsync } from './is-matching.js';
3
+ export { NonExhaustiveError } from './errors.js';
4
+ export type { StandardSchemaV1 } from './standard-schema/contract.js';
5
+ export { prettifyStandardSchemaError, StandardSchemaV1Error, toDotPath } from './standard-schema/errors.js';
6
+ export { looksLikeStandardSchema, looksLikeStandardSchemaFailure } from './standard-schema/utils.js';
7
+ export type { InferInput, InferOutput, StandardSchema } from './types.js';
package/dist/index.js ADDED
@@ -0,0 +1,6 @@
1
+ export { match, matchAsync } from './match.js';
2
+ export { isMatching, isMatchingAsync } from './is-matching.js';
3
+ export { NonExhaustiveError } from './errors.js';
4
+ export { prettifyStandardSchemaError, StandardSchemaV1Error, toDotPath } from './standard-schema/errors.js';
5
+ export { looksLikeStandardSchema, looksLikeStandardSchemaFailure } from './standard-schema/utils.js';
6
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAC,KAAK,EAAE,UAAU,EAAC,MAAM,YAAY,CAAA;AAC5C,OAAO,EAAC,UAAU,EAAE,eAAe,EAAC,MAAM,kBAAkB,CAAA;AAC5D,OAAO,EAAC,kBAAkB,EAAC,MAAM,aAAa,CAAA;AAG9C,OAAO,EAAC,2BAA2B,EAAE,qBAAqB,EAAE,SAAS,EAAC,MAAM,6BAA6B,CAAA;AACzG,OAAO,EAAC,uBAAuB,EAAE,8BAA8B,EAAC,MAAM,4BAA4B,CAAA"}
@@ -0,0 +1,6 @@
1
+ import type { StandardSchemaV1 } from './standard-schema/contract.js';
2
+ import type { InferOutput } from './types.js';
3
+ export declare function isMatching<const schema extends StandardSchemaV1>(schema: schema): (value: unknown) => value is InferOutput<schema>;
4
+ export declare function isMatching<const schema extends StandardSchemaV1>(schema: schema, value: unknown): value is InferOutput<schema>;
5
+ export declare function isMatchingAsync<const schema extends StandardSchemaV1>(schema: schema): (value: unknown) => Promise<boolean>;
6
+ export declare function isMatchingAsync<const schema extends StandardSchemaV1>(schema: schema, value: unknown): Promise<boolean>;
@@ -0,0 +1,28 @@
1
+ import { ASYNC_REQUIRED, NO_MATCH, matchSchemaAsync, matchSchemaSync } from './standard-schema/compiled.js';
2
+ import { assertStandardSchema } from './standard-schema/validation.js';
3
+ export function isMatching(schema, value) {
4
+ assertStandardSchema(schema);
5
+ if (arguments.length === 1) {
6
+ return (next) => isMatchingValue(schema, next);
7
+ }
8
+ return isMatchingValue(schema, value);
9
+ }
10
+ export function isMatchingAsync(schema, value) {
11
+ assertStandardSchema(schema);
12
+ if (arguments.length === 1) {
13
+ return async (next) => {
14
+ return (await matchSchemaAsync(schema, next)) !== NO_MATCH;
15
+ };
16
+ }
17
+ return (async () => {
18
+ return (await matchSchemaAsync(schema, value)) !== NO_MATCH;
19
+ })();
20
+ }
21
+ const isMatchingValue = (schema, value) => {
22
+ const result = matchSchemaSync(schema, value);
23
+ if (result === ASYNC_REQUIRED) {
24
+ throw new Error('Schema validation returned a Promise. Use isMatchingAsync instead.');
25
+ }
26
+ return result !== NO_MATCH;
27
+ };
28
+ //# sourceMappingURL=is-matching.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"is-matching.js","sourceRoot":"","sources":["../src/is-matching.ts"],"names":[],"mappings":"AACA,OAAO,EAAC,cAAc,EAAE,QAAQ,EAAE,gBAAgB,EAAE,eAAe,EAAC,MAAM,+BAA+B,CAAA;AACzG,OAAO,EAAC,oBAAoB,EAAC,MAAM,iCAAiC,CAAA;AAUpE,MAAM,UAAU,UAAU,CACxB,MAAc,EACd,KAAe;IAEf,oBAAoB,CAAC,MAAM,CAAC,CAAA;IAC5B,IAAI,SAAS,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;QAC3B,OAAO,CAAC,IAAa,EAA+B,EAAE,CAAC,eAAe,CAAC,MAAM,EAAE,IAAI,CAAC,CAAA;IACtF,CAAC;IACD,OAAO,eAAe,CAAC,MAAM,EAAE,KAAK,CAAC,CAAA;AACvC,CAAC;AASD,MAAM,UAAU,eAAe,CAC7B,MAAc,EACd,KAAe;IAEf,oBAAoB,CAAC,MAAM,CAAC,CAAA;IAC5B,IAAI,SAAS,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;QAC3B,OAAO,KAAK,EAAE,IAAa,EAAE,EAAE;YAC7B,OAAO,CAAC,MAAM,gBAAgB,CAAC,MAAM,EAAE,IAAI,CAAC,CAAC,KAAK,QAAQ,CAAA;QAC5D,CAAC,CAAA;IACH,CAAC;IACD,OAAO,CAAC,KAAK,IAAI,EAAE;QACjB,OAAO,CAAC,MAAM,gBAAgB,CAAC,MAAM,EAAE,KAAK,CAAC,CAAC,KAAK,QAAQ,CAAA;IAC7D,CAAC,CAAC,EAAE,CAAA;AACN,CAAC;AAED,MAAM,eAAe,GAAG,CACtB,MAAc,EACd,KAAc,EACgB,EAAE;IAChC,MAAM,MAAM,GAAG,eAAe,CAAC,MAAM,EAAE,KAAK,CAAC,CAAA;IAC7C,IAAI,MAAM,KAAK,cAAc,EAAE,CAAC;QAC9B,MAAM,IAAI,KAAK,CAAC,oEAAoE,CAAC,CAAA;IACvF,CAAC;IACD,OAAO,MAAM,KAAK,QAAQ,CAAA;AAC5B,CAAC,CAAA"}
@@ -0,0 +1,221 @@
1
+ import type { StandardSchemaV1 } from './standard-schema/contract.js';
2
+ import type { InferInput, InferOutput } from './types.js';
3
+ import { NonExhaustiveError } from './errors.js';
4
+ /** Resolves `Unset` to `never` for use in StandardSchema types. */
5
+ type ResolveOutput<T> = T extends typeof unset ? never : T;
6
+ type MatchState<output> = {
7
+ matched: true;
8
+ value: output;
9
+ } | {
10
+ matched: false;
11
+ value: undefined;
12
+ };
13
+ declare const unset: unique symbol;
14
+ type Unset = typeof unset;
15
+ type WithReturn<current, next> = current extends Unset ? next : current | next;
16
+ type WithAsyncReturn<current, next> = current extends Unset ? Awaited<next> : current | Awaited<next>;
17
+ type MatchFactory = {
18
+ <const input, output = Unset>(value: input): MatchExpression<input, output>;
19
+ input<input>(): ReusableMatcher<input, Unset>;
20
+ output<output>(): ReusableMatcher<unknown, output>;
21
+ case<input, schema extends StandardSchemaV1, result>(schema: schema, handler: (value: InferOutput<schema>, input: input) => result): ReusableMatcher<input, WithReturn<Unset, result>, InferInput<schema>>;
22
+ case<input, schema extends StandardSchemaV1, result>(schema: schema, predicate: (value: InferOutput<schema>, input: input) => unknown, handler: (value: InferOutput<schema>, input: input) => result): ReusableMatcher<input, WithReturn<Unset, result>, InferInput<schema>>;
23
+ case<input, schemas extends readonly [StandardSchemaV1, ...StandardSchemaV1[]], result>(...args: [...schemas, (value: InferOutput<schemas[number]>, input: input) => result]): ReusableMatcher<input, WithReturn<Unset, result>, InferInput<schemas[number]>>;
24
+ };
25
+ type MatchAsyncFactory = {
26
+ <const input, output = Unset>(value: input): MatchExpressionAsync<input, output>;
27
+ input<input>(): ReusableMatcherAsync<input, Unset>;
28
+ output<output>(): ReusableMatcherAsync<unknown, output>;
29
+ case<input, schema extends StandardSchemaV1, result>(schema: schema, handler: (value: InferOutput<schema>, input: input) => result | Promise<result>): ReusableMatcherAsync<input, WithAsyncReturn<Unset, result>, InferInput<schema>>;
30
+ case<input, schema extends StandardSchemaV1, result>(schema: schema, predicate: (value: InferOutput<schema>, input: input) => unknown | Promise<unknown>, handler: (value: InferOutput<schema>, input: input) => result | Promise<result>): ReusableMatcherAsync<input, WithAsyncReturn<Unset, result>, InferInput<schema>>;
31
+ case<input, schemas extends readonly [StandardSchemaV1, ...StandardSchemaV1[]], result>(...args: [...schemas, (value: InferOutput<schemas[number]>, input: input) => result | Promise<result>]): ReusableMatcherAsync<input, WithAsyncReturn<Unset, result>, InferInput<schemas[number]>>;
32
+ };
33
+ export declare const match: MatchFactory;
34
+ export declare const matchAsync: MatchAsyncFactory;
35
+ declare class MatchExpression<input, output, CaseInputs = never> {
36
+ private input;
37
+ private matched;
38
+ private value;
39
+ private schemas;
40
+ constructor(input: input, matched: boolean, value: output | undefined);
41
+ case<schema extends StandardSchemaV1, result>(schema: schema, handler: (value: InferOutput<schema>, input: input) => result): MatchExpression<input, WithReturn<output, result>, CaseInputs | InferInput<schema>>;
42
+ case<schema extends StandardSchemaV1, result>(schema: schema, predicate: (value: InferOutput<schema>, input: input) => unknown, handler: (value: InferOutput<schema>, input: input) => result): MatchExpression<input, WithReturn<output, result>, CaseInputs | InferInput<schema>>;
43
+ case<schemas extends readonly [StandardSchemaV1, ...StandardSchemaV1[]], result>(...args: [...schemas, (value: InferOutput<schemas[number]>, input: input) => result]): MatchExpression<input, WithReturn<output, result>, CaseInputs | InferInput<schemas[number]>>;
44
+ when<result>(predicate: (value: input) => unknown, handler: (value: input, input: input) => result): MatchExpression<input, WithReturn<output, result>, CaseInputs>;
45
+ /**
46
+ * Terminates the match expression with a default behavior when no case matches.
47
+ *
48
+ * @overload `.default('assert')` — Throws a {@link NonExhaustiveError} if no case matched. Accepts any input.
49
+ * @overload `.default('never')` — Throws a {@link NonExhaustiveError} if no case matched. Produces a type error if the input doesn't match the union of case input types.
50
+ * @overload `.default('reject')` — Returns a {@link NonExhaustiveError} instance (instead of throwing) if no case matched. Accepts any input.
51
+ * @overload `.default(handler)` — Calls the handler with the input value if no case matched.
52
+ */
53
+ default(
54
+ /** Throw a {@link NonExhaustiveError} if no case matched. Accepts any input type. */
55
+ mode: 'assert'): output;
56
+ default(
57
+ /**
58
+ * Throw a {@link NonExhaustiveError} if no case matched.
59
+ * Constrains the input type to the union of all case schema input types —
60
+ * produces a compile-time error if the match input doesn't extend that union.
61
+ */
62
+ mode: input extends CaseInputs ? 'never' : never): output;
63
+ default(
64
+ /** Return a {@link NonExhaustiveError} instance (instead of throwing) if no case matched. */
65
+ mode: 'reject'): output | NonExhaustiveError;
66
+ default<result>(
67
+ /** A fallback handler called with the raw input when no case matched. */
68
+ handler: (value: input) => result): WithReturn<output, result>;
69
+ output<O>(): MatchExpression<input, O, CaseInputs>;
70
+ returnType(): this;
71
+ narrow(): this;
72
+ }
73
+ declare class MatchExpressionAsync<input, output, CaseInputs = never> {
74
+ private input;
75
+ private state;
76
+ private schemas;
77
+ constructor(input: input, state: Promise<MatchState<output>>, schemas?: StandardSchemaV1[]);
78
+ case<schema extends StandardSchemaV1, result>(schema: schema, handler: (value: InferOutput<schema>, input: input) => result | Promise<result>): MatchExpressionAsync<input, WithAsyncReturn<output, result>, CaseInputs | InferInput<schema>>;
79
+ case<schema extends StandardSchemaV1, result>(schema: schema, predicate: (value: InferOutput<schema>, input: input) => unknown | Promise<unknown>, handler: (value: InferOutput<schema>, input: input) => result | Promise<result>): MatchExpressionAsync<input, WithAsyncReturn<output, result>, CaseInputs | InferInput<schema>>;
80
+ case<schemas extends readonly [StandardSchemaV1, ...StandardSchemaV1[]], result>(...args: [...schemas, (value: InferOutput<schemas[number]>, input: input) => result | Promise<result>]): MatchExpressionAsync<input, WithAsyncReturn<output, result>, CaseInputs | InferInput<schemas[number]>>;
81
+ when<result>(predicate: (value: input) => unknown | Promise<unknown>, handler: (value: input, input: input) => result | Promise<result>): MatchExpressionAsync<input, WithAsyncReturn<output, result>, CaseInputs>;
82
+ /**
83
+ * Terminates the async match expression with a default behavior when no case matches.
84
+ *
85
+ * @overload `.default('assert')` — Throws a {@link NonExhaustiveError} if no case matched.
86
+ * @overload `.default('never')` — Throws a {@link NonExhaustiveError} if no case matched. Type error if input doesn't match case union.
87
+ * @overload `.default('reject')` — Resolves to a {@link NonExhaustiveError} instance if no case matched.
88
+ * @overload `.default(handler)` — Calls the handler with the input value if no case matched.
89
+ */
90
+ default(
91
+ /** Throw a {@link NonExhaustiveError} if no case matched. Accepts any input type. */
92
+ mode: 'assert'): Promise<output>;
93
+ default(
94
+ /**
95
+ * Throw a {@link NonExhaustiveError} if no case matched.
96
+ * Constrains the input type to the union of all case schema input types.
97
+ */
98
+ mode: input extends CaseInputs ? 'never' : never): Promise<output>;
99
+ default(
100
+ /** Resolve to a {@link NonExhaustiveError} instance if no case matched. */
101
+ mode: 'reject'): Promise<output | NonExhaustiveError>;
102
+ default<result>(
103
+ /** A fallback handler called with the raw input when no case matched. */
104
+ handler: (value: input) => result | Promise<result>): Promise<WithAsyncReturn<output, result>>;
105
+ output<O>(): MatchExpressionAsync<input, O, CaseInputs>;
106
+ returnType(): this;
107
+ narrow(): this;
108
+ }
109
+ type ReusableClause<input> = {
110
+ schemas: StandardSchemaV1[];
111
+ predicate?: (value: unknown, input: input) => unknown;
112
+ handler: (value: unknown, input: input) => unknown;
113
+ };
114
+ type ReusableWhenClause<input> = {
115
+ when: (input: input) => unknown;
116
+ handler: (value: input, input: input) => unknown;
117
+ };
118
+ declare class ReusableMatcher<input, output, CaseInputs = never> {
119
+ private readonly terminal;
120
+ private readonly clauses;
121
+ private dispatch;
122
+ /**
123
+ * Standard Schema V1 interface. The matcher itself is a valid standard-schema:
124
+ * - `validate(value)` tries all cases in order and returns `{ value }` on match or `{ issues }` on failure.
125
+ * - `types.input` is the union of all case schema input types (`CaseInputs`).
126
+ * - `types.output` is the union of all case handler return types.
127
+ */
128
+ readonly '~standard': StandardSchemaV1.Props<CaseInputs, ResolveOutput<output>>;
129
+ constructor(terminal: MatchState<output>, clauses?: Array<ReusableClause<input> | ReusableWhenClause<input>>);
130
+ private getDispatch;
131
+ case<schema extends StandardSchemaV1, result>(schema: schema, handler: (value: InferOutput<schema>, input: input) => result): ReusableMatcher<input, WithReturn<output, result>, CaseInputs | InferInput<schema>>;
132
+ case<schema extends StandardSchemaV1, result>(schema: schema, predicate: (value: InferOutput<schema>, input: input) => unknown, handler: (value: InferOutput<schema>, input: input) => result): ReusableMatcher<input, WithReturn<output, result>, CaseInputs | InferInput<schema>>;
133
+ case<schemas extends readonly [StandardSchemaV1, ...StandardSchemaV1[]], result>(...args: [...schemas, (value: InferOutput<schemas[number]>, input: input) => result]): ReusableMatcher<input, WithReturn<output, result>, CaseInputs | InferInput<schemas[number]>>;
134
+ when<result>(predicate: (value: input) => unknown, handler: (value: input, input: input) => result): ReusableMatcher<input, WithReturn<output, result>, CaseInputs>;
135
+ output<O>(): ReusableMatcher<input, O, CaseInputs>;
136
+ /**
137
+ * Terminates the reusable matcher and returns a function that executes the match.
138
+ *
139
+ * @overload `.default('assert')` — Returns a function that throws {@link NonExhaustiveError} on no match. Accepts `unknown` input.
140
+ * @overload `.default('never')` — Returns a function that throws {@link NonExhaustiveError} on no match. Input type is constrained to the union of case schema input types.
141
+ * @overload `.default('reject')` — Returns a function whose return type includes {@link NonExhaustiveError} (returned, not thrown) on no match.
142
+ * @overload `.default(handler)` — Returns a function that calls the handler on no match.
143
+ */
144
+ default(
145
+ /** Throw a {@link NonExhaustiveError} if no case matched. Accepts any input type. */
146
+ mode: 'assert'): (input: input) => output;
147
+ default(
148
+ /**
149
+ * Throw a {@link NonExhaustiveError} if no case matched.
150
+ * The returned function's input type is constrained to the union of all case schema input types.
151
+ */
152
+ mode: 'never'): (input: CaseInputs) => output;
153
+ default(
154
+ /** Return a {@link NonExhaustiveError} instance (instead of throwing) if no case matched. */
155
+ mode: 'reject'): (input: input) => output | NonExhaustiveError;
156
+ default<result>(
157
+ /** A fallback handler called with the raw input when no case matched. */
158
+ handler: (value: input) => result): (input: input) => WithReturn<output, result>;
159
+ private buildNonExhaustiveError;
160
+ /** Build a standard-schema FailureResult for use in `~standard.validate`. */
161
+ private buildFailureResult;
162
+ private execClause;
163
+ private exec;
164
+ }
165
+ type ReusableClauseAsync<input> = {
166
+ schemas: StandardSchemaV1[];
167
+ predicate?: (value: unknown, input: input) => unknown | Promise<unknown>;
168
+ handler: (value: unknown, input: input) => unknown | Promise<unknown>;
169
+ };
170
+ type ReusableWhenClauseAsync<input> = {
171
+ when: (input: input) => unknown | Promise<unknown>;
172
+ handler: (value: input, input: input) => unknown | Promise<unknown>;
173
+ };
174
+ declare class ReusableMatcherAsync<input, output, CaseInputs = never> {
175
+ private readonly terminal;
176
+ private readonly clauses;
177
+ private dispatch;
178
+ /**
179
+ * Standard Schema V1 interface (async). The matcher itself is a valid standard-schema:
180
+ * - `validate(value)` tries all cases in order and returns `Promise<{ value }>` on match or `Promise<{ issues }>` on failure.
181
+ * - `types.input` is the union of all case schema input types (`CaseInputs`).
182
+ * - `types.output` is the union of all case handler return types.
183
+ */
184
+ readonly '~standard': StandardSchemaV1.Props<CaseInputs, ResolveOutput<output>>;
185
+ constructor(terminal: Promise<MatchState<output>>, clauses?: Array<ReusableClauseAsync<input> | ReusableWhenClauseAsync<input>>);
186
+ private getDispatch;
187
+ case<schema extends StandardSchemaV1, result>(schema: schema, handler: (value: InferOutput<schema>, input: input) => result | Promise<result>): ReusableMatcherAsync<input, WithAsyncReturn<output, result>, CaseInputs | InferInput<schema>>;
188
+ case<schema extends StandardSchemaV1, result>(schema: schema, predicate: (value: InferOutput<schema>, input: input) => unknown | Promise<unknown>, handler: (value: InferOutput<schema>, input: input) => result | Promise<result>): ReusableMatcherAsync<input, WithAsyncReturn<output, result>, CaseInputs | InferInput<schema>>;
189
+ case<schemas extends readonly [StandardSchemaV1, ...StandardSchemaV1[]], result>(...args: [...schemas, (value: InferOutput<schemas[number]>, input: input) => result | Promise<result>]): ReusableMatcherAsync<input, WithAsyncReturn<output, result>, CaseInputs | InferInput<schemas[number]>>;
190
+ when<result>(predicate: (value: input) => unknown | Promise<unknown>, handler: (value: input, input: input) => result | Promise<result>): ReusableMatcherAsync<input, WithAsyncReturn<output, result>, CaseInputs>;
191
+ output<O>(): ReusableMatcherAsync<input, O, CaseInputs>;
192
+ /**
193
+ * Terminates the async reusable matcher and returns a function that executes the match.
194
+ *
195
+ * @overload `.default('assert')` — Returns an async function that throws {@link NonExhaustiveError} on no match.
196
+ * @overload `.default('never')` — Returns an async function that throws on no match, with input constrained to case union.
197
+ * @overload `.default('reject')` — Returns an async function that resolves to {@link NonExhaustiveError} on no match.
198
+ * @overload `.default(handler)` — Returns an async function that calls the handler on no match.
199
+ */
200
+ default(
201
+ /** Throw a {@link NonExhaustiveError} if no case matched. Accepts any input type. */
202
+ mode: 'assert'): (input: input) => Promise<output>;
203
+ default(
204
+ /**
205
+ * Throw a {@link NonExhaustiveError} if no case matched.
206
+ * The returned function's input type is constrained to the union of all case schema input types.
207
+ */
208
+ mode: 'never'): (input: CaseInputs) => Promise<output>;
209
+ default(
210
+ /** Resolve to a {@link NonExhaustiveError} instance if no case matched. */
211
+ mode: 'reject'): (input: input) => Promise<output | NonExhaustiveError>;
212
+ default<result>(
213
+ /** A fallback handler called with the raw input when no case matched. */
214
+ handler: (value: input) => result | Promise<result>): (input: input) => Promise<WithAsyncReturn<output, result>>;
215
+ private buildNonExhaustiveError;
216
+ /** Build a standard-schema FailureResult for use in `~standard.validate`. */
217
+ private buildFailureResult;
218
+ private execClause;
219
+ private exec;
220
+ }
221
+ export {};