@bian-womp/spark-workbench 0.2.23 → 0.2.25
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/lib/cjs/index.cjs +63 -18
- package/lib/cjs/index.cjs.map +1 -1
- package/lib/cjs/src/adapters/cli/index.d.ts +1 -1
- package/lib/cjs/src/adapters/cli/index.d.ts.map +1 -1
- package/lib/cjs/src/core/AbstractWorkbench.d.ts +3 -3
- package/lib/cjs/src/core/AbstractWorkbench.d.ts.map +1 -1
- package/lib/cjs/src/core/InMemoryWorkbench.d.ts +4 -3
- package/lib/cjs/src/core/InMemoryWorkbench.d.ts.map +1 -1
- package/lib/cjs/src/core/contracts.d.ts +4 -3
- package/lib/cjs/src/core/contracts.d.ts.map +1 -1
- package/lib/cjs/src/misc/WorkbenchStudio.d.ts +12 -2
- package/lib/cjs/src/misc/WorkbenchStudio.d.ts.map +1 -1
- package/lib/cjs/src/misc/context/WorkbenchContext.d.ts +2 -1
- package/lib/cjs/src/misc/context/WorkbenchContext.d.ts.map +1 -1
- package/lib/cjs/src/misc/context/WorkbenchContext.provider.d.ts.map +1 -1
- package/lib/cjs/src/misc/layout.d.ts +5 -5
- package/lib/cjs/src/misc/layout.d.ts.map +1 -1
- package/lib/cjs/src/misc/mapping.d.ts +2 -1
- package/lib/cjs/src/misc/mapping.d.ts.map +1 -1
- package/lib/cjs/src/runtime/AbstractGraphRunner.d.ts +2 -2
- package/lib/cjs/src/runtime/AbstractGraphRunner.d.ts.map +1 -1
- package/lib/cjs/src/runtime/IGraphRunner.d.ts +7 -3
- package/lib/cjs/src/runtime/IGraphRunner.d.ts.map +1 -1
- package/lib/cjs/src/runtime/LocalGraphRunner.d.ts +2 -2
- package/lib/cjs/src/runtime/LocalGraphRunner.d.ts.map +1 -1
- package/lib/cjs/src/runtime/RemoteGraphRunner.d.ts +2 -2
- package/lib/cjs/src/runtime/RemoteGraphRunner.d.ts.map +1 -1
- package/lib/esm/index.js +63 -18
- package/lib/esm/index.js.map +1 -1
- package/lib/esm/src/adapters/cli/index.d.ts +1 -1
- package/lib/esm/src/adapters/cli/index.d.ts.map +1 -1
- package/lib/esm/src/core/AbstractWorkbench.d.ts +3 -3
- package/lib/esm/src/core/AbstractWorkbench.d.ts.map +1 -1
- package/lib/esm/src/core/InMemoryWorkbench.d.ts +4 -3
- package/lib/esm/src/core/InMemoryWorkbench.d.ts.map +1 -1
- package/lib/esm/src/core/contracts.d.ts +4 -3
- package/lib/esm/src/core/contracts.d.ts.map +1 -1
- package/lib/esm/src/misc/WorkbenchStudio.d.ts +12 -2
- package/lib/esm/src/misc/WorkbenchStudio.d.ts.map +1 -1
- package/lib/esm/src/misc/context/WorkbenchContext.d.ts +2 -1
- package/lib/esm/src/misc/context/WorkbenchContext.d.ts.map +1 -1
- package/lib/esm/src/misc/context/WorkbenchContext.provider.d.ts.map +1 -1
- package/lib/esm/src/misc/layout.d.ts +5 -5
- package/lib/esm/src/misc/layout.d.ts.map +1 -1
- package/lib/esm/src/misc/mapping.d.ts +2 -1
- package/lib/esm/src/misc/mapping.d.ts.map +1 -1
- package/lib/esm/src/runtime/AbstractGraphRunner.d.ts +2 -2
- package/lib/esm/src/runtime/AbstractGraphRunner.d.ts.map +1 -1
- package/lib/esm/src/runtime/IGraphRunner.d.ts +7 -3
- package/lib/esm/src/runtime/IGraphRunner.d.ts.map +1 -1
- package/lib/esm/src/runtime/LocalGraphRunner.d.ts +2 -2
- package/lib/esm/src/runtime/LocalGraphRunner.d.ts.map +1 -1
- package/lib/esm/src/runtime/RemoteGraphRunner.d.ts +2 -2
- package/lib/esm/src/runtime/RemoteGraphRunner.d.ts.map +1 -1
- package/package.json +4 -4
package/lib/cjs/index.cjs
CHANGED
|
@@ -817,22 +817,39 @@ class RemoteGraphRunner extends AbstractGraphRunner {
|
|
|
817
817
|
return this.runner;
|
|
818
818
|
let transport;
|
|
819
819
|
const kind = this.backend.kind;
|
|
820
|
+
const backend = this.backend;
|
|
821
|
+
const connectOptions = backend.connectOptions;
|
|
820
822
|
this.emit("transport", { state: "connecting", kind });
|
|
821
|
-
if (
|
|
823
|
+
if (backend.kind === "remote-http") {
|
|
822
824
|
if (!sparkRemote.HttpPollingTransport)
|
|
823
825
|
throw new Error("HttpPollingTransport not available");
|
|
824
|
-
transport = new sparkRemote.HttpPollingTransport(
|
|
825
|
-
await transport.connect();
|
|
826
|
+
transport = new sparkRemote.HttpPollingTransport(backend.baseUrl);
|
|
827
|
+
await transport.connect(connectOptions);
|
|
826
828
|
}
|
|
827
|
-
else if (
|
|
829
|
+
else if (backend.kind === "remote-ws") {
|
|
828
830
|
if (!sparkRemote.WebSocketTransport)
|
|
829
831
|
throw new Error("WebSocketTransport not available");
|
|
830
|
-
transport = new sparkRemote.WebSocketTransport(
|
|
831
|
-
await transport.connect();
|
|
832
|
+
transport = new sparkRemote.WebSocketTransport(backend.url);
|
|
833
|
+
await transport.connect(connectOptions);
|
|
832
834
|
}
|
|
833
835
|
else {
|
|
834
836
|
throw new Error("Remote backend not configured");
|
|
835
837
|
}
|
|
838
|
+
// Subscribe to custom events if handler provided
|
|
839
|
+
if (backend.onCustomEvent) {
|
|
840
|
+
transport.subscribe((event) => {
|
|
841
|
+
// Filter out standard runtime events, pass others to custom handler
|
|
842
|
+
const msg = event.message;
|
|
843
|
+
if (msg && typeof msg === "object" && "type" in msg) {
|
|
844
|
+
const type = msg.type;
|
|
845
|
+
// Standard runtime events: stats, value, error, invalidate
|
|
846
|
+
// Custom events are anything else (e.g., flow-opened, flow-latest)
|
|
847
|
+
if (!["stats", "value", "error", "invalidate"].includes(type)) {
|
|
848
|
+
backend.onCustomEvent?.(event);
|
|
849
|
+
}
|
|
850
|
+
}
|
|
851
|
+
});
|
|
852
|
+
}
|
|
836
853
|
const runner = new sparkRemote.RemoteRunner(transport);
|
|
837
854
|
this.runner = runner;
|
|
838
855
|
this.transport = transport;
|
|
@@ -2837,7 +2854,7 @@ const WorkbenchCanvas = React.forwardRef(({ showValues, toString, toElement, get
|
|
|
2837
2854
|
})
|
|
2838
2855
|
.map((n) => n.id);
|
|
2839
2856
|
// Detect handle updates (ids/length changes) for targeted debug
|
|
2840
|
-
const toIds = (arr) => Array.isArray(arr) ? arr.map((h) => h
|
|
2857
|
+
const toIds = (arr) => Array.isArray(arr) ? arr.map((h) => (h && typeof h === "object" && "id" in h ? String(h.id) : "")).filter(Boolean) : [];
|
|
2841
2858
|
const handlesEqual = (a, b) => {
|
|
2842
2859
|
const aIds = toIds(a);
|
|
2843
2860
|
const bIds = toIds(b);
|
|
@@ -3109,7 +3126,8 @@ function WorkbenchStudioCanvas({ setRegistry, autoScroll, onAutoScrollChange, ex
|
|
|
3109
3126
|
URL.revokeObjectURL(url);
|
|
3110
3127
|
}
|
|
3111
3128
|
catch (err) {
|
|
3112
|
-
|
|
3129
|
+
const message = err instanceof Error ? err.message : String(err);
|
|
3130
|
+
alert(message);
|
|
3113
3131
|
}
|
|
3114
3132
|
}, [wb, runner]);
|
|
3115
3133
|
const onUploadPicked = React.useCallback(async (e) => {
|
|
@@ -3167,7 +3185,8 @@ function WorkbenchStudioCanvas({ setRegistry, autoScroll, onAutoScrollChange, ex
|
|
|
3167
3185
|
runAutoLayout();
|
|
3168
3186
|
}
|
|
3169
3187
|
catch (err) {
|
|
3170
|
-
|
|
3188
|
+
const message = err instanceof Error ? err.message : String(err);
|
|
3189
|
+
alert(message);
|
|
3171
3190
|
}
|
|
3172
3191
|
finally {
|
|
3173
3192
|
// reset input so same file can be picked again
|
|
@@ -3417,8 +3436,11 @@ function WorkbenchStudioCanvas({ setRegistry, autoScroll, onAutoScrollChange, ex
|
|
|
3417
3436
|
return pre;
|
|
3418
3437
|
if (typeof value === "object" &&
|
|
3419
3438
|
value !== null &&
|
|
3439
|
+
"url" in value &&
|
|
3420
3440
|
typeof value.url === "string") {
|
|
3421
|
-
const title = value.title
|
|
3441
|
+
const title = "title" in value && typeof value.title === "string"
|
|
3442
|
+
? value.title
|
|
3443
|
+
: "";
|
|
3422
3444
|
const url = String(value.url || "");
|
|
3423
3445
|
// value.ts handles data URL formatting
|
|
3424
3446
|
return title || url.slice(0, 32) + (url.length > 32 ? "…" : "");
|
|
@@ -3431,7 +3453,11 @@ function WorkbenchStudioCanvas({ setRegistry, autoScroll, onAutoScrollChange, ex
|
|
|
3431
3453
|
const round4 = (n) => Math.round(Number(n) * 10000) / 10000;
|
|
3432
3454
|
if (typeId === "base.vec3" && Array.isArray(value)) {
|
|
3433
3455
|
const a = value;
|
|
3434
|
-
return [
|
|
3456
|
+
return [
|
|
3457
|
+
round4(Number(a[0] ?? 0)),
|
|
3458
|
+
round4(Number(a[1] ?? 0)),
|
|
3459
|
+
round4(Number(a[2] ?? 0)),
|
|
3460
|
+
].join(",");
|
|
3435
3461
|
}
|
|
3436
3462
|
const stringifyRounded = (v) => {
|
|
3437
3463
|
try {
|
|
@@ -3482,7 +3508,8 @@ function WorkbenchStudioCanvas({ setRegistry, autoScroll, onAutoScrollChange, ex
|
|
|
3482
3508
|
runner.launch(wb.export(), { engine: kind });
|
|
3483
3509
|
}
|
|
3484
3510
|
catch (err) {
|
|
3485
|
-
|
|
3511
|
+
const message = err instanceof Error ? err.message : String(err);
|
|
3512
|
+
alert(message);
|
|
3486
3513
|
}
|
|
3487
3514
|
}, disabled: !engine, title: engine ? "Start engine" : "Select an engine first", children: [jsxRuntime.jsx(react$1.PlayIcon, { size: 14, weight: "fill" }), jsxRuntime.jsx("span", { className: "font-medium ml-1", children: "Start" })] })), jsxRuntime.jsx("button", { className: "border border-gray-300 rounded px-2 py-1.5", onClick: runAutoLayout, children: "Auto Layout" }), jsxRuntime.jsx("button", { className: "ml-2 border border-gray-300 rounded px-2 py-1.5", onClick: () => canvasRef.current?.fitView?.(), title: "Fit View", children: "Fit View" }), jsxRuntime.jsx("button", { className: "ml-2 border border-gray-300 rounded px-2 py-1.5", onClick: downloadGraph, children: "Download Graph" }), jsxRuntime.jsx("button", { className: "ml-2 border border-gray-300 rounded px-2 py-1.5", onClick: async () => {
|
|
3488
3515
|
try {
|
|
@@ -3510,25 +3537,43 @@ function WorkbenchStudioCanvas({ setRegistry, autoScroll, onAutoScrollChange, ex
|
|
|
3510
3537
|
URL.revokeObjectURL(url);
|
|
3511
3538
|
}
|
|
3512
3539
|
catch (err) {
|
|
3513
|
-
|
|
3540
|
+
const message = err instanceof Error ? err.message : String(err);
|
|
3541
|
+
alert(message);
|
|
3514
3542
|
}
|
|
3515
3543
|
}, children: "Download Snapshot" }), jsxRuntime.jsx("input", { ref: uploadInputRef, type: "file", accept: "application/json,.json", className: "hidden", onChange: onUploadPicked }), jsxRuntime.jsx("button", { className: "ml-2 border border-gray-300 rounded px-2 py-1.5", onClick: triggerUpload, children: "Upload Graph/Snapshot" }), jsxRuntime.jsxs("label", { className: "ml-2 flex items-center gap-1", children: [jsxRuntime.jsx("input", { type: "checkbox", checked: debug, onChange: (e) => onDebugChange(e.target.checked) }), jsxRuntime.jsx("span", { children: "Debug events" })] }), jsxRuntime.jsxs("label", { className: "ml-2 flex items-center gap-1", children: [jsxRuntime.jsx("input", { type: "checkbox", checked: showValues, onChange: (e) => onShowValuesChange(e.target.checked) }), jsxRuntime.jsx("span", { children: "Show values in nodes" })] })] }), jsxRuntime.jsxs("div", { className: "flex flex-1 min-h-0", children: [jsxRuntime.jsx("div", { className: "flex-1 min-w-0", children: jsxRuntime.jsx(WorkbenchCanvas, { ref: canvasRef, showValues: showValues, toString: toString, toElement: toElement, getDefaultNodeSize: overrides?.getDefaultNodeSize }) }), jsxRuntime.jsx(Inspector, { setInput: setInput, debug: debug, autoScroll: autoScroll, hideWorkbench: hideWorkbench, onAutoScrollChange: onAutoScrollChange, onHideWorkbenchChange: onHideWorkbenchChange, toString: toString, toElement: toElement, contextPanel: overrides?.contextPanel })] })] }));
|
|
3516
3544
|
}
|
|
3517
|
-
function WorkbenchStudio({ engine, onEngineChange, example, onExampleChange, backendKind, onBackendKindChange, httpBaseUrl, onHttpBaseUrlChange, wsUrl, onWsUrlChange, debug, onDebugChange, showValues, onShowValuesChange, hideWorkbench, onHideWorkbenchChange, autoScroll, onAutoScrollChange, overrides, onInit, onChange, }) {
|
|
3545
|
+
function WorkbenchStudio({ engine, onEngineChange, example, onExampleChange, backendKind, onBackendKindChange, httpBaseUrl, onHttpBaseUrlChange, wsUrl, onWsUrlChange, debug, onDebugChange, showValues, onShowValuesChange, hideWorkbench, onHideWorkbenchChange, autoScroll, onAutoScrollChange, backendOptions, overrides, onInit, onChange, }) {
|
|
3518
3546
|
const [registry, setRegistry] = React.useState(sparkGraph.createSimpleGraphRegistry());
|
|
3519
3547
|
const [wb] = React.useState(() => new InMemoryWorkbench({ ui: new DefaultUIExtensionRegistry() }));
|
|
3520
3548
|
const runner = React.useMemo(() => {
|
|
3521
3549
|
if (backendKind === "remote-http") {
|
|
3522
|
-
|
|
3550
|
+
const backend = {
|
|
3523
3551
|
kind: "remote-http",
|
|
3524
3552
|
baseUrl: httpBaseUrl,
|
|
3525
|
-
|
|
3553
|
+
...(backendOptions?.connectOptions && {
|
|
3554
|
+
connectOptions: backendOptions.connectOptions,
|
|
3555
|
+
}),
|
|
3556
|
+
...(backendOptions?.onCustomEvent && {
|
|
3557
|
+
onCustomEvent: backendOptions.onCustomEvent,
|
|
3558
|
+
}),
|
|
3559
|
+
};
|
|
3560
|
+
return new RemoteGraphRunner(registry, backend);
|
|
3526
3561
|
}
|
|
3527
3562
|
if (backendKind === "remote-ws") {
|
|
3528
|
-
|
|
3563
|
+
const backend = {
|
|
3564
|
+
kind: "remote-ws",
|
|
3565
|
+
url: wsUrl,
|
|
3566
|
+
...(backendOptions?.connectOptions && {
|
|
3567
|
+
connectOptions: backendOptions.connectOptions,
|
|
3568
|
+
}),
|
|
3569
|
+
...(backendOptions?.onCustomEvent && {
|
|
3570
|
+
onCustomEvent: backendOptions.onCustomEvent,
|
|
3571
|
+
}),
|
|
3572
|
+
};
|
|
3573
|
+
return new RemoteGraphRunner(registry, backend);
|
|
3529
3574
|
}
|
|
3530
3575
|
return new LocalGraphRunner(registry);
|
|
3531
|
-
}, [registry, backendKind, httpBaseUrl, wsUrl]);
|
|
3576
|
+
}, [registry, backendKind, httpBaseUrl, wsUrl, backendOptions]);
|
|
3532
3577
|
// Allow external UI registration (e.g., node renderers) with access to wb
|
|
3533
3578
|
React.useEffect(() => {
|
|
3534
3579
|
const baseRegisterUI = (_wb) => { };
|