@vef-framework-react/core 2.3.0 → 2.4.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/LICENSE +201 -0
- package/dist/cjs/api/client.cjs +1 -1
- package/dist/cjs/api/constants.cjs +1 -1
- package/dist/cjs/api/helpers.cjs +1 -1
- package/dist/cjs/api/index.cjs +1 -1
- package/dist/cjs/auth/helpers.cjs +1 -1
- package/dist/cjs/auth/index.cjs +1 -1
- package/dist/cjs/context/api-client.cjs +1 -1
- package/dist/cjs/context/app.cjs +1 -1
- package/dist/cjs/context/context-selector.cjs +1 -1
- package/dist/cjs/context/disabled.cjs +1 -1
- package/dist/cjs/context/index.cjs +1 -1
- package/dist/cjs/dnd/index.cjs +1 -1
- package/dist/cjs/http/client.cjs +1 -1
- package/dist/cjs/http/helpers.cjs +1 -1
- package/dist/cjs/http/index.cjs +1 -1
- package/dist/cjs/immer/index.cjs +1 -1
- package/dist/cjs/index.cjs +1 -1
- package/dist/cjs/motion/features.cjs +1 -1
- package/dist/cjs/motion/index.cjs +1 -1
- package/dist/cjs/motion/motion-provider.cjs +1 -1
- package/dist/cjs/query/helpers.cjs +1 -1
- package/dist/cjs/query/hooks.cjs +1 -1
- package/dist/cjs/query/index.cjs +1 -1
- package/dist/cjs/sse/client.cjs +1 -1
- package/dist/cjs/sse/helpers.cjs +1 -1
- package/dist/cjs/sse/index.cjs +1 -1
- package/dist/cjs/sse/stream-machine.cjs +1 -0
- package/dist/cjs/state/index.cjs +1 -1
- package/dist/cjs/state-machine/index.cjs +1 -1
- package/dist/cjs/storage/index.cjs +1 -1
- package/dist/cjs/storage/protocol.cjs +1 -1
- package/dist/cjs/storage/resumable/index.cjs +1 -1
- package/dist/cjs/storage/resumable/plan.cjs +1 -1
- package/dist/cjs/storage/uploader-machine.cjs +1 -0
- package/dist/cjs/storage/uploader.cjs +1 -1
- package/dist/cjs/store/bound.cjs +1 -1
- package/dist/cjs/store/index.cjs +1 -1
- package/dist/cjs/store/unbound.cjs +1 -1
- package/dist/cjs/store/use-deep.cjs +1 -1
- package/dist/es/api/client.js +1 -1
- package/dist/es/api/constants.js +1 -1
- package/dist/es/api/helpers.js +1 -1
- package/dist/es/api/index.js +1 -1
- package/dist/es/auth/helpers.js +1 -1
- package/dist/es/auth/index.js +1 -1
- package/dist/es/context/api-client.js +1 -1
- package/dist/es/context/app.js +1 -1
- package/dist/es/context/context-selector.js +1 -1
- package/dist/es/context/disabled.js +1 -1
- package/dist/es/context/index.js +1 -1
- package/dist/es/dnd/index.js +11 -10
- package/dist/es/http/client.js +1 -1
- package/dist/es/http/constants.js +1 -1
- package/dist/es/http/errors.js +1 -1
- package/dist/es/http/helpers.js +1 -1
- package/dist/es/http/index.js +1 -1
- package/dist/es/immer/index.js +1 -1
- package/dist/es/index.js +22 -22
- package/dist/es/motion/features.js +1 -1
- package/dist/es/motion/index.js +1 -1
- package/dist/es/motion/motion-provider.js +1 -1
- package/dist/es/query/constants.js +1 -1
- package/dist/es/query/helpers.js +1 -1
- package/dist/es/query/hooks.js +1 -1
- package/dist/es/query/index.js +1 -1
- package/dist/es/sse/client.js +61 -55
- package/dist/es/sse/helpers.js +1 -1
- package/dist/es/sse/index.js +1 -1
- package/dist/es/sse/stream-machine.js +102 -0
- package/dist/es/state/index.js +1 -1
- package/dist/es/state-machine/index.js +9 -9
- package/dist/es/storage/errors.js +1 -1
- package/dist/es/storage/index.js +1 -1
- package/dist/es/storage/protocol.js +1 -1
- package/dist/es/storage/resumable/fingerprint.js +1 -1
- package/dist/es/storage/resumable/index.js +1 -1
- package/dist/es/storage/resumable/persistence.js +1 -1
- package/dist/es/storage/resumable/plan.js +1 -1
- package/dist/es/storage/types.js +1 -1
- package/dist/es/storage/uploader-machine.js +88 -0
- package/dist/es/storage/uploader.js +135 -89
- package/dist/es/store/bound.js +1 -1
- package/dist/es/store/index.js +1 -1
- package/dist/es/store/unbound.js +1 -1
- package/dist/es/store/use-deep.js +1 -1
- package/dist/types/dnd/index.d.ts +3 -2
- package/dist/types/index.d.ts +1 -1
- package/dist/types/query/hooks.d.ts +1 -1
- package/dist/types/sse/client.d.ts +9 -1
- package/dist/types/sse/stream-machine.d.ts +104 -0
- package/dist/types/storage/uploader-machine.d.ts +108 -0
- package/dist/types/storage/uploader.d.ts +8 -2
- package/package.json +8 -8
|
@@ -0,0 +1,108 @@
|
|
|
1
|
+
import { ResumePlan } from './resumable/plan';
|
|
2
|
+
import { StateMachine, MachineContext, ActorRefFromLogic, PromiseActorLogic, NonReducibleUnknown, EventObject, MetaObject } from 'xstate';
|
|
3
|
+
/**
|
|
4
|
+
* Side-effect surface the uploader statechart drives. The machine owns the
|
|
5
|
+
* lifecycle only — every phase runner closes over the `Uploader` instance
|
|
6
|
+
* that supplies it, so the chart stays a pure, domain-free transition table.
|
|
7
|
+
*/
|
|
8
|
+
export interface UploaderMachineDeps {
|
|
9
|
+
/**
|
|
10
|
+
* Open (fresh) or synthesise (resume) the multipart session and seed the
|
|
11
|
+
* uploader's bookkeeping. Rejection means the session never opened.
|
|
12
|
+
*/
|
|
13
|
+
prepareSession: (plan: ResumePlan) => Promise<void>;
|
|
14
|
+
/**
|
|
15
|
+
* Stream every pending part through the worker pool. Rejection carries the
|
|
16
|
+
* first terminal worker error.
|
|
17
|
+
*/
|
|
18
|
+
uploadParts: () => Promise<void>;
|
|
19
|
+
/**
|
|
20
|
+
* Finalize the multipart session and capture the upload result.
|
|
21
|
+
*/
|
|
22
|
+
completeSession: () => Promise<void>;
|
|
23
|
+
/**
|
|
24
|
+
* Best-effort backend `abort_upload`. Must never reject for control flow —
|
|
25
|
+
* the machine lands in `aborted` either way.
|
|
26
|
+
*/
|
|
27
|
+
abortSession: () => Promise<void>;
|
|
28
|
+
/**
|
|
29
|
+
* Abort the shared transport controller so in-flight HTTP requests and
|
|
30
|
+
* pending retry backoffs unwind immediately.
|
|
31
|
+
*/
|
|
32
|
+
killTransport: () => void;
|
|
33
|
+
/**
|
|
34
|
+
* Record the error a phase rejected with; `start()` rejects with it once
|
|
35
|
+
* the machine reaches `failed`.
|
|
36
|
+
*/
|
|
37
|
+
recordFailure: (error: unknown) => void;
|
|
38
|
+
/**
|
|
39
|
+
* Whether an abort was latched before the run started (external signal
|
|
40
|
+
* already aborted, or `abort()` called while still idle).
|
|
41
|
+
*/
|
|
42
|
+
abortRequested: () => boolean;
|
|
43
|
+
}
|
|
44
|
+
export type UploaderEvent = {
|
|
45
|
+
type: "START";
|
|
46
|
+
plan: ResumePlan;
|
|
47
|
+
} | {
|
|
48
|
+
type: "ABORT";
|
|
49
|
+
};
|
|
50
|
+
/**
|
|
51
|
+
* Lifecycle statechart behind `Uploader`. State names are exactly the public
|
|
52
|
+
* `UploadStatus` values — the chart IS the documented contract in
|
|
53
|
+
* `./types.ts`, and `Uploader` maps snapshots to statuses by name.
|
|
54
|
+
*
|
|
55
|
+
* Cancellation is an *event channel* (`ABORT`), not an error-instance check:
|
|
56
|
+
* a phase rejection always means failure (`onError` → `failed`, session kept
|
|
57
|
+
* alive for resume), while a caller abort always transitions to `aborting`
|
|
58
|
+
* (backend session torn down). The two can no longer be confused, even when
|
|
59
|
+
* the worker pool trips the shared controller itself to stop sibling workers
|
|
60
|
+
* after a terminal part failure.
|
|
61
|
+
*/
|
|
62
|
+
export declare function createUploaderMachine(deps: UploaderMachineDeps): StateMachine<MachineContext, {
|
|
63
|
+
type: "START";
|
|
64
|
+
plan: ResumePlan;
|
|
65
|
+
} | {
|
|
66
|
+
type: "ABORT";
|
|
67
|
+
}, {
|
|
68
|
+
[x: string]: ActorRefFromLogic<PromiseActorLogic<void, NonReducibleUnknown, EventObject>> | ActorRefFromLogic<PromiseActorLogic<void, ResumePlan, EventObject>> | undefined;
|
|
69
|
+
}, {
|
|
70
|
+
src: "prepareSession";
|
|
71
|
+
logic: PromiseActorLogic<void, ResumePlan, EventObject>;
|
|
72
|
+
id: string | undefined;
|
|
73
|
+
} | {
|
|
74
|
+
src: "uploadParts";
|
|
75
|
+
logic: PromiseActorLogic<void, NonReducibleUnknown, EventObject>;
|
|
76
|
+
id: string | undefined;
|
|
77
|
+
} | {
|
|
78
|
+
src: "completeSession";
|
|
79
|
+
logic: PromiseActorLogic<void, NonReducibleUnknown, EventObject>;
|
|
80
|
+
id: string | undefined;
|
|
81
|
+
} | {
|
|
82
|
+
src: "abortSession";
|
|
83
|
+
logic: PromiseActorLogic<void, NonReducibleUnknown, EventObject>;
|
|
84
|
+
id: string | undefined;
|
|
85
|
+
}, {
|
|
86
|
+
type: "recordFailure";
|
|
87
|
+
params: {
|
|
88
|
+
error: unknown;
|
|
89
|
+
};
|
|
90
|
+
} | {
|
|
91
|
+
type: "killTransport";
|
|
92
|
+
params: unknown;
|
|
93
|
+
}, {
|
|
94
|
+
type: "abortRequested";
|
|
95
|
+
params: unknown;
|
|
96
|
+
}, never, "idle" | "failed" | "aborted" | "initializing" | "uploading" | "completing" | "aborting" | "succeeded", string, NonReducibleUnknown, NonReducibleUnknown, EventObject, MetaObject, {
|
|
97
|
+
id: "uploader";
|
|
98
|
+
states: {
|
|
99
|
+
readonly idle: {};
|
|
100
|
+
readonly initializing: {};
|
|
101
|
+
readonly uploading: {};
|
|
102
|
+
readonly completing: {};
|
|
103
|
+
readonly aborting: {};
|
|
104
|
+
readonly succeeded: {};
|
|
105
|
+
readonly failed: {};
|
|
106
|
+
readonly aborted: {};
|
|
107
|
+
};
|
|
108
|
+
}>;
|
|
@@ -4,8 +4,14 @@ import { UploaderOptions, UploadProgress, UploadResult, UploadStatus } from './t
|
|
|
4
4
|
/**
|
|
5
5
|
* Drives a single file through the four-step chunked upload protocol
|
|
6
6
|
* (`init_upload → upload_part* → complete_upload`) exposed by the framework's
|
|
7
|
-
* `sys/storage` resource.
|
|
8
|
-
*
|
|
7
|
+
* `sys/storage` resource. A caller abort triggers a best-effort
|
|
8
|
+
* `abort_upload`; non-abort failures leave the session intact so the upload
|
|
9
|
+
* can resume.
|
|
10
|
+
*
|
|
11
|
+
* The lifecycle is governed by the statechart in `./uploader-machine.ts`:
|
|
12
|
+
* this class supplies the phase runners (session prep, worker pool,
|
|
13
|
+
* completion, backend abort) and bridges actor snapshots onto the public
|
|
14
|
+
* `status` / `onStatusChange` / `start()`-promise surface.
|
|
9
15
|
*
|
|
10
16
|
* The instance is one-shot: a successful or failed run cannot be restarted.
|
|
11
17
|
* Create a fresh `Uploader` for each file.
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@vef-framework-react/core",
|
|
3
3
|
"type": "module",
|
|
4
|
-
"version": "2.
|
|
4
|
+
"version": "2.4.1",
|
|
5
5
|
"private": false,
|
|
6
6
|
"description": "Core features for VEF framework",
|
|
7
7
|
"author": {
|
|
@@ -56,20 +56,20 @@
|
|
|
56
56
|
"@emotion/react": "^11.14.0",
|
|
57
57
|
"@hello-pangea/dnd": "^18.0.1",
|
|
58
58
|
"@microsoft/fetch-event-source": "^2.0.1",
|
|
59
|
-
"@tanstack/react-query": "^5.
|
|
59
|
+
"@tanstack/react-query": "^5.101.0",
|
|
60
60
|
"@xstate/react": "^6.1.0",
|
|
61
|
-
"axios": "^1.
|
|
61
|
+
"axios": "^1.17.0",
|
|
62
62
|
"clsx": "^2.1.1",
|
|
63
63
|
"immer": "^11.1.7",
|
|
64
64
|
"jotai": "^2.20.0",
|
|
65
|
-
"motion": "^12.
|
|
65
|
+
"motion": "^12.40.0",
|
|
66
66
|
"use-immer": "^0.11.0",
|
|
67
|
-
"xstate": "^5.
|
|
68
|
-
"zustand": "^5.0.
|
|
69
|
-
"@vef-framework-react/shared": "2.
|
|
67
|
+
"xstate": "^5.32.0",
|
|
68
|
+
"zustand": "^5.0.14",
|
|
69
|
+
"@vef-framework-react/shared": "2.4.1"
|
|
70
70
|
},
|
|
71
71
|
"devDependencies": {
|
|
72
|
-
"react": "^19.2.
|
|
72
|
+
"react": "^19.2.7"
|
|
73
73
|
},
|
|
74
74
|
"scripts": {
|
|
75
75
|
"clean": "rimraf dist",
|