@barnum/barnum 0.3.0 → 0.4.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/artifacts/linux-arm64/barnum +0 -0
- package/artifacts/linux-x64/barnum +0 -0
- package/artifacts/macos-arm64/barnum +0 -0
- package/artifacts/macos-x64/barnum +0 -0
- package/artifacts/win-x64/barnum.exe +0 -0
- package/dist/all.d.ts +41 -10
- package/dist/all.d.ts.map +1 -0
- package/dist/all.js +1 -1
- package/dist/ast.d.ts +199 -98
- package/dist/ast.d.ts.map +1 -0
- package/dist/ast.js +271 -233
- package/dist/bind.d.ts +9 -12
- package/dist/bind.d.ts.map +1 -0
- package/dist/bind.js +14 -51
- package/dist/builtins/array.d.ts +36 -0
- package/dist/builtins/array.d.ts.map +1 -0
- package/dist/builtins/array.js +93 -0
- package/dist/builtins/index.d.ts +6 -0
- package/dist/builtins/index.d.ts.map +1 -0
- package/dist/builtins/index.js +5 -0
- package/dist/builtins/scalar.d.ts +12 -0
- package/dist/builtins/scalar.d.ts.map +1 -0
- package/dist/builtins/scalar.js +41 -0
- package/dist/builtins/struct.d.ts +25 -0
- package/dist/builtins/struct.d.ts.map +1 -0
- package/dist/builtins/struct.js +67 -0
- package/dist/builtins/tagged-union.d.ts +54 -0
- package/dist/builtins/tagged-union.d.ts.map +1 -0
- package/dist/builtins/tagged-union.js +81 -0
- package/dist/builtins/with-resource.d.ts +23 -0
- package/dist/builtins/with-resource.d.ts.map +1 -0
- package/dist/builtins/with-resource.js +35 -0
- package/dist/chain.d.ts +1 -0
- package/dist/chain.d.ts.map +1 -0
- package/dist/chain.js +3 -3
- package/dist/effect-id.d.ts +1 -0
- package/dist/effect-id.d.ts.map +1 -0
- package/dist/handler.d.ts +7 -6
- package/dist/handler.d.ts.map +1 -0
- package/dist/handler.js +5 -21
- package/dist/index.d.ts +10 -6
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +4 -2
- package/dist/iterator.d.ts +32 -0
- package/dist/iterator.d.ts.map +1 -0
- package/dist/iterator.js +123 -0
- package/dist/option.d.ts +74 -0
- package/dist/option.d.ts.map +1 -0
- package/dist/option.js +141 -0
- package/dist/pipe.d.ts +11 -10
- package/dist/pipe.d.ts.map +1 -0
- package/dist/pipe.js +5 -4
- package/dist/race.d.ts +5 -4
- package/dist/race.d.ts.map +1 -0
- package/dist/race.js +17 -42
- package/dist/recursive.d.ts +9 -3
- package/dist/recursive.d.ts.map +1 -0
- package/dist/recursive.js +18 -13
- package/dist/result.d.ts +50 -0
- package/dist/result.d.ts.map +1 -0
- package/dist/result.js +117 -0
- package/dist/run.d.ts +9 -2
- package/dist/run.d.ts.map +1 -0
- package/dist/run.js +37 -20
- package/dist/runtime.d.ts +6 -0
- package/dist/runtime.d.ts.map +1 -0
- package/dist/runtime.js +7 -0
- package/dist/schema.d.ts +1 -0
- package/dist/schema.d.ts.map +1 -0
- package/dist/schemas.d.ts +5 -0
- package/dist/schemas.d.ts.map +1 -0
- package/dist/schemas.js +13 -0
- package/dist/try-catch.d.ts +2 -1
- package/dist/try-catch.d.ts.map +1 -0
- package/dist/try-catch.js +10 -9
- package/dist/values.d.ts +6 -0
- package/dist/values.d.ts.map +1 -0
- package/dist/values.js +12 -0
- package/dist/worker.d.ts +5 -1
- package/dist/worker.d.ts.map +1 -0
- package/dist/worker.js +15 -3
- package/package.json +8 -6
- package/src/all.ts +118 -74
- package/src/ast.ts +773 -350
- package/src/bind.ts +32 -62
- package/src/builtins/array.ts +121 -0
- package/src/builtins/index.ts +17 -0
- package/src/builtins/scalar.ts +49 -0
- package/src/builtins/struct.ts +111 -0
- package/src/builtins/tagged-union.ts +142 -0
- package/src/builtins/with-resource.ts +69 -0
- package/src/chain.ts +4 -4
- package/src/handler.ts +12 -28
- package/src/index.ts +24 -17
- package/src/iterator.ts +243 -0
- package/src/option.ts +199 -0
- package/src/pipe.ts +123 -78
- package/src/race.ts +41 -51
- package/src/recursive.ts +44 -27
- package/src/result.ts +168 -0
- package/src/run.ts +53 -25
- package/src/runtime.ts +16 -0
- package/src/schemas.ts +21 -0
- package/src/try-catch.ts +14 -10
- package/src/values.ts +21 -0
- package/src/worker.ts +17 -2
- package/dist/builtins.d.ts +0 -257
- package/dist/builtins.js +0 -600
- package/src/builtins.ts +0 -804
package/dist/ast.js
CHANGED
|
@@ -1,182 +1,227 @@
|
|
|
1
|
+
import { chain } from "./chain.js";
|
|
2
|
+
import { constant, drop, extractPrefix, flatten as flattenBuiltin, getField, getIndex, identity, panic, pick, splitFirst, splitLast, tag, wrapInField, asOption as asOptionStandalone, } from "./builtins/index.js";
|
|
3
|
+
import { Option } from "./option.js";
|
|
4
|
+
import { Result } from "./result.js";
|
|
5
|
+
// Lazy import — iterator.ts imports from ast.ts, but these are only called inside
|
|
6
|
+
// methods (after all modules load), so the circular reference is safe at runtime.
|
|
7
|
+
import { Iterator as IteratorNs } from "./iterator.js";
|
|
8
|
+
// Lazy import — bind.ts imports from ast.ts, but these are only called inside
|
|
9
|
+
// methods (after all modules load), so the circular reference is safe at runtime.
|
|
10
|
+
import { bind as bindStandalone, bindInput as bindInputStandalone, } from "./bind.js";
|
|
11
|
+
/**
|
|
12
|
+
* Strip phantom types from a Pipeable, returning a plain Action.
|
|
13
|
+
*
|
|
14
|
+
* Replaces `x as Action` casts throughout the codebase. The constraint
|
|
15
|
+
* ensures the argument is structurally a Pipeable — unlike a bare cast,
|
|
16
|
+
* `toAction(123)` is a type error.
|
|
17
|
+
*/
|
|
18
|
+
export function toAction(pipeable) {
|
|
19
|
+
return pipeable;
|
|
20
|
+
}
|
|
1
21
|
// ---------------------------------------------------------------------------
|
|
2
22
|
// typedAction — attach .then() and .forEach() as non-enumerable methods
|
|
3
23
|
// ---------------------------------------------------------------------------
|
|
4
24
|
// Shared implementations (one closure, not per-instance)
|
|
5
25
|
function thenMethod(next) {
|
|
6
|
-
return
|
|
7
|
-
}
|
|
8
|
-
function forEachMethod(action) {
|
|
9
|
-
return typedAction({
|
|
10
|
-
kind: "Chain",
|
|
11
|
-
first: this,
|
|
12
|
-
rest: { kind: "ForEach", action },
|
|
13
|
-
});
|
|
26
|
+
return chain(this, next);
|
|
14
27
|
}
|
|
15
28
|
function branchMethod(cases) {
|
|
16
|
-
return
|
|
17
|
-
kind: "Chain",
|
|
18
|
-
first: this,
|
|
19
|
-
rest: { kind: "Branch", cases: unwrapBranchCases(cases) },
|
|
20
|
-
});
|
|
29
|
+
return chain(toAction(this), toAction(branch(cases)));
|
|
21
30
|
}
|
|
22
31
|
function flattenMethod() {
|
|
23
|
-
return
|
|
24
|
-
kind: "Chain",
|
|
25
|
-
first: this,
|
|
26
|
-
rest: {
|
|
27
|
-
kind: "Invoke",
|
|
28
|
-
handler: { kind: "Builtin", builtin: { kind: "Flatten" } },
|
|
29
|
-
},
|
|
30
|
-
});
|
|
32
|
+
return chain(toAction(this), toAction(flattenBuiltin()));
|
|
31
33
|
}
|
|
32
34
|
function dropMethod() {
|
|
33
|
-
return
|
|
34
|
-
kind: "Chain",
|
|
35
|
-
first: this,
|
|
36
|
-
rest: {
|
|
37
|
-
kind: "Invoke",
|
|
38
|
-
handler: { kind: "Builtin", builtin: { kind: "Drop" } },
|
|
39
|
-
},
|
|
40
|
-
});
|
|
35
|
+
return chain(toAction(this), toAction(drop));
|
|
41
36
|
}
|
|
42
|
-
function tagMethod(kind) {
|
|
43
|
-
return
|
|
44
|
-
kind: "Chain",
|
|
45
|
-
first: this,
|
|
46
|
-
rest: {
|
|
47
|
-
kind: "Invoke",
|
|
48
|
-
handler: { kind: "Builtin", builtin: { kind: "Tag", value: kind } },
|
|
49
|
-
},
|
|
50
|
-
});
|
|
37
|
+
function tagMethod(kind, enumName) {
|
|
38
|
+
return chain(toAction(this), toAction(tag(kind, enumName)));
|
|
51
39
|
}
|
|
52
|
-
function
|
|
53
|
-
return
|
|
54
|
-
kind: "Chain",
|
|
55
|
-
first: this,
|
|
56
|
-
rest: {
|
|
57
|
-
kind: "Invoke",
|
|
58
|
-
handler: {
|
|
59
|
-
kind: "Builtin",
|
|
60
|
-
builtin: { kind: "ExtractField", value: field },
|
|
61
|
-
},
|
|
62
|
-
},
|
|
63
|
-
});
|
|
40
|
+
function someMethod() {
|
|
41
|
+
return chain(toAction(this), toAction(Option.some()));
|
|
64
42
|
}
|
|
65
|
-
function
|
|
66
|
-
|
|
67
|
-
// "this" is the sub-pipeline. augment() wraps it so the original input
|
|
68
|
-
// flows through identity alongside the sub-pipeline, then merges the results.
|
|
69
|
-
return typedAction({
|
|
70
|
-
kind: "Chain",
|
|
71
|
-
first: {
|
|
72
|
-
kind: "All",
|
|
73
|
-
actions: [
|
|
74
|
-
this,
|
|
75
|
-
{
|
|
76
|
-
kind: "Invoke",
|
|
77
|
-
handler: { kind: "Builtin", builtin: { kind: "Identity" } },
|
|
78
|
-
},
|
|
79
|
-
],
|
|
80
|
-
},
|
|
81
|
-
rest: {
|
|
82
|
-
kind: "Invoke",
|
|
83
|
-
handler: { kind: "Builtin", builtin: { kind: "Merge" } },
|
|
84
|
-
},
|
|
85
|
-
});
|
|
43
|
+
function okMethod() {
|
|
44
|
+
return chain(toAction(this), toAction(Result.ok()));
|
|
86
45
|
}
|
|
87
|
-
function
|
|
88
|
-
return
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
46
|
+
function errMethod() {
|
|
47
|
+
return chain(toAction(this), toAction(Result.err()));
|
|
48
|
+
}
|
|
49
|
+
function getFieldMethod(field) {
|
|
50
|
+
return chain(toAction(this), toAction(getField(field)));
|
|
51
|
+
}
|
|
52
|
+
function getIndexMethod(index) {
|
|
53
|
+
return chain(toAction(this), toAction(getIndex(index)));
|
|
54
|
+
}
|
|
55
|
+
function wrapInFieldMethod(field) {
|
|
56
|
+
return chain(toAction(this), toAction(wrapInField(field)));
|
|
96
57
|
}
|
|
97
58
|
function pickMethod(...keys) {
|
|
98
|
-
return
|
|
99
|
-
kind: "Chain",
|
|
100
|
-
first: this,
|
|
101
|
-
rest: {
|
|
102
|
-
kind: "Invoke",
|
|
103
|
-
handler: { kind: "Builtin", builtin: { kind: "Pick", value: keys } },
|
|
104
|
-
},
|
|
105
|
-
});
|
|
59
|
+
return chain(toAction(this), toAction(pick(...keys)));
|
|
106
60
|
}
|
|
107
|
-
function
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
return typedAction({
|
|
113
|
-
kind: "Chain",
|
|
114
|
-
first: this,
|
|
115
|
-
rest: {
|
|
116
|
-
kind: "Branch",
|
|
117
|
-
cases: unwrapBranchCases({
|
|
118
|
-
Some: {
|
|
119
|
-
kind: "Chain",
|
|
120
|
-
first: action,
|
|
121
|
-
rest: {
|
|
122
|
-
kind: "Invoke",
|
|
123
|
-
handler: {
|
|
124
|
-
kind: "Builtin",
|
|
125
|
-
builtin: { kind: "Tag", value: "Some" },
|
|
126
|
-
},
|
|
127
|
-
},
|
|
128
|
-
},
|
|
129
|
-
None: {
|
|
130
|
-
kind: "Invoke",
|
|
131
|
-
handler: { kind: "Builtin", builtin: { kind: "Tag", value: "None" } },
|
|
132
|
-
},
|
|
133
|
-
}),
|
|
134
|
-
},
|
|
135
|
-
});
|
|
61
|
+
function splitFirstMethod() {
|
|
62
|
+
return chain(toAction(this), toAction(branchFamily({
|
|
63
|
+
Iterator: IteratorNs.splitFirst(),
|
|
64
|
+
Array: splitFirst(),
|
|
65
|
+
})));
|
|
136
66
|
}
|
|
137
|
-
function
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
67
|
+
function splitLastMethod() {
|
|
68
|
+
return chain(toAction(this), toAction(branchFamily({
|
|
69
|
+
Iterator: IteratorNs.splitLast(),
|
|
70
|
+
Array: splitLast(),
|
|
71
|
+
})));
|
|
72
|
+
}
|
|
73
|
+
// --- Shared postfix methods (Option + Result) — dispatch via branchFamily ---
|
|
74
|
+
function mapMethod(action) {
|
|
75
|
+
return chain(toAction(this), toAction(branchFamily({
|
|
76
|
+
Result: branch({
|
|
77
|
+
Ok: chain(toAction(action), toAction(Result.ok())),
|
|
78
|
+
Err: Result.err(),
|
|
79
|
+
}),
|
|
80
|
+
Option: branch({
|
|
81
|
+
Some: chain(toAction(action), toAction(Option.some())),
|
|
82
|
+
None: Option.none(),
|
|
83
|
+
}),
|
|
84
|
+
Iterator: IteratorNs.map(action),
|
|
85
|
+
})));
|
|
86
|
+
}
|
|
87
|
+
function unwrapMethod() {
|
|
88
|
+
return chain(toAction(this), toAction(branchFamily({
|
|
89
|
+
Result: branch({ Ok: identity(), Err: panic("called unwrap on Err") }),
|
|
90
|
+
Option: branch({
|
|
91
|
+
Some: identity(),
|
|
92
|
+
None: panic("called unwrap on None"),
|
|
93
|
+
}),
|
|
94
|
+
})));
|
|
163
95
|
}
|
|
164
96
|
function unwrapOrMethod(defaultAction) {
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
97
|
+
return chain(toAction(this), toAction(branchFamily({
|
|
98
|
+
Result: branch({ Ok: identity(), Err: defaultAction }),
|
|
99
|
+
Option: branch({ Some: identity(), None: defaultAction }),
|
|
100
|
+
})));
|
|
101
|
+
}
|
|
102
|
+
function andThenMethod(action) {
|
|
103
|
+
return chain(toAction(this), toAction(branchFamily({
|
|
104
|
+
Result: branch({ Ok: action, Err: Result.err() }),
|
|
105
|
+
Option: branch({ Some: action, None: Option.none() }),
|
|
106
|
+
})));
|
|
107
|
+
}
|
|
108
|
+
function transposeMethod() {
|
|
109
|
+
return chain(toAction(this), toAction(branchFamily({
|
|
110
|
+
Option: branch({
|
|
111
|
+
Some: branch({
|
|
112
|
+
Ok: chain(toAction(Option.some()), toAction(Result.ok())),
|
|
113
|
+
Err: Result.err(),
|
|
177
114
|
}),
|
|
178
|
-
|
|
179
|
-
|
|
115
|
+
None: chain(toAction(chain(toAction(drop), toAction(Option.none()))), toAction(Result.ok())),
|
|
116
|
+
}),
|
|
117
|
+
Result: branch({
|
|
118
|
+
Ok: branch({
|
|
119
|
+
Some: chain(toAction(Result.ok()), toAction(Option.some())),
|
|
120
|
+
None: chain(toAction(drop), toAction(Option.none())),
|
|
121
|
+
}),
|
|
122
|
+
Err: chain(toAction(Result.err()), toAction(Option.some())),
|
|
123
|
+
}),
|
|
124
|
+
})));
|
|
125
|
+
}
|
|
126
|
+
// --- Result-only postfix methods ---
|
|
127
|
+
function mapErrMethod(action) {
|
|
128
|
+
return chain(toAction(this), toAction(branch({
|
|
129
|
+
Ok: Result.ok(),
|
|
130
|
+
Err: chain(toAction(action), toAction(Result.err())),
|
|
131
|
+
})));
|
|
132
|
+
}
|
|
133
|
+
function orMethod(fallback) {
|
|
134
|
+
return chain(toAction(this), toAction(branch({
|
|
135
|
+
Ok: Result.ok(),
|
|
136
|
+
Err: fallback,
|
|
137
|
+
})));
|
|
138
|
+
}
|
|
139
|
+
function asOkOptionMethod() {
|
|
140
|
+
return chain(toAction(this), toAction(branch({
|
|
141
|
+
Ok: Option.some(),
|
|
142
|
+
Err: chain(toAction(drop), toAction(Option.none())),
|
|
143
|
+
})));
|
|
144
|
+
}
|
|
145
|
+
function asErrOptionMethod() {
|
|
146
|
+
return chain(toAction(this), toAction(branch({
|
|
147
|
+
Ok: chain(toAction(drop), toAction(Option.none())),
|
|
148
|
+
Err: Option.some(),
|
|
149
|
+
})));
|
|
150
|
+
}
|
|
151
|
+
function isOkMethod() {
|
|
152
|
+
return chain(toAction(this), toAction(branch({
|
|
153
|
+
Ok: constant(true),
|
|
154
|
+
Err: constant(false),
|
|
155
|
+
})));
|
|
156
|
+
}
|
|
157
|
+
function isErrMethod() {
|
|
158
|
+
return chain(toAction(this), toAction(branch({
|
|
159
|
+
Ok: constant(false),
|
|
160
|
+
Err: constant(true),
|
|
161
|
+
})));
|
|
162
|
+
}
|
|
163
|
+
// --- Option-only postfix methods ---
|
|
164
|
+
function filterMethod(predicate) {
|
|
165
|
+
return chain(toAction(this), toAction(branchFamily({
|
|
166
|
+
Option: branch({
|
|
167
|
+
Some: predicate,
|
|
168
|
+
None: Option.none(),
|
|
169
|
+
}),
|
|
170
|
+
Iterator: IteratorNs.filter(predicate),
|
|
171
|
+
})));
|
|
172
|
+
}
|
|
173
|
+
function isSomeMethod() {
|
|
174
|
+
return chain(toAction(this), toAction(branch({
|
|
175
|
+
Some: constant(true),
|
|
176
|
+
None: constant(false),
|
|
177
|
+
})));
|
|
178
|
+
}
|
|
179
|
+
function isNoneMethod() {
|
|
180
|
+
return chain(toAction(this), toAction(branch({
|
|
181
|
+
Some: constant(false),
|
|
182
|
+
None: constant(true),
|
|
183
|
+
})));
|
|
184
|
+
}
|
|
185
|
+
function asOptionMethod() {
|
|
186
|
+
return chain(toAction(this), toAction(asOptionStandalone()));
|
|
187
|
+
}
|
|
188
|
+
// --- Iterator postfix methods ---
|
|
189
|
+
function iterateMethod() {
|
|
190
|
+
return chain(toAction(this), toAction(branchFamily({
|
|
191
|
+
Option: IteratorNs.fromOption(),
|
|
192
|
+
Result: IteratorNs.fromResult(),
|
|
193
|
+
Array: IteratorNs.fromArray(),
|
|
194
|
+
})));
|
|
195
|
+
}
|
|
196
|
+
function flatMapMethod(action) {
|
|
197
|
+
return chain(toAction(this), toAction(IteratorNs.flatMap(action)));
|
|
198
|
+
}
|
|
199
|
+
function collectMethod() {
|
|
200
|
+
return chain(toAction(this), toAction(branchFamily({
|
|
201
|
+
Array: Option.collect(),
|
|
202
|
+
Iterator: IteratorNs.collect(),
|
|
203
|
+
})));
|
|
204
|
+
}
|
|
205
|
+
function foldMethod(init, body) {
|
|
206
|
+
return chain(toAction(this), toAction(IteratorNs.fold(init, body)));
|
|
207
|
+
}
|
|
208
|
+
function isEmptyMethod() {
|
|
209
|
+
return chain(toAction(this), toAction(IteratorNs.isEmpty()));
|
|
210
|
+
}
|
|
211
|
+
function sliceMethod(start, end) {
|
|
212
|
+
return chain(toAction(this), toAction(IteratorNs.slice(start, end)));
|
|
213
|
+
}
|
|
214
|
+
function takeMethod(n) {
|
|
215
|
+
return chain(toAction(this), toAction(IteratorNs.take(n)));
|
|
216
|
+
}
|
|
217
|
+
function skipMethod(n) {
|
|
218
|
+
return chain(toAction(this), toAction(IteratorNs.skip(n)));
|
|
219
|
+
}
|
|
220
|
+
function bindMethod(bindings, body) {
|
|
221
|
+
return chain(toAction(this), toAction(bindStandalone(bindings, body)));
|
|
222
|
+
}
|
|
223
|
+
function bindInputMethod(body) {
|
|
224
|
+
return chain(toAction(this), toAction(bindInputStandalone(body)));
|
|
180
225
|
}
|
|
181
226
|
/**
|
|
182
227
|
* Attach `.then()` and `.forEach()` methods to a plain Action object.
|
|
@@ -186,18 +231,44 @@ export function typedAction(action) {
|
|
|
186
231
|
if (!("then" in action)) {
|
|
187
232
|
Object.defineProperties(action, {
|
|
188
233
|
then: { value: thenMethod, configurable: true },
|
|
189
|
-
forEach: { value: forEachMethod, configurable: true },
|
|
190
234
|
branch: { value: branchMethod, configurable: true },
|
|
191
235
|
flatten: { value: flattenMethod, configurable: true },
|
|
192
236
|
drop: { value: dropMethod, configurable: true },
|
|
193
237
|
tag: { value: tagMethod, configurable: true },
|
|
194
|
-
|
|
195
|
-
|
|
196
|
-
|
|
238
|
+
some: { value: someMethod, configurable: true },
|
|
239
|
+
ok: { value: okMethod, configurable: true },
|
|
240
|
+
err: { value: errMethod, configurable: true },
|
|
241
|
+
getField: { value: getFieldMethod, configurable: true },
|
|
242
|
+
getIndex: { value: getIndexMethod, configurable: true },
|
|
243
|
+
wrapInField: { value: wrapInFieldMethod, configurable: true },
|
|
197
244
|
pick: { value: pickMethod, configurable: true },
|
|
198
|
-
|
|
245
|
+
splitFirst: { value: splitFirstMethod, configurable: true },
|
|
246
|
+
splitLast: { value: splitLastMethod, configurable: true },
|
|
247
|
+
map: { value: mapMethod, configurable: true },
|
|
199
248
|
mapErr: { value: mapErrMethod, configurable: true },
|
|
249
|
+
unwrap: { value: unwrapMethod, configurable: true },
|
|
200
250
|
unwrapOr: { value: unwrapOrMethod, configurable: true },
|
|
251
|
+
andThen: { value: andThenMethod, configurable: true },
|
|
252
|
+
filter: { value: filterMethod, configurable: true },
|
|
253
|
+
isSome: { value: isSomeMethod, configurable: true },
|
|
254
|
+
isNone: { value: isNoneMethod, configurable: true },
|
|
255
|
+
asOption: { value: asOptionMethod, configurable: true },
|
|
256
|
+
collect: { value: collectMethod, configurable: true },
|
|
257
|
+
fold: { value: foldMethod, configurable: true },
|
|
258
|
+
isEmpty: { value: isEmptyMethod, configurable: true },
|
|
259
|
+
slice: { value: sliceMethod, configurable: true },
|
|
260
|
+
take: { value: takeMethod, configurable: true },
|
|
261
|
+
skip: { value: skipMethod, configurable: true },
|
|
262
|
+
or: { value: orMethod, configurable: true },
|
|
263
|
+
iterate: { value: iterateMethod, configurable: true },
|
|
264
|
+
flatMap: { value: flatMapMethod, configurable: true },
|
|
265
|
+
asOkOption: { value: asOkOptionMethod, configurable: true },
|
|
266
|
+
asErrOption: { value: asErrOptionMethod, configurable: true },
|
|
267
|
+
isOk: { value: isOkMethod, configurable: true },
|
|
268
|
+
isErr: { value: isErrMethod, configurable: true },
|
|
269
|
+
transpose: { value: transposeMethod, configurable: true },
|
|
270
|
+
bind: { value: bindMethod, configurable: true },
|
|
271
|
+
bindInput: { value: bindInputMethod, configurable: true },
|
|
201
272
|
});
|
|
202
273
|
}
|
|
203
274
|
return action;
|
|
@@ -215,10 +286,10 @@ import { allocateRestartHandlerId, } from "./effect-id.js";
|
|
|
215
286
|
export { tryCatch } from "./try-catch.js";
|
|
216
287
|
export { race, sleep, withTimeout } from "./race.js";
|
|
217
288
|
export function forEach(action) {
|
|
218
|
-
return typedAction({ kind: "ForEach", action: action });
|
|
289
|
+
return typedAction({ kind: "ForEach", action: toAction(action) });
|
|
219
290
|
}
|
|
220
291
|
/**
|
|
221
|
-
* Insert
|
|
292
|
+
* Insert GetField("value") before each case handler in a branch.
|
|
222
293
|
* This implements auto-unwrapping: the engine dispatches on `kind`, then
|
|
223
294
|
* extracts `value` before passing to the handler. Case handlers receive
|
|
224
295
|
* the payload directly, not the full `{ kind, value }` variant.
|
|
@@ -226,17 +297,7 @@ export function forEach(action) {
|
|
|
226
297
|
function unwrapBranchCases(cases) {
|
|
227
298
|
const unwrapped = {};
|
|
228
299
|
for (const key of Object.keys(cases)) {
|
|
229
|
-
unwrapped[key] =
|
|
230
|
-
kind: "Chain",
|
|
231
|
-
first: {
|
|
232
|
-
kind: "Invoke",
|
|
233
|
-
handler: {
|
|
234
|
-
kind: "Builtin",
|
|
235
|
-
builtin: { kind: "ExtractField", value: "value" },
|
|
236
|
-
},
|
|
237
|
-
},
|
|
238
|
-
rest: cases[key],
|
|
239
|
-
};
|
|
300
|
+
unwrapped[key] = toAction(chain(toAction(getField("value")), toAction(cases[key])));
|
|
240
301
|
}
|
|
241
302
|
return unwrapped;
|
|
242
303
|
}
|
|
@@ -244,25 +305,21 @@ function unwrapBranchCases(cases) {
|
|
|
244
305
|
export function branch(cases) {
|
|
245
306
|
return typedAction({ kind: "Branch", cases: unwrapBranchCases(cases) });
|
|
246
307
|
}
|
|
247
|
-
|
|
248
|
-
|
|
249
|
-
|
|
250
|
-
|
|
251
|
-
|
|
252
|
-
|
|
253
|
-
}
|
|
254
|
-
|
|
255
|
-
|
|
256
|
-
|
|
257
|
-
|
|
258
|
-
|
|
259
|
-
|
|
260
|
-
|
|
261
|
-
}
|
|
262
|
-
export const IDENTITY = {
|
|
263
|
-
kind: "Invoke",
|
|
264
|
-
handler: { kind: "Builtin", builtin: { kind: "Identity" } },
|
|
265
|
-
};
|
|
308
|
+
/**
|
|
309
|
+
* Two-level dispatch: extract the enum prefix from a tagged value's `kind`,
|
|
310
|
+
* then branch on that prefix. Used by postfix methods (`.map()`, `.unwrapOr()`,
|
|
311
|
+
* etc.) to dispatch across union families (Option, Result) without runtime
|
|
312
|
+
* metadata.
|
|
313
|
+
*
|
|
314
|
+
* `branchFamily({ Result: ..., Option: ... })` ≡ `chain(extractPrefix(), branch(cases))`
|
|
315
|
+
*/
|
|
316
|
+
export function branchFamily(cases) {
|
|
317
|
+
return typedAction({
|
|
318
|
+
kind: "Chain",
|
|
319
|
+
first: toAction(extractPrefix()),
|
|
320
|
+
rest: toAction(branch(cases)),
|
|
321
|
+
});
|
|
322
|
+
}
|
|
266
323
|
// ---------------------------------------------------------------------------
|
|
267
324
|
// recur — restart body primitive
|
|
268
325
|
// ---------------------------------------------------------------------------
|
|
@@ -273,7 +330,7 @@ export const IDENTITY = {
|
|
|
273
330
|
* If the body completes normally → output is TOut.
|
|
274
331
|
* If restart fires → body re-executes with the restarted value.
|
|
275
332
|
*
|
|
276
|
-
* Compiled form: `RestartHandle(id,
|
|
333
|
+
* Compiled form: `RestartHandle(id, GetIndex(0), body)`
|
|
277
334
|
*/
|
|
278
335
|
export function recur(bodyFn) {
|
|
279
336
|
const restartHandlerId = allocateRestartHandlerId();
|
|
@@ -281,12 +338,12 @@ export function recur(bodyFn) {
|
|
|
281
338
|
kind: "RestartPerform",
|
|
282
339
|
restart_handler_id: restartHandlerId,
|
|
283
340
|
});
|
|
284
|
-
const body = bodyFn(restartAction);
|
|
341
|
+
const body = toAction(bodyFn(restartAction));
|
|
285
342
|
return typedAction({
|
|
286
343
|
kind: "RestartHandle",
|
|
287
344
|
restart_handler_id: restartHandlerId,
|
|
288
345
|
body,
|
|
289
|
-
handler:
|
|
346
|
+
handler: toAction(getIndex(0).unwrap()),
|
|
290
347
|
});
|
|
291
348
|
}
|
|
292
349
|
// ---------------------------------------------------------------------------
|
|
@@ -306,20 +363,19 @@ export function recur(bodyFn) {
|
|
|
306
363
|
*/
|
|
307
364
|
export function earlyReturn(bodyFn) {
|
|
308
365
|
const restartHandlerId = allocateRestartHandlerId();
|
|
309
|
-
const earlyReturnAction = typedAction({
|
|
310
|
-
kind: "
|
|
311
|
-
|
|
312
|
-
|
|
313
|
-
|
|
314
|
-
|
|
315
|
-
return typedAction(buildRestartBranchAction(restartHandlerId, body, IDENTITY));
|
|
366
|
+
const earlyReturnAction = typedAction(toAction(chain(toAction(tag("Break", "LoopResult")), {
|
|
367
|
+
kind: "RestartPerform",
|
|
368
|
+
restart_handler_id: restartHandlerId,
|
|
369
|
+
})));
|
|
370
|
+
const body = toAction(bodyFn(earlyReturnAction));
|
|
371
|
+
return typedAction(buildRestartBranchAction(restartHandlerId, body, toAction(identity())));
|
|
316
372
|
}
|
|
317
373
|
// ---------------------------------------------------------------------------
|
|
318
374
|
// loop — iterative restart with break
|
|
319
375
|
// ---------------------------------------------------------------------------
|
|
320
376
|
/**
|
|
321
377
|
* Build the restart+branch compiled form:
|
|
322
|
-
* `Chain(Tag("Continue"), RestartHandle(id,
|
|
378
|
+
* `Chain(Tag("Continue"), RestartHandle(id, GetIndex(0), Branch({ Continue: continueArm, Break: breakArm })))`
|
|
323
379
|
*
|
|
324
380
|
* Input is tagged Continue so the Branch enters the continueArm on first execution.
|
|
325
381
|
* Continue tag → restart → re-enters continueArm. Break tag → restart → runs breakArm, exits `RestartHandle`.
|
|
@@ -327,22 +383,12 @@ export function earlyReturn(bodyFn) {
|
|
|
327
383
|
* Used by earlyReturn, loop, tryCatch, and race.
|
|
328
384
|
*/
|
|
329
385
|
export function buildRestartBranchAction(restartHandlerId, continueArm, breakArm) {
|
|
330
|
-
return {
|
|
331
|
-
kind: "
|
|
332
|
-
|
|
333
|
-
|
|
334
|
-
|
|
335
|
-
|
|
336
|
-
body: {
|
|
337
|
-
kind: "Branch",
|
|
338
|
-
cases: unwrapBranchCases({
|
|
339
|
-
Continue: continueArm,
|
|
340
|
-
Break: breakArm,
|
|
341
|
-
}),
|
|
342
|
-
},
|
|
343
|
-
handler: EXTRACT_PAYLOAD,
|
|
344
|
-
},
|
|
345
|
-
};
|
|
386
|
+
return toAction(chain(toAction(tag("Continue", "LoopResult")), {
|
|
387
|
+
kind: "RestartHandle",
|
|
388
|
+
restart_handler_id: restartHandlerId,
|
|
389
|
+
body: toAction(branch({ Continue: continueArm, Break: breakArm })),
|
|
390
|
+
handler: toAction(getIndex(0).unwrap()),
|
|
391
|
+
}));
|
|
346
392
|
}
|
|
347
393
|
/**
|
|
348
394
|
* Iterative loop. The body callback receives `recur` and `done`:
|
|
@@ -359,18 +405,10 @@ export function loop(bodyFn) {
|
|
|
359
405
|
kind: "RestartPerform",
|
|
360
406
|
restart_handler_id: restartHandlerId,
|
|
361
407
|
};
|
|
362
|
-
const recurAction = typedAction(
|
|
363
|
-
|
|
364
|
-
|
|
365
|
-
|
|
366
|
-
});
|
|
367
|
-
const doneAction = typedAction({
|
|
368
|
-
kind: "Chain",
|
|
369
|
-
first: TAG_BREAK,
|
|
370
|
-
rest: perform,
|
|
371
|
-
});
|
|
372
|
-
const body = bodyFn(recurAction, doneAction);
|
|
373
|
-
return typedAction(buildRestartBranchAction(restartHandlerId, body, IDENTITY));
|
|
408
|
+
const recurAction = typedAction(toAction(chain(toAction(tag("Continue", "LoopResult")), toAction(perform))));
|
|
409
|
+
const doneAction = typedAction(toAction(chain(toAction(tag("Break", "LoopResult")), toAction(perform))));
|
|
410
|
+
const body = toAction(bodyFn(recurAction, doneAction));
|
|
411
|
+
return typedAction(buildRestartBranchAction(restartHandlerId, body, toAction(identity())));
|
|
374
412
|
}
|
|
375
413
|
// ---------------------------------------------------------------------------
|
|
376
414
|
// Config builders
|
package/dist/bind.d.ts
CHANGED
|
@@ -3,20 +3,17 @@ import { type Action, type ExtractInput, type ExtractOutput, type TypedAction }
|
|
|
3
3
|
* A typed reference to a bound value. Output is `TValue`.
|
|
4
4
|
*
|
|
5
5
|
* Use `.then()` (not `pipe()`) when chaining a VarRef into a generic
|
|
6
|
-
* action like `pick` or `
|
|
6
|
+
* action like `pick` or `getField` — pipe overloads can't infer
|
|
7
7
|
* the generic's type parameter from the VarRef's output.
|
|
8
8
|
*/
|
|
9
|
-
export type VarRef<TValue> = TypedAction<
|
|
9
|
+
export type VarRef<TValue> = TypedAction<any, TValue>;
|
|
10
10
|
/**
|
|
11
11
|
* Maps each binding's output type to a VarRef. TypeScript resolves
|
|
12
12
|
* ExtractOutput from each binding expression.
|
|
13
13
|
*
|
|
14
|
-
* Constraint is `Action[]` (not `Pipeable<any, any>[]`)
|
|
15
|
-
* `
|
|
16
|
-
*
|
|
17
|
-
* Action union. Using raw `Action[]` avoids the phantom field
|
|
18
|
-
* assignability issue while `ExtractOutput` still extracts the correct
|
|
19
|
-
* output type from the phantom fields on the concrete types.
|
|
14
|
+
* Constraint is `Action[]` (not `Pipeable<any, any>[]`) so that
|
|
15
|
+
* `ExtractOutput` extracts the correct output type from the phantom
|
|
16
|
+
* fields on the concrete types without fighting invariant `__in` checks.
|
|
20
17
|
*/
|
|
21
18
|
export type InferVarRefs<TBindings extends Action[]> = {
|
|
22
19
|
[K in keyof TBindings]: VarRef<ExtractOutput<TBindings[K]>>;
|
|
@@ -33,19 +30,18 @@ export type InferVarRefs<TBindings extends Action[]> = {
|
|
|
33
30
|
* All(...bindings, Identity),
|
|
34
31
|
* ResumeHandle(r0, readVar(0),
|
|
35
32
|
* ResumeHandle(r1, readVar(1),
|
|
36
|
-
* Chain(
|
|
33
|
+
* Chain(GetIndex(N), body)
|
|
37
34
|
* )
|
|
38
35
|
* )
|
|
39
36
|
* )
|
|
40
37
|
*/
|
|
41
38
|
/**
|
|
42
39
|
* Constraint for the body callback return type. Only requires the output
|
|
43
|
-
* phantom
|
|
44
|
-
*
|
|
40
|
+
* phantom field — omits `__in` and `__in_co` so that body actions with
|
|
41
|
+
* any input type (e.g. pipelines starting from a VarRef) are assignable.
|
|
45
42
|
*/
|
|
46
43
|
type BodyResult<TOut> = Action & {
|
|
47
44
|
__out?: () => TOut;
|
|
48
|
-
__out_contra?: (output: TOut) => void;
|
|
49
45
|
};
|
|
50
46
|
export declare function bind<TBindings extends Action[], TOut>(bindings: [...TBindings], body: (vars: InferVarRefs<TBindings>) => BodyResult<TOut>): TypedAction<ExtractInput<TBindings[number]>, TOut>;
|
|
51
47
|
/**
|
|
@@ -60,3 +56,4 @@ export declare function bind<TBindings extends Action[], TOut>(bindings: [...TBi
|
|
|
60
56
|
*/
|
|
61
57
|
export declare function bindInput<TIn, TOut = any>(body: (input: VarRef<TIn>) => BodyResult<TOut>): TypedAction<TIn, TOut>;
|
|
62
58
|
export {};
|
|
59
|
+
//# sourceMappingURL=bind.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"bind.d.ts","sourceRoot":"","sources":["../src/bind.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,KAAK,MAAM,EACX,KAAK,YAAY,EACjB,KAAK,aAAa,EAClB,KAAK,WAAW,EAGjB,MAAM,UAAU,CAAC;AAWlB;;;;;;GAMG;AACH,MAAM,MAAM,MAAM,CAAC,MAAM,IAAI,WAAW,CAAC,GAAG,EAAE,MAAM,CAAC,CAAC;AAetD;;;;;;;GAOG;AACH,MAAM,MAAM,YAAY,CAAC,SAAS,SAAS,MAAM,EAAE,IAAI;KACpD,CAAC,IAAI,MAAM,SAAS,GAAG,MAAM,CAAC,aAAa,CAAC,SAAS,CAAC,CAAC,CAAC,CAAC,CAAC;CAC5D,CAAC;AA4BF;;;;;;;;;;;;;;;;GAgBG;AACH;;;;GAIG;AACH,KAAK,UAAU,CAAC,IAAI,IAAI,MAAM,GAAG;IAC/B,KAAK,CAAC,EAAE,MAAM,IAAI,CAAC;CACpB,CAAC;AAEF,wBAAgB,IAAI,CAAC,SAAS,SAAS,MAAM,EAAE,EAAE,IAAI,EACnD,QAAQ,EAAE,CAAC,GAAG,SAAS,CAAC,EACxB,IAAI,EAAE,CAAC,IAAI,EAAE,YAAY,CAAC,SAAS,CAAC,KAAK,UAAU,CAAC,IAAI,CAAC,GACxD,WAAW,CAAC,YAAY,CAAC,SAAS,CAAC,MAAM,CAAC,CAAC,EAAE,IAAI,CAAC,CAkCpD;AAMD;;;;;;;;;GASG;AACH,wBAAgB,SAAS,CAAC,GAAG,EAAE,IAAI,GAAG,GAAG,EACvC,IAAI,EAAE,CAAC,KAAK,EAAE,MAAM,CAAC,GAAG,CAAC,KAAK,UAAU,CAAC,IAAI,CAAC,GAC7C,WAAW,CAAC,GAAG,EAAE,IAAI,CAAC,CAExB"}
|