@smthrs/flow 1.0.0-rc.5 → 1.0.0-rc.7
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/CHANGELOG.md +1 -0
- package/README.md +4 -4
- package/dist/cjs/DurableDeferred.js +3 -3
- package/dist/cjs/DurableDeferred.js.map +2 -2
- package/dist/cjs/DurableQueue.d.ts +1 -1
- package/dist/cjs/DurableQueue.d.ts.map +1 -1
- package/dist/cjs/DurableQueue.js +2 -2
- package/dist/cjs/DurableQueue.js.map +2 -2
- package/dist/cjs/Flow/ExecutionIds.js +1 -1
- package/dist/cjs/Flow/ExecutionIds.js.map +2 -2
- package/dist/cjs/Flow/Result.d.ts +1 -1
- package/dist/cjs/Flow/Result.d.ts.map +1 -1
- package/dist/cjs/Flow/Result.js.map +2 -2
- package/dist/cjs/Flow/Runtime.js +1 -1
- package/dist/cjs/Flow/Runtime.js.map +2 -2
- package/dist/cjs/Flow/internal.js +1 -1
- package/dist/cjs/Flow/internal.js.map +2 -2
- package/dist/cjs/Graph.d.ts.map +1 -1
- package/dist/cjs/Graph.js +1 -2
- package/dist/cjs/Graph.js.map +2 -2
- package/dist/esm/DurableDeferred.js +3 -3
- package/dist/esm/DurableDeferred.js.map +1 -1
- package/dist/esm/DurableQueue.d.ts +1 -1
- package/dist/esm/DurableQueue.d.ts.map +1 -1
- package/dist/esm/DurableQueue.js +2 -2
- package/dist/esm/DurableQueue.js.map +1 -1
- package/dist/esm/Flow/ExecutionIds.js +1 -1
- package/dist/esm/Flow/ExecutionIds.js.map +1 -1
- package/dist/esm/Flow/Result.d.ts +1 -1
- package/dist/esm/Flow/Result.d.ts.map +1 -1
- package/dist/esm/Flow/Result.js.map +1 -1
- package/dist/esm/Flow/Runtime.js +1 -1
- package/dist/esm/Flow/Runtime.js.map +1 -1
- package/dist/esm/Flow/internal.js +1 -1
- package/dist/esm/Flow/internal.js.map +1 -1
- package/dist/esm/Graph.d.ts.map +1 -1
- package/dist/esm/Graph.js +4 -2
- package/dist/esm/Graph.js.map +1 -1
- package/docs/README.md +1 -1
- package/docs/guides/implement-an-action.md +13 -5
- package/docs/guides/inspect-the-plan.md +92 -11
- package/docs/installation.md +4 -4
- package/docs/reference/flow.md +1 -1
- package/package.json +10 -10
- package/src/DurableDeferred.ts +3 -3
- package/src/DurableQueue.ts +2 -2
- package/src/Flow/ExecutionIds.ts +1 -1
- package/src/Flow/Result.ts +1 -1
- package/src/Flow/Runtime.ts +1 -1
- package/src/Flow/internal.ts +1 -1
- package/src/Graph.ts +5 -2
|
@@ -68,11 +68,19 @@ fails to compile the same way a missing action implementation does.
|
|
|
68
68
|
The tier tells the engine what retrying this action means. It is part of the step
|
|
69
69
|
key, so it is not a hint.
|
|
70
70
|
|
|
71
|
-
| Tier | Choose it when | What the engine does
|
|
72
|
-
| -------------- | ----------------------------------------------------- |
|
|
73
|
-
| `sealed` | The result is a pure function of the declared inputs. | Records the result and replays it. With the right declarations, reuses it across runs.
|
|
74
|
-
| `compensable` | The body changes the workspace. | Takes a pre-image before each attempt and restores it before the next one, so attempt two does not trip over attempt one's half-written files. Requires a `FlowEngine.SnapshotBoundary` in context, which [`@smthrs/engine-store`](/api/engine-store) supplies. |
|
|
75
|
-
| `irreversible` | The body changes the world outside the workspace. | Refuses to retry without a declared `idempotencyKey`, dying with `IrreversibleRetryRequiresIdempotencyKey`.
|
|
71
|
+
| Tier | Choose it when | What the engine does |
|
|
72
|
+
| -------------- | ----------------------------------------------------- | -------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
|
|
73
|
+
| `sealed` | The result is a pure function of the declared inputs. | Records the result and replays it. With the right declarations, reuses it across runs. |
|
|
74
|
+
| `compensable` | The body changes the workspace. | Takes a pre-image before each attempt and restores it before the next one, so attempt two does not trip over attempt one's half-written files. Requires a `FlowEngine.SnapshotBoundary` in context, which [`@smthrs/engine-store`](/api/engine-store) supplies, and a workspace that is a jj repository. |
|
|
75
|
+
| `irreversible` | The body changes the world outside the workspace. | Refuses to retry without a declared `idempotencyKey`, dying with `IrreversibleRetryRequiresIdempotencyKey`. |
|
|
76
|
+
|
|
77
|
+
The `compensable` pre-image is a jj snapshot of the workspace, so the
|
|
78
|
+
workspace must be a jj repository: run `jj git init` in it first. Without one,
|
|
79
|
+
the step dies before its first attempt runs:
|
|
80
|
+
|
|
81
|
+
```text
|
|
82
|
+
@smthrs/jj/JjError: jj snapshot: Error: There is no jj repo in "."
|
|
83
|
+
```
|
|
76
84
|
|
|
77
85
|
`sealed` is the default, and it is a claim about the body: this result is worth
|
|
78
86
|
replaying. Add `nondeterministic: true` when several legitimate results may race
|
|
@@ -11,15 +11,57 @@ tool to reach for when a step key changed unexpectedly, when a branch took the
|
|
|
11
11
|
arm you did not expect, or when you want to show an operator what a run is about
|
|
12
12
|
to do.
|
|
13
13
|
|
|
14
|
+
## Before you start
|
|
15
|
+
|
|
16
|
+
The examples run with `node <file>.ts` on Node.js 26.4.0 or later and need no
|
|
17
|
+
engine, database, or jj: planning reads declarations only. They import
|
|
18
|
+
`@smthrs/flow` and `@smthrs/plan`. In a project that installed `@smthrs/flows`,
|
|
19
|
+
add both at the version of `@smthrs/flows` you have:
|
|
20
|
+
|
|
21
|
+
```bash
|
|
22
|
+
npm install @smthrs/flow@1.0.0-rc.7 @smthrs/plan@1.0.0-rc.7
|
|
23
|
+
```
|
|
24
|
+
|
|
25
|
+
`@smthrs/flows` re-exports the same modules, so `import { Graph } from "@smthrs/flows"`
|
|
26
|
+
and its `Plan.Node` work too. The outputs below are real output from 1.0.0-rc.6.
|
|
27
|
+
|
|
14
28
|
## Build the graph
|
|
15
29
|
|
|
30
|
+
Create `inspect.ts`. The flow runs two checks in parallel, joins them into a
|
|
31
|
+
report, and then ships or explains:
|
|
32
|
+
|
|
16
33
|
```ts
|
|
17
|
-
import { Graph } from "@smthrs/flow"
|
|
34
|
+
import { Action, Flow, Graph } from "@smthrs/flow"
|
|
35
|
+
import { Node } from "@smthrs/plan"
|
|
36
|
+
import * as Schema from "effect/Schema"
|
|
37
|
+
|
|
38
|
+
const Lint = Action.make("release/Lint", { payload: { target: Schema.String }, success: Schema.String })
|
|
39
|
+
const Types = Action.make("release/Types", { payload: { target: Schema.String }, success: Schema.String })
|
|
40
|
+
const Report = Action.make("release/Report", {
|
|
41
|
+
payload: { lint: Schema.String, types: Schema.String },
|
|
42
|
+
success: Schema.String
|
|
43
|
+
})
|
|
44
|
+
const Ship = Action.make("release/Ship", { payload: { report: Schema.String }, success: Schema.String })
|
|
45
|
+
const Explain = Action.make("release/Explain", { payload: { reason: Schema.String }, success: Schema.String })
|
|
46
|
+
|
|
47
|
+
const Release = Flow.make("release/Release", {
|
|
48
|
+
payload: { target: Schema.String },
|
|
49
|
+
success: Schema.String,
|
|
50
|
+
body: ({ target }) =>
|
|
51
|
+
Node.all({ lint: Lint.call({ target }), types: Types.call({ target }) }).pipe(
|
|
52
|
+
Node.bindPlanned((checks) => Report.call({ lint: checks.lint, types: checks.types })),
|
|
53
|
+
Node.branch({
|
|
54
|
+
if: (report) => report.includes("clean"),
|
|
55
|
+
then: (report) => Ship.call({ report }),
|
|
56
|
+
else: (reason) => Explain.call({ reason })
|
|
57
|
+
})
|
|
58
|
+
)
|
|
59
|
+
})
|
|
18
60
|
|
|
19
61
|
const graph = Graph.build(Release, { target: "web" })
|
|
20
62
|
|
|
21
63
|
for (const node of Graph.nodes(graph)) {
|
|
22
|
-
console.log(node.id
|
|
64
|
+
console.log(`${node.id} ${node.kind} [${node.dependencies.join(", ")}]`)
|
|
23
65
|
}
|
|
24
66
|
|
|
25
67
|
for (const edge of Graph.edges(graph)) {
|
|
@@ -27,6 +69,33 @@ for (const edge of Graph.edges(graph)) {
|
|
|
27
69
|
}
|
|
28
70
|
```
|
|
29
71
|
|
|
72
|
+
```bash
|
|
73
|
+
node inspect.ts
|
|
74
|
+
```
|
|
75
|
+
|
|
76
|
+
```text
|
|
77
|
+
root.flow.branch.andThen.all.lint ActionCall []
|
|
78
|
+
root.flow.branch.andThen.all.types ActionCall []
|
|
79
|
+
root.flow.branch.andThen All [root.flow.branch.andThen.all.lint, root.flow.branch.andThen.all.types]
|
|
80
|
+
root.flow.branch.then ActionCall [root.flow.branch.andThen]
|
|
81
|
+
root.flow.branch AndThen [root.flow.branch.andThen, root.flow.branch.then]
|
|
82
|
+
root.flow.then ActionCall [root.flow.branch]
|
|
83
|
+
root.flow.else ActionCall [root.flow.branch]
|
|
84
|
+
root.flow Branch [root.flow.branch, root.flow.then, root.flow.else]
|
|
85
|
+
root FlowCall [root.flow]
|
|
86
|
+
root.flow.branch.andThen.all.lint -> root.flow.branch.andThen (value)
|
|
87
|
+
root.flow.branch.andThen.all.types -> root.flow.branch.andThen (value)
|
|
88
|
+
root.flow.branch.andThen -> root.flow.branch (value)
|
|
89
|
+
root.flow.branch.andThen -> root.flow.branch.then (continuation)
|
|
90
|
+
root.flow.branch.then -> root.flow.branch (value)
|
|
91
|
+
root.flow.branch -> root.flow (value)
|
|
92
|
+
root.flow.branch -> root.flow.then (continuation)
|
|
93
|
+
root.flow.then -> root.flow (value)
|
|
94
|
+
root.flow.branch -> root.flow.else (continuation)
|
|
95
|
+
root.flow.else -> root.flow (value)
|
|
96
|
+
root.flow -> root (value)
|
|
97
|
+
```
|
|
98
|
+
|
|
30
99
|
`Graph.build` takes a flow declaration or a bare node, the payload, and options.
|
|
31
100
|
Nothing runs. It refuses a nesting depth past its bound and a duplicate node id,
|
|
32
101
|
because a node id is durable dispatch identity and two nodes answering to one
|
|
@@ -79,9 +148,14 @@ partial drafts. Check diagnostics before asking for drafts:
|
|
|
79
148
|
const issues = Graph.diagnostics(graph)
|
|
80
149
|
if (issues.length === 0) {
|
|
81
150
|
const drafts = Graph.drafts(graph) // ready for Plan.compile or Plan.append
|
|
151
|
+
console.log(`${drafts.length} drafts`)
|
|
82
152
|
}
|
|
83
153
|
```
|
|
84
154
|
|
|
155
|
+
Appended to `inspect.ts`, it prints `9 drafts`: one per node above.
|
|
156
|
+
[Diff two plans](../../../plan/docs/guides/diff-two-plans.md) compiles drafts like
|
|
157
|
+
these and compares two versions of a flow.
|
|
158
|
+
|
|
85
159
|
## Resolve layers while building
|
|
86
160
|
|
|
87
161
|
`BuildOptions.resolveLayers` is invoked once per node and is told a
|
|
@@ -103,17 +177,22 @@ that read the world would make a plan a function of more than its declarations.
|
|
|
103
177
|
## Drive one interpretation
|
|
104
178
|
|
|
105
179
|
`Interpreter.interpret` builds the graph and walks it against real values,
|
|
106
|
-
without registering the flow. It
|
|
180
|
+
without registering the flow. It is the walk `Interpreter.layer` runs for each
|
|
181
|
+
round of an execution, and it requires the `FlowInstance` the runtime provides
|
|
182
|
+
to an executing round, so a program reaches it through `execute` rather than by
|
|
183
|
+
calling it at top level. It answers an `Interpretation`:
|
|
107
184
|
|
|
108
185
|
```ts
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
186
|
+
interface Interpretation {
|
|
187
|
+
/** The root's value. */
|
|
188
|
+
readonly value: unknown
|
|
189
|
+
/** Every node that settled. */
|
|
190
|
+
readonly settled: ReadonlyMap<string, unknown>
|
|
191
|
+
/** The typed failures observed before a catch recovered them. */
|
|
192
|
+
readonly failed: ReadonlyMap<string, unknown>
|
|
193
|
+
/** The nodes a branch went the other way on. */
|
|
194
|
+
readonly skipped: ReadonlyArray<string>
|
|
195
|
+
}
|
|
117
196
|
```
|
|
118
197
|
|
|
119
198
|
`skipped` is the field that answers "why did nothing happen here". The walk is
|
|
@@ -147,6 +226,8 @@ implementation layers instead of provided under them.
|
|
|
147
226
|
|
|
148
227
|
## Related pages
|
|
149
228
|
|
|
229
|
+
- [Diff two plans](../../../plan/docs/guides/diff-two-plans.md): compile two
|
|
230
|
+
versions of a flow and see which steps were added, removed, or re-keyed.
|
|
150
231
|
- [Bodies are plans](../concepts/bodies-and-plans.md): why the build is pure and
|
|
151
232
|
what it refuses.
|
|
152
233
|
- [Execution identity](../concepts/execution-identity.md): how a node id becomes
|
package/docs/installation.md
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
---
|
|
2
2
|
title: "Installation"
|
|
3
|
-
description: "Install @smthrs/flow, its runtime requirements and
|
|
3
|
+
description: "Install @smthrs/flow, its runtime requirements and effect range, its import forms, and the packages a runnable composition adds."
|
|
4
4
|
sidebar:
|
|
5
5
|
order: 1
|
|
6
6
|
---
|
|
@@ -9,8 +9,8 @@ sidebar:
|
|
|
9
9
|
|
|
10
10
|
`@smthrs/flow` is not on npm yet. Link the source packages as described in [Use the libraries](#use-the-libraries).
|
|
11
11
|
|
|
12
|
-
`effect` is a
|
|
13
|
-
|
|
12
|
+
`effect` is a peer dependency of this package, in the range `^4.0.4`. Add one
|
|
13
|
+
`effect` in that range to your own dependencies: your declarations import
|
|
14
14
|
`effect/Schema` and your implementations import `effect/Effect` directly, and two
|
|
15
15
|
copies of `effect` in one program are two sets of service tags.
|
|
16
16
|
|
|
@@ -23,7 +23,7 @@ from, and the canonical JSON checks applied to values.
|
|
|
23
23
|
|
|
24
24
|
## Use the libraries
|
|
25
25
|
|
|
26
|
-
First [install the source checkout](https://github.com/smithersai/smithers/blob/main/packages/smithers/docs/installation.md#install-the-cli). The checkout's `examples` workspace carries the packages used by the flow tutorials and their pinned `effect@4.0.
|
|
26
|
+
First [install the source checkout](https://github.com/smithersai/smithers/blob/main/packages/smithers/docs/installation.md#install-the-cli). The checkout's `examples` workspace carries the packages used by the flow tutorials and their pinned `effect@4.0.4`.
|
|
27
27
|
|
|
28
28
|
Create a project beside the checkout:
|
|
29
29
|
|
package/docs/reference/flow.md
CHANGED
|
@@ -5,7 +5,7 @@ area: api
|
|
|
5
5
|
order: 10
|
|
6
6
|
---
|
|
7
7
|
|
|
8
|
-
Install the package with its
|
|
8
|
+
Install the package with its `effect` peer. Not on npm yet; see [Installation](../installation.md#use-the-libraries).
|
|
9
9
|
|
|
10
10
|
## Entry points
|
|
11
11
|
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@smthrs/flow",
|
|
3
3
|
"type": "module",
|
|
4
|
-
"version": "1.0.0-rc.
|
|
4
|
+
"version": "1.0.0-rc.7",
|
|
5
5
|
"license": "MIT",
|
|
6
6
|
"smthrs": {
|
|
7
7
|
"group": "engine"
|
|
@@ -289,21 +289,21 @@
|
|
|
289
289
|
"tag": "next"
|
|
290
290
|
},
|
|
291
291
|
"dependencies": {
|
|
292
|
-
"@smthrs/crypto": "1.0.0-rc.
|
|
293
|
-
"@smthrs/keys": "1.0.0-rc.
|
|
294
|
-
"@smthrs/plan": "1.0.0-rc.
|
|
295
|
-
"@smthrs/canonical": "1.0.0-rc.
|
|
296
|
-
"@smthrs/capability": "1.0.0-rc.
|
|
292
|
+
"@smthrs/crypto": "1.0.0-rc.7",
|
|
293
|
+
"@smthrs/keys": "1.0.0-rc.7",
|
|
294
|
+
"@smthrs/plan": "1.0.0-rc.7",
|
|
295
|
+
"@smthrs/canonical": "1.0.0-rc.7",
|
|
296
|
+
"@smthrs/capability": "1.0.0-rc.7"
|
|
297
297
|
},
|
|
298
298
|
"devDependencies": {
|
|
299
299
|
"@effect/language-service": "0.87.2",
|
|
300
|
-
"@effect/platform-node": "4.0.
|
|
301
|
-
"@effect/vitest": "4.0.
|
|
300
|
+
"@effect/platform-node": "4.0.4",
|
|
301
|
+
"@effect/vitest": "4.0.4",
|
|
302
302
|
"@eslint/js": "9.39.5",
|
|
303
303
|
"@types/node": "26.4.1",
|
|
304
304
|
"@vitest/coverage-v8": "5.0.0",
|
|
305
305
|
"dprint": "0.57.1",
|
|
306
|
-
"effect": "4.0.
|
|
306
|
+
"effect": "4.0.4",
|
|
307
307
|
"esbuild": "0.28.2",
|
|
308
308
|
"eslint": "9.39.5",
|
|
309
309
|
"eslint-import-resolver-typescript": "4.4.5",
|
|
@@ -316,7 +316,7 @@
|
|
|
316
316
|
"vitest": "5.0.0"
|
|
317
317
|
},
|
|
318
318
|
"peerDependencies": {
|
|
319
|
-
"effect": "4.0.
|
|
319
|
+
"effect": "^4.0.4"
|
|
320
320
|
},
|
|
321
321
|
"scripts": {
|
|
322
322
|
"lint": "eslint src --max-warnings=0 && dprint check",
|
package/src/DurableDeferred.ts
CHANGED
|
@@ -19,7 +19,7 @@ import * as Cause from "effect/Cause"
|
|
|
19
19
|
import * as Context from "effect/Context"
|
|
20
20
|
import type * as Crypto from "effect/Crypto"
|
|
21
21
|
import * as Effect from "effect/Effect"
|
|
22
|
-
import * as
|
|
22
|
+
import * as Base64Url from "effect/encoding/Base64Url"
|
|
23
23
|
import * as Exit from "effect/Exit"
|
|
24
24
|
import * as Filter from "effect/Filter"
|
|
25
25
|
import { dual } from "effect/Function"
|
|
@@ -249,7 +249,7 @@ export const into: {
|
|
|
249
249
|
// Untraced because completion encoding is called for each deferred result.
|
|
250
250
|
Effect.fnUntraced(function*(exit) {
|
|
251
251
|
if (Exit.isFailure(exit)) {
|
|
252
|
-
const [
|
|
252
|
+
const [interrupts, reasons] = Arr.partition(
|
|
253
253
|
exit.cause.reasons,
|
|
254
254
|
Filter.fromPredicate(Cause.isInterruptReason)
|
|
255
255
|
)
|
|
@@ -396,7 +396,7 @@ export class TokenParsed extends Schema.Class<TokenParsed>(
|
|
|
396
396
|
* @since 0.1.0
|
|
397
397
|
*/
|
|
398
398
|
get asToken(): Token {
|
|
399
|
-
return
|
|
399
|
+
return Base64Url.encode(
|
|
400
400
|
JSON.stringify([this.flowName, this.executionId, this.deferredName])
|
|
401
401
|
) as Token
|
|
402
402
|
}
|
package/src/DurableQueue.ts
CHANGED
|
@@ -20,10 +20,10 @@ import * as Effect from "effect/Effect"
|
|
|
20
20
|
import * as Exit from "effect/Exit"
|
|
21
21
|
import * as Filter from "effect/Filter"
|
|
22
22
|
import * as Layer from "effect/Layer"
|
|
23
|
+
import * as PersistedQueue from "effect/persistence/PersistedQueue"
|
|
23
24
|
import * as Schedule from "effect/Schedule"
|
|
24
25
|
import * as Schema from "effect/Schema"
|
|
25
26
|
import * as Tracer from "effect/Tracer"
|
|
26
|
-
import * as PersistedQueue from "effect/unstable/persistence/PersistedQueue"
|
|
27
27
|
import * as Action from "./Action/index.ts"
|
|
28
28
|
import * as DurableDeferred from "./DurableDeferred.ts"
|
|
29
29
|
import { annotateWaiting, type FlowInstance, type FlowRuntime } from "./FlowRuntime/index.ts"
|
|
@@ -367,7 +367,7 @@ const makeWorkerEffect = Effect.fnUntraced(function*<
|
|
|
367
367
|
})
|
|
368
368
|
let exit = yield* Effect.exit(f(item.payload))
|
|
369
369
|
if (Exit.isFailure(exit)) {
|
|
370
|
-
const [
|
|
370
|
+
const [interrupts, reasons] = Arr.partition(
|
|
371
371
|
exit.cause.reasons,
|
|
372
372
|
Filter.fromPredicate(Cause.isInterruptReason)
|
|
373
373
|
)
|
package/src/Flow/ExecutionIds.ts
CHANGED
|
@@ -99,7 +99,7 @@ export const derived: ExecutionIdSource = {
|
|
|
99
99
|
* @since 0.1.0
|
|
100
100
|
*/
|
|
101
101
|
export const fresh: ExecutionIdSource = {
|
|
102
|
-
mint: () => Effect.flatMap(Crypto.Crypto, (crypto) => Effect.orDie(crypto.randomUUIDv4))
|
|
102
|
+
mint: () => Effect.flatMap(Crypto.Crypto, (crypto) => Effect.orDie(crypto.randomUUIDv4()))
|
|
103
103
|
}
|
|
104
104
|
|
|
105
105
|
/**
|
package/src/Flow/Result.ts
CHANGED
|
@@ -10,11 +10,11 @@ import { CapabilityPattern } from "@smthrs/capability/Capability"
|
|
|
10
10
|
import * as Data from "effect/Data"
|
|
11
11
|
import * as Effect from "effect/Effect"
|
|
12
12
|
import type * as Exit from "effect/Exit"
|
|
13
|
+
import type { ExitEncoded } from "effect/rpc/RpcMessage"
|
|
13
14
|
import * as Schema from "effect/Schema"
|
|
14
15
|
import * as SchemaIssue from "effect/SchemaIssue"
|
|
15
16
|
import * as SchemaParser from "effect/SchemaParser"
|
|
16
17
|
import * as Transformation from "effect/SchemaTransformation"
|
|
17
|
-
import type { ExitEncoded } from "effect/unstable/rpc/RpcMessage"
|
|
18
18
|
|
|
19
19
|
const ResultTypeId = "@smthrs/flow/Flow/Result"
|
|
20
20
|
|
package/src/Flow/Runtime.ts
CHANGED
|
@@ -62,7 +62,7 @@ export const intoResult = <A, E, R>(
|
|
|
62
62
|
instance.handoff ?? new Complete({ exit: Exit.succeed(value) })
|
|
63
63
|
),
|
|
64
64
|
onFailure: (cause): Effect.Effect<Result<A, E>> => {
|
|
65
|
-
const [
|
|
65
|
+
const [interrupts, reasons] = Arr.partition(
|
|
66
66
|
cause.reasons,
|
|
67
67
|
Filter.fromPredicate(Cause.isInterruptReason)
|
|
68
68
|
)
|
package/src/Flow/internal.ts
CHANGED
package/src/Graph.ts
CHANGED
|
@@ -65,7 +65,7 @@ import * as Planned from "@smthrs/plan/Planned"
|
|
|
65
65
|
import * as Context from "effect/Context"
|
|
66
66
|
import * as Option from "effect/Option"
|
|
67
67
|
import * as Predicate from "effect/Predicate"
|
|
68
|
-
import * as Schema from "effect/Schema"
|
|
68
|
+
import type * as Schema from "effect/Schema"
|
|
69
69
|
import type * as Action from "./Action/Action.ts"
|
|
70
70
|
import { TypeId as ActionTypeId } from "./Action/TypeId.ts"
|
|
71
71
|
import * as Annotations from "./Flow/Annotations.ts"
|
|
@@ -321,12 +321,15 @@ const refusalMessage = (
|
|
|
321
321
|
* transformation and needs the call re-keyed renames the declaration.
|
|
322
322
|
* `@smthrs/core` carries the same algorithm and the same limit.
|
|
323
323
|
*
|
|
324
|
+
* `Node.schemaIdentity` prints the document, not the installed `effect`: a
|
|
325
|
+
* release that prints a schema differently must not move the identity.
|
|
326
|
+
*
|
|
324
327
|
* @private
|
|
325
328
|
*/
|
|
326
329
|
const schemaIdentity = (schema: Schema.Top): unknown => {
|
|
327
330
|
const cached = schemaDocuments.get(schema)
|
|
328
331
|
if (cached !== undefined) return cached
|
|
329
|
-
const document =
|
|
332
|
+
const document = Node.schemaIdentity(schema, { onExcessProperty: "error" })
|
|
330
333
|
schemaDocuments.set(schema, document)
|
|
331
334
|
return document
|
|
332
335
|
}
|