@almadar/ui 5.157.0 → 5.159.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/dist/{EntityBindingContext-BfZGeDfX.d.cts → EntityBindingContext-0Evn_LcT.d.cts} +7 -3
- package/dist/{EntityBindingContext-BfZGeDfX.d.ts → EntityBindingContext-0Evn_LcT.d.ts} +7 -3
- package/dist/avl/index.cjs +379 -50
- package/dist/avl/index.js +380 -51
- package/dist/components/index.cjs +394 -17
- package/dist/components/index.d.cts +48 -6
- package/dist/components/index.d.ts +48 -6
- package/dist/components/index.js +395 -18
- package/dist/context/index.cjs +134 -39
- package/dist/context/index.js +92 -1
- package/dist/hooks/index.cjs +328 -233
- package/dist/hooks/index.js +93 -2
- package/dist/lib/index.cjs +92 -0
- package/dist/lib/index.d.cts +58 -1
- package/dist/lib/index.d.ts +58 -1
- package/dist/lib/index.js +62 -1
- package/dist/locales/index.cjs +3 -0
- package/dist/locales/index.js +3 -0
- package/dist/perf-DaVdsbU0.d.cts +21 -0
- package/dist/perf-DaVdsbU0.d.ts +21 -0
- package/dist/providers/index.cjs +461 -106
- package/dist/providers/index.d.cts +1 -1
- package/dist/providers/index.d.ts +1 -1
- package/dist/providers/index.js +462 -107
- package/dist/runtime/index.cjs +387 -55
- package/dist/runtime/index.d.cts +15 -23
- package/dist/runtime/index.d.ts +15 -23
- package/dist/runtime/index.js +389 -56
- package/locales/ar.json +1 -0
- package/locales/en.json +1 -0
- package/locales/sl.json +1 -0
- package/package.json +5 -5
package/dist/providers/index.js
CHANGED
|
@@ -15,7 +15,7 @@ import { useTranslate } from '@almadar/ui/hooks';
|
|
|
15
15
|
import { useUISlots, ThemeProvider, useTheme } from '@almadar/ui/context';
|
|
16
16
|
export { DesignThemeProvider, useDesignTheme } from '@almadar/ui/context';
|
|
17
17
|
import { evaluate, createMinimalContext } from '@almadar/evaluator';
|
|
18
|
-
import { wrapCallbackForEvent } from '@almadar/runtime/ui';
|
|
18
|
+
import { wrapCallbackForEvent, perfStart, perfEnd } from '@almadar/runtime/ui';
|
|
19
19
|
import { useLocation, useNavigate, Link, Outlet } from 'react-router-dom';
|
|
20
20
|
import ELK from 'elkjs/lib/elk.bundled.js';
|
|
21
21
|
import SyntaxHighlighter from 'react-syntax-highlighter/dist/esm/prism-light.js';
|
|
@@ -286,11 +286,54 @@ function isPlainObject(value) {
|
|
|
286
286
|
if (typeof value === "function") return false;
|
|
287
287
|
return true;
|
|
288
288
|
}
|
|
289
|
+
function isEvaluatorResolvedData(value) {
|
|
290
|
+
return evaluatorResolvedData.has(value);
|
|
291
|
+
}
|
|
292
|
+
function brandResolved(value) {
|
|
293
|
+
if (value !== null && typeof value === "object" && !React87__default.isValidElement(value) && !(value instanceof Date)) {
|
|
294
|
+
resolvedMarkerFree.add(value);
|
|
295
|
+
}
|
|
296
|
+
}
|
|
297
|
+
function subtreeHasMarker(value) {
|
|
298
|
+
if (resolvedMarkerFree.has(value)) return false;
|
|
299
|
+
const cached = markerPresenceCache.get(value);
|
|
300
|
+
if (cached !== void 0) return cached;
|
|
301
|
+
let found = false;
|
|
302
|
+
const children = Array.isArray(value) ? value : Object.values(value);
|
|
303
|
+
for (const child of children) {
|
|
304
|
+
if (isRenderBindingMarker(child)) {
|
|
305
|
+
found = true;
|
|
306
|
+
break;
|
|
307
|
+
}
|
|
308
|
+
if (Array.isArray(child) || isPlainObject(child)) {
|
|
309
|
+
if (subtreeHasMarker(child)) {
|
|
310
|
+
found = true;
|
|
311
|
+
break;
|
|
312
|
+
}
|
|
313
|
+
}
|
|
314
|
+
}
|
|
315
|
+
markerPresenceCache.set(value, found);
|
|
316
|
+
return found;
|
|
317
|
+
}
|
|
289
318
|
function walkValue(value, scopeTrait, entity, config, state) {
|
|
290
319
|
if (isRenderBindingMarker(value)) {
|
|
291
|
-
|
|
320
|
+
const cached = markerResolutionCache.get(value);
|
|
321
|
+
if (cached !== void 0 && cached.entity === entity && cached.config === config && cached.state === state) {
|
|
322
|
+
return { resolved: cached.resolved, changed: false };
|
|
323
|
+
}
|
|
324
|
+
const resolved = resolveMarkerExpression(value.expression, entity, config, state);
|
|
325
|
+
markerResolutionCache.set(value, { entity, config, state, resolved });
|
|
326
|
+
if (resolved !== null && typeof resolved === "object" && !React87__default.isValidElement(resolved) && !(resolved instanceof Date)) {
|
|
327
|
+
resolvedMarkerFree.add(resolved);
|
|
328
|
+
evaluatorResolvedData.add(resolved);
|
|
329
|
+
}
|
|
330
|
+
return { resolved, changed: true };
|
|
292
331
|
}
|
|
293
332
|
if (Array.isArray(value)) {
|
|
333
|
+
if (!subtreeHasMarker(value)) {
|
|
334
|
+
brandResolved(value);
|
|
335
|
+
return { resolved: value, changed: false };
|
|
336
|
+
}
|
|
294
337
|
const out = [];
|
|
295
338
|
let changed = false;
|
|
296
339
|
for (const item of value) {
|
|
@@ -305,9 +348,14 @@ function walkValue(value, scopeTrait, entity, config, state) {
|
|
|
305
348
|
out.push(resolved);
|
|
306
349
|
if (itemChanged) changed = true;
|
|
307
350
|
}
|
|
351
|
+
brandResolved(out);
|
|
308
352
|
return changed ? { resolved: out, changed: true } : { resolved: value, changed: false };
|
|
309
353
|
}
|
|
310
354
|
if (isPlainObject(value)) {
|
|
355
|
+
if (!subtreeHasMarker(value)) {
|
|
356
|
+
brandResolved(value);
|
|
357
|
+
return { resolved: value, changed: false };
|
|
358
|
+
}
|
|
311
359
|
const sourceTrait = value._sourceTrait;
|
|
312
360
|
if (typeof sourceTrait === "string" && sourceTrait !== scopeTrait) {
|
|
313
361
|
return { resolved: value, changed: false };
|
|
@@ -319,11 +367,13 @@ function walkValue(value, scopeTrait, entity, config, state) {
|
|
|
319
367
|
out[key] = resolved;
|
|
320
368
|
if (itemChanged) changed = true;
|
|
321
369
|
}
|
|
370
|
+
brandResolved(out);
|
|
322
371
|
return changed ? { resolved: out, changed: true } : { resolved: value, changed: false };
|
|
323
372
|
}
|
|
324
373
|
return { resolved: value, changed: false };
|
|
325
374
|
}
|
|
326
375
|
function resolveRenderBindingMarkers(props, scopeTrait, entity, config, state) {
|
|
376
|
+
if (resolvedMarkerFree.has(props)) return props;
|
|
327
377
|
const out = {};
|
|
328
378
|
let changed = false;
|
|
329
379
|
for (const [key, value] of Object.entries(props)) {
|
|
@@ -331,11 +381,17 @@ function resolveRenderBindingMarkers(props, scopeTrait, entity, config, state) {
|
|
|
331
381
|
out[key] = resolved;
|
|
332
382
|
if (propChanged) changed = true;
|
|
333
383
|
}
|
|
384
|
+
brandResolved(out);
|
|
334
385
|
return changed ? out : props;
|
|
335
386
|
}
|
|
387
|
+
var markerPresenceCache, markerResolutionCache, resolvedMarkerFree, evaluatorResolvedData;
|
|
336
388
|
var init_resolve_render_bindings = __esm({
|
|
337
389
|
"lib/resolve-render-bindings.ts"() {
|
|
338
390
|
"use client";
|
|
391
|
+
markerPresenceCache = /* @__PURE__ */ new WeakMap();
|
|
392
|
+
markerResolutionCache = /* @__PURE__ */ new WeakMap();
|
|
393
|
+
resolvedMarkerFree = /* @__PURE__ */ new WeakSet();
|
|
394
|
+
evaluatorResolvedData = /* @__PURE__ */ new WeakSet();
|
|
339
395
|
}
|
|
340
396
|
});
|
|
341
397
|
function cn(...inputs) {
|
|
@@ -11769,6 +11825,10 @@ var init_molecules = __esm({
|
|
|
11769
11825
|
init_puzzleObject();
|
|
11770
11826
|
}
|
|
11771
11827
|
});
|
|
11828
|
+
var init_perf = __esm({
|
|
11829
|
+
"lib/perf.ts"() {
|
|
11830
|
+
}
|
|
11831
|
+
});
|
|
11772
11832
|
function themeBodyFont(el) {
|
|
11773
11833
|
if (typeof getComputedStyle !== "function") return "system-ui, sans-serif";
|
|
11774
11834
|
const v = getComputedStyle(el).getPropertyValue("--font-family-body").trim();
|
|
@@ -12117,6 +12177,7 @@ var init_LearningCanvas = __esm({
|
|
|
12117
12177
|
"components/learning/atoms/LearningCanvas.tsx"() {
|
|
12118
12178
|
"use client";
|
|
12119
12179
|
init_cn();
|
|
12180
|
+
init_perf();
|
|
12120
12181
|
init_useEventBus();
|
|
12121
12182
|
DASH_PATTERNS = { dashed: [6, 4], dotted: [2, 3] };
|
|
12122
12183
|
TRACE_SERIES_COLORS = ["#2563eb", "#dc2626", "#16a34a", "#f59e0b"];
|
|
@@ -12160,6 +12221,7 @@ var init_LearningCanvas = __esm({
|
|
|
12160
12221
|
return [...shapes, ...traceOut, ...readoutOut];
|
|
12161
12222
|
}, [shapes, traces, readouts, width, height]);
|
|
12162
12223
|
const draw = useCallback(() => {
|
|
12224
|
+
const _perfT = perfStart("learningcanvas:paint");
|
|
12163
12225
|
const canvas = canvasRef.current;
|
|
12164
12226
|
if (!canvas) return;
|
|
12165
12227
|
const ctx = canvas.getContext("2d");
|
|
@@ -12181,6 +12243,7 @@ var init_LearningCanvas = __esm({
|
|
|
12181
12243
|
for (const shape of derivedShapes) {
|
|
12182
12244
|
if (shape.type === "text") drawShape(ctx, shape, width, height, derivedShapes);
|
|
12183
12245
|
}
|
|
12246
|
+
perfEnd("learningcanvas:paint", _perfT);
|
|
12184
12247
|
}, [width, height, backgroundColor, derivedShapes]);
|
|
12185
12248
|
useEffect(() => {
|
|
12186
12249
|
draw();
|
|
@@ -27368,7 +27431,7 @@ function fileIcon(name) {
|
|
|
27368
27431
|
return "file";
|
|
27369
27432
|
}
|
|
27370
27433
|
}
|
|
27371
|
-
var TreeNodeItem, FileTree;
|
|
27434
|
+
var TreeNodeItem, FlatTreeNodeItem, FileTree;
|
|
27372
27435
|
var init_FileTree = __esm({
|
|
27373
27436
|
"components/core/molecules/FileTree.tsx"() {
|
|
27374
27437
|
"use client";
|
|
@@ -27453,14 +27516,101 @@ var init_FileTree = __esm({
|
|
|
27453
27516
|
)) })
|
|
27454
27517
|
] });
|
|
27455
27518
|
};
|
|
27519
|
+
FlatTreeNodeItem = ({
|
|
27520
|
+
item,
|
|
27521
|
+
depth,
|
|
27522
|
+
indent,
|
|
27523
|
+
childrenByParent,
|
|
27524
|
+
onNodeSelect,
|
|
27525
|
+
defaultExpanded = false
|
|
27526
|
+
}) => {
|
|
27527
|
+
const [expanded, setExpanded] = useState(defaultExpanded || depth < 1);
|
|
27528
|
+
const children = childrenByParent.get(item.id);
|
|
27529
|
+
const hasChildren = !!children && children.length > 0;
|
|
27530
|
+
const handleClick = useCallback(() => {
|
|
27531
|
+
if (hasChildren) setExpanded((prev) => !prev);
|
|
27532
|
+
onNodeSelect?.(item.id);
|
|
27533
|
+
}, [hasChildren, item.id, onNodeSelect]);
|
|
27534
|
+
return /* @__PURE__ */ jsxs(Fragment, { children: [
|
|
27535
|
+
/* @__PURE__ */ jsxs(
|
|
27536
|
+
Box,
|
|
27537
|
+
{
|
|
27538
|
+
className: "flex items-center gap-1.5 py-0.5 px-2 cursor-pointer rounded-sm transition-colors hover:bg-muted",
|
|
27539
|
+
style: { paddingLeft: depth * indent + 8 },
|
|
27540
|
+
onClick: handleClick,
|
|
27541
|
+
role: "treeitem",
|
|
27542
|
+
"aria-expanded": hasChildren ? expanded : void 0,
|
|
27543
|
+
children: [
|
|
27544
|
+
hasChildren ? /* @__PURE__ */ jsx(
|
|
27545
|
+
Icon,
|
|
27546
|
+
{
|
|
27547
|
+
name: expanded ? "chevron-down" : "chevron-right",
|
|
27548
|
+
size: "xs",
|
|
27549
|
+
className: "text-[var(--color-muted-foreground)] flex-shrink-0"
|
|
27550
|
+
}
|
|
27551
|
+
) : /* @__PURE__ */ jsx(Box, { style: { width: 12, flexShrink: 0 } }),
|
|
27552
|
+
/* @__PURE__ */ jsx(
|
|
27553
|
+
Icon,
|
|
27554
|
+
{
|
|
27555
|
+
name: item.icon ?? (hasChildren ? expanded ? "folder-open" : "folder" : "file"),
|
|
27556
|
+
size: "xs",
|
|
27557
|
+
className: hasChildren ? "text-[var(--color-warning)]" : "text-[var(--color-muted-foreground)]"
|
|
27558
|
+
}
|
|
27559
|
+
),
|
|
27560
|
+
/* @__PURE__ */ jsx(Typography, { variant: "caption", className: "truncate font-mono text-xs", children: item.label })
|
|
27561
|
+
]
|
|
27562
|
+
}
|
|
27563
|
+
),
|
|
27564
|
+
hasChildren && expanded && /* @__PURE__ */ jsx(Box, { role: "group", children: children.map((child) => /* @__PURE__ */ jsx(
|
|
27565
|
+
FlatTreeNodeItem,
|
|
27566
|
+
{
|
|
27567
|
+
item: child,
|
|
27568
|
+
depth: depth + 1,
|
|
27569
|
+
indent,
|
|
27570
|
+
childrenByParent,
|
|
27571
|
+
onNodeSelect
|
|
27572
|
+
},
|
|
27573
|
+
child.id
|
|
27574
|
+
)) })
|
|
27575
|
+
] });
|
|
27576
|
+
};
|
|
27456
27577
|
FileTree = ({
|
|
27457
27578
|
tree,
|
|
27579
|
+
items,
|
|
27458
27580
|
selectedPath,
|
|
27459
27581
|
onFileSelect,
|
|
27582
|
+
onNodeSelect,
|
|
27460
27583
|
className,
|
|
27461
27584
|
indent = 16
|
|
27462
27585
|
}) => {
|
|
27463
|
-
if (
|
|
27586
|
+
if (items) {
|
|
27587
|
+
if (items.length === 0) return null;
|
|
27588
|
+
const ids = new Set(items.map((node) => node.id));
|
|
27589
|
+
const childrenByParent = /* @__PURE__ */ new Map();
|
|
27590
|
+
const roots = [];
|
|
27591
|
+
for (const item of items) {
|
|
27592
|
+
if (item.parentId && ids.has(item.parentId)) {
|
|
27593
|
+
const siblings = childrenByParent.get(item.parentId);
|
|
27594
|
+
if (siblings) siblings.push(item);
|
|
27595
|
+
else childrenByParent.set(item.parentId, [item]);
|
|
27596
|
+
} else {
|
|
27597
|
+
roots.push(item);
|
|
27598
|
+
}
|
|
27599
|
+
}
|
|
27600
|
+
return /* @__PURE__ */ jsx(Box, { className: `py-1 overflow-y-auto ${className ?? ""}`, role: "tree", children: roots.map((item) => /* @__PURE__ */ jsx(
|
|
27601
|
+
FlatTreeNodeItem,
|
|
27602
|
+
{
|
|
27603
|
+
item,
|
|
27604
|
+
depth: 0,
|
|
27605
|
+
indent,
|
|
27606
|
+
childrenByParent,
|
|
27607
|
+
onNodeSelect,
|
|
27608
|
+
defaultExpanded: true
|
|
27609
|
+
},
|
|
27610
|
+
item.id
|
|
27611
|
+
)) });
|
|
27612
|
+
}
|
|
27613
|
+
if (!tree || tree.length === 0) return null;
|
|
27464
27614
|
return /* @__PURE__ */ jsx(Box, { className: `py-1 overflow-y-auto ${className ?? ""}`, role: "tree", children: tree.map((node) => /* @__PURE__ */ jsx(
|
|
27465
27615
|
TreeNodeItem,
|
|
27466
27616
|
{
|
|
@@ -28855,7 +29005,7 @@ var init_debug = __esm({
|
|
|
28855
29005
|
createLogger("almadar:ui:debug:game-state");
|
|
28856
29006
|
}
|
|
28857
29007
|
});
|
|
28858
|
-
var isRelationsDebugEnabled, RelationSelect;
|
|
29008
|
+
var isRelationsDebugEnabled, MANY_CARDINALITIES, RelationSelect;
|
|
28859
29009
|
var init_RelationSelect = __esm({
|
|
28860
29010
|
"components/core/molecules/RelationSelect.tsx"() {
|
|
28861
29011
|
"use client";
|
|
@@ -28869,6 +29019,11 @@ var init_RelationSelect = __esm({
|
|
|
28869
29019
|
init_Typography();
|
|
28870
29020
|
init_debug();
|
|
28871
29021
|
isRelationsDebugEnabled = () => isDebugEnabled();
|
|
29022
|
+
MANY_CARDINALITIES = [
|
|
29023
|
+
"many",
|
|
29024
|
+
"one-to-many",
|
|
29025
|
+
"many-to-many"
|
|
29026
|
+
];
|
|
28872
29027
|
RelationSelect = ({
|
|
28873
29028
|
value,
|
|
28874
29029
|
onChange,
|
|
@@ -30493,6 +30648,7 @@ var init_MathCanvas = __esm({
|
|
|
30493
30648
|
"components/learning/molecules/MathCanvas.tsx"() {
|
|
30494
30649
|
"use client";
|
|
30495
30650
|
init_useEventBus();
|
|
30651
|
+
init_perf();
|
|
30496
30652
|
init_atoms();
|
|
30497
30653
|
init_Stack();
|
|
30498
30654
|
init_LearningCanvas();
|
|
@@ -30533,17 +30689,21 @@ var init_MathCanvas = __esm({
|
|
|
30533
30689
|
error
|
|
30534
30690
|
}) => {
|
|
30535
30691
|
const eventBus = useEventBus();
|
|
30692
|
+
const keyMapKey = keyMap ? JSON.stringify(keyMap) : null;
|
|
30693
|
+
const keyUpMapKey = keyUpMap ? JSON.stringify(keyUpMap) : null;
|
|
30694
|
+
const stableKeyMap = useMemo(() => keyMap, [keyMapKey]);
|
|
30695
|
+
const stableKeyUpMap = useMemo(() => keyUpMap, [keyUpMapKey]);
|
|
30536
30696
|
useEffect(() => {
|
|
30537
|
-
if (!
|
|
30697
|
+
if (!stableKeyMap && !stableKeyUpMap) return;
|
|
30538
30698
|
const onDown = (e) => {
|
|
30539
|
-
const ev =
|
|
30699
|
+
const ev = stableKeyMap?.[e.code];
|
|
30540
30700
|
if (ev) {
|
|
30541
30701
|
eventBus.emit(`UI:${ev}`, {});
|
|
30542
30702
|
e.preventDefault();
|
|
30543
30703
|
}
|
|
30544
30704
|
};
|
|
30545
30705
|
const onUp = (e) => {
|
|
30546
|
-
const ev =
|
|
30706
|
+
const ev = stableKeyUpMap?.[e.code];
|
|
30547
30707
|
if (ev) eventBus.emit(`UI:${ev}`, {});
|
|
30548
30708
|
};
|
|
30549
30709
|
window.addEventListener("keydown", onDown);
|
|
@@ -30552,8 +30712,9 @@ var init_MathCanvas = __esm({
|
|
|
30552
30712
|
window.removeEventListener("keydown", onDown);
|
|
30553
30713
|
window.removeEventListener("keyup", onUp);
|
|
30554
30714
|
};
|
|
30555
|
-
}, [
|
|
30715
|
+
}, [stableKeyMap, stableKeyUpMap, eventBus]);
|
|
30556
30716
|
const derivedShapes = useMemo(() => {
|
|
30717
|
+
const _perfT = perfStart("mathcanvas:derive");
|
|
30557
30718
|
const out = [];
|
|
30558
30719
|
const margin = 24;
|
|
30559
30720
|
const plotW = width - margin * 2;
|
|
@@ -30797,6 +30958,7 @@ var init_MathCanvas = __esm({
|
|
|
30797
30958
|
}
|
|
30798
30959
|
}
|
|
30799
30960
|
out.push(...shapes);
|
|
30961
|
+
perfEnd("mathcanvas:derive", _perfT);
|
|
30800
30962
|
return out;
|
|
30801
30963
|
}, [
|
|
30802
30964
|
width,
|
|
@@ -32060,12 +32222,12 @@ var init_MapView = __esm({
|
|
|
32060
32222
|
shadowSize: [41, 41]
|
|
32061
32223
|
});
|
|
32062
32224
|
L.Marker.prototype.options.icon = defaultIcon;
|
|
32063
|
-
const { useEffect: useEffect67, useRef:
|
|
32225
|
+
const { useEffect: useEffect67, useRef: useRef65, useCallback: useCallback97, useState: useState95 } = React87__default;
|
|
32064
32226
|
const { Typography: Typography2 } = await Promise.resolve().then(() => (init_Typography(), Typography_exports));
|
|
32065
32227
|
const { useEventBus: useEventBus2 } = await Promise.resolve().then(() => (init_useEventBus(), useEventBus_exports));
|
|
32066
32228
|
function MapUpdater({ centerLat, centerLng, zoom }) {
|
|
32067
32229
|
const map = useMap();
|
|
32068
|
-
const prevRef =
|
|
32230
|
+
const prevRef = useRef65({ centerLat, centerLng, zoom });
|
|
32069
32231
|
useEffect67(() => {
|
|
32070
32232
|
const prev = prevRef.current;
|
|
32071
32233
|
if (prev.centerLat !== centerLat || prev.centerLng !== centerLng || prev.zoom !== zoom) {
|
|
@@ -37150,7 +37312,7 @@ var init_RichBlockEditor = __esm({
|
|
|
37150
37312
|
{
|
|
37151
37313
|
variant: "bordered",
|
|
37152
37314
|
padding: "none",
|
|
37153
|
-
className: cn("flex flex-col", className),
|
|
37315
|
+
className: cn("flex flex-col text-card-foreground", className),
|
|
37154
37316
|
children: [
|
|
37155
37317
|
enableBlocks && showToolbar && !readOnly && /* @__PURE__ */ jsx(
|
|
37156
37318
|
Box,
|
|
@@ -42378,6 +42540,7 @@ var init_DetailPanel = __esm({
|
|
|
42378
42540
|
"use client";
|
|
42379
42541
|
init_atoms();
|
|
42380
42542
|
init_Box();
|
|
42543
|
+
init_Input();
|
|
42381
42544
|
init_Stack();
|
|
42382
42545
|
init_SimpleGrid();
|
|
42383
42546
|
init_Menu();
|
|
@@ -42393,6 +42556,7 @@ var init_DetailPanel = __esm({
|
|
|
42393
42556
|
ReactMarkdown2 = lazy(() => import('react-markdown'));
|
|
42394
42557
|
DetailPanel = ({
|
|
42395
42558
|
title: propTitle,
|
|
42559
|
+
onTitleCommit,
|
|
42396
42560
|
subtitle,
|
|
42397
42561
|
status,
|
|
42398
42562
|
avatar,
|
|
@@ -42414,6 +42578,7 @@ var init_DetailPanel = __esm({
|
|
|
42414
42578
|
}) => {
|
|
42415
42579
|
const eventBus = useEventBus();
|
|
42416
42580
|
const { t } = useTranslate();
|
|
42581
|
+
const [titleDraft, setTitleDraft] = React87__default.useState(null);
|
|
42417
42582
|
const isFieldDefArray = (arr) => {
|
|
42418
42583
|
if (!arr || arr.length === 0) return false;
|
|
42419
42584
|
const first = arr[0];
|
|
@@ -42634,6 +42799,50 @@ var init_DetailPanel = __esm({
|
|
|
42634
42799
|
}),
|
|
42635
42800
|
status && /* @__PURE__ */ jsx(Badge, { variant: status.variant ?? "default", children: status.label })
|
|
42636
42801
|
] });
|
|
42802
|
+
const commitTitle = () => {
|
|
42803
|
+
if (!onTitleCommit) return;
|
|
42804
|
+
const next = (titleDraft ?? "").trim();
|
|
42805
|
+
setTitleDraft(null);
|
|
42806
|
+
if (!next || next === title) return;
|
|
42807
|
+
onTitleCommit(next, normalizedData?.id !== void 0 ? String(normalizedData.id) : "");
|
|
42808
|
+
};
|
|
42809
|
+
const titleNode = onTitleCommit && titleDraft !== null ? /* @__PURE__ */ jsx(
|
|
42810
|
+
Input,
|
|
42811
|
+
{
|
|
42812
|
+
value: titleDraft,
|
|
42813
|
+
autoFocus: true,
|
|
42814
|
+
"aria-label": t("common.title"),
|
|
42815
|
+
className: "h-auto py-1 text-3xl font-bold tracking-tight",
|
|
42816
|
+
onChange: (e) => setTitleDraft(e.target.value),
|
|
42817
|
+
onBlur: commitTitle,
|
|
42818
|
+
onKeyDown: (e) => {
|
|
42819
|
+
if (e.key === "Enter") {
|
|
42820
|
+
e.preventDefault();
|
|
42821
|
+
commitTitle();
|
|
42822
|
+
} else if (e.key === "Escape") {
|
|
42823
|
+
e.preventDefault();
|
|
42824
|
+
setTitleDraft(null);
|
|
42825
|
+
}
|
|
42826
|
+
},
|
|
42827
|
+
"data-testid": "detail-title-input"
|
|
42828
|
+
}
|
|
42829
|
+
) : onTitleCommit ? /* @__PURE__ */ jsx(
|
|
42830
|
+
Box,
|
|
42831
|
+
{
|
|
42832
|
+
role: "button",
|
|
42833
|
+
tabIndex: 0,
|
|
42834
|
+
className: "cursor-text rounded px-1 -mx-1 transition-colors hover:bg-muted/40",
|
|
42835
|
+
onClick: () => setTitleDraft(title ?? ""),
|
|
42836
|
+
onKeyDown: (e) => {
|
|
42837
|
+
if (e.key === "Enter" || e.key === " ") {
|
|
42838
|
+
e.preventDefault();
|
|
42839
|
+
setTitleDraft(title ?? "");
|
|
42840
|
+
}
|
|
42841
|
+
},
|
|
42842
|
+
"data-testid": "detail-title-editable",
|
|
42843
|
+
children: /* @__PURE__ */ jsx(Typography, { variant: "h2", weight: "bold", children: title || "Details" })
|
|
42844
|
+
}
|
|
42845
|
+
) : /* @__PURE__ */ jsx(Typography, { variant: "h2", weight: "bold", children: title || "Details" });
|
|
42637
42846
|
const content = /* @__PURE__ */ jsx(Card, { variant: "elevated", children: /* @__PURE__ */ jsxs(VStack, { gap: "md", className: "p-6", children: [
|
|
42638
42847
|
/* @__PURE__ */ jsxs(HStack, { justify: "between", align: "start", gap: "md", children: [
|
|
42639
42848
|
/* @__PURE__ */ jsxs(HStack, { align: "start", gap: "sm", className: "min-w-0", children: [
|
|
@@ -42653,7 +42862,7 @@ var init_DetailPanel = __esm({
|
|
|
42653
42862
|
avatar,
|
|
42654
42863
|
/* @__PURE__ */ jsxs(VStack, { gap: "xs", className: "min-w-0", children: [
|
|
42655
42864
|
/* @__PURE__ */ jsxs(HStack, { align: "center", gap: "sm", wrap: true, children: [
|
|
42656
|
-
|
|
42865
|
+
titleNode,
|
|
42657
42866
|
statusBadges
|
|
42658
42867
|
] }),
|
|
42659
42868
|
subtitle && /* @__PURE__ */ jsx(Typography, { variant: "body", color: "secondary", children: subtitle })
|
|
@@ -42989,6 +43198,9 @@ function determineInputType(field) {
|
|
|
42989
43198
|
if (field.type === "relation" || field.relation) {
|
|
42990
43199
|
return "relation";
|
|
42991
43200
|
}
|
|
43201
|
+
if (field.type === "array") {
|
|
43202
|
+
return "array";
|
|
43203
|
+
}
|
|
42992
43204
|
if (field.type === "enum" || field.values || getEnumOptions(field).length > 0) {
|
|
42993
43205
|
return "select";
|
|
42994
43206
|
}
|
|
@@ -43064,6 +43276,7 @@ var init_Form = __esm({
|
|
|
43064
43276
|
init_Typography();
|
|
43065
43277
|
init_Icon();
|
|
43066
43278
|
init_RelationSelect();
|
|
43279
|
+
init_TagInput();
|
|
43067
43280
|
init_UploadDropZone();
|
|
43068
43281
|
init_Alert();
|
|
43069
43282
|
init_useEventBus();
|
|
@@ -43143,7 +43356,7 @@ var init_Form = __esm({
|
|
|
43143
43356
|
values: "values" in f3 ? f3.values : void 0,
|
|
43144
43357
|
min: f3.min,
|
|
43145
43358
|
max: f3.max,
|
|
43146
|
-
relation: "relation" in f3 ? { entity: f3.relation.entity } : void 0
|
|
43359
|
+
relation: "relation" in f3 ? { entity: f3.relation.entity, cardinality: f3.relation.cardinality } : void 0
|
|
43147
43360
|
})
|
|
43148
43361
|
);
|
|
43149
43362
|
}, [entity, fields]);
|
|
@@ -43210,7 +43423,7 @@ var init_Form = __esm({
|
|
|
43210
43423
|
});
|
|
43211
43424
|
debug(
|
|
43212
43425
|
"forms",
|
|
43213
|
-
`Calculation triggered: ${calc.variableName} = ${value}`
|
|
43426
|
+
`Calculation triggered: ${calc.variableName} = ${String(value)}`
|
|
43214
43427
|
);
|
|
43215
43428
|
}
|
|
43216
43429
|
});
|
|
@@ -43378,7 +43591,7 @@ var init_Form = __esm({
|
|
|
43378
43591
|
values: "values" in entityField ? entityField.values : void 0,
|
|
43379
43592
|
min: entityField.min,
|
|
43380
43593
|
max: entityField.max,
|
|
43381
|
-
relation: "relation" in entityField ? { entity: entityField.relation.entity } : void 0
|
|
43594
|
+
relation: "relation" in entityField ? { entity: entityField.relation.entity, cardinality: entityField.relation.cardinality } : void 0
|
|
43382
43595
|
};
|
|
43383
43596
|
}
|
|
43384
43597
|
return { name: field, type: "string" };
|
|
@@ -43490,6 +43703,22 @@ var init_Form = __esm({
|
|
|
43490
43703
|
case "relation": {
|
|
43491
43704
|
const relationOptions = relationsData[fieldName] || [];
|
|
43492
43705
|
const relationLoading = relationsLoading[fieldName] || false;
|
|
43706
|
+
if (field.relation?.cardinality !== void 0 && MANY_CARDINALITIES.includes(field.relation.cardinality)) {
|
|
43707
|
+
const selectedValues = Array.isArray(currentValue) ? currentValue.map((v) => String(v)) : [];
|
|
43708
|
+
return /* @__PURE__ */ jsx(
|
|
43709
|
+
Select,
|
|
43710
|
+
{
|
|
43711
|
+
...commonProps,
|
|
43712
|
+
multiple: true,
|
|
43713
|
+
searchable: true,
|
|
43714
|
+
clearable: true,
|
|
43715
|
+
options: [...relationOptions],
|
|
43716
|
+
value: selectedValues,
|
|
43717
|
+
onValueChange: (value) => handleChange(fieldName, Array.isArray(value) ? value : [value]),
|
|
43718
|
+
placeholder: field.placeholder || `Select ${label}...`
|
|
43719
|
+
}
|
|
43720
|
+
);
|
|
43721
|
+
}
|
|
43493
43722
|
return /* @__PURE__ */ jsx(
|
|
43494
43723
|
RelationSelect,
|
|
43495
43724
|
{
|
|
@@ -43504,6 +43733,18 @@ var init_Form = __esm({
|
|
|
43504
43733
|
}
|
|
43505
43734
|
);
|
|
43506
43735
|
}
|
|
43736
|
+
case "array": {
|
|
43737
|
+
const arrayValue = Array.isArray(currentValue) ? currentValue.map((v) => String(v)) : currentValue != null && currentValue !== "" ? [String(currentValue)] : [];
|
|
43738
|
+
return /* @__PURE__ */ jsx(
|
|
43739
|
+
TagInput,
|
|
43740
|
+
{
|
|
43741
|
+
placeholder: field.placeholder,
|
|
43742
|
+
disabled: isLoading,
|
|
43743
|
+
value: arrayValue,
|
|
43744
|
+
onChange: (next) => handleChange(fieldName, [...next])
|
|
43745
|
+
}
|
|
43746
|
+
);
|
|
43747
|
+
}
|
|
43507
43748
|
case "number":
|
|
43508
43749
|
return /* @__PURE__ */ jsx(
|
|
43509
43750
|
Input,
|
|
@@ -49053,7 +49294,10 @@ function enrichFormFields(fields, entityDef) {
|
|
|
49053
49294
|
enriched.values = entityField.enumValues;
|
|
49054
49295
|
}
|
|
49055
49296
|
if (entityField.relation) {
|
|
49056
|
-
enriched.relation =
|
|
49297
|
+
enriched.relation = {
|
|
49298
|
+
entity: entityField.relation.entity,
|
|
49299
|
+
cardinality: entityField.relation.cardinality
|
|
49300
|
+
};
|
|
49057
49301
|
}
|
|
49058
49302
|
return enriched;
|
|
49059
49303
|
}
|
|
@@ -49081,7 +49325,10 @@ function enrichFormFields(fields, entityDef) {
|
|
|
49081
49325
|
}
|
|
49082
49326
|
}
|
|
49083
49327
|
if (!obj.relation && entityField.relation) {
|
|
49084
|
-
enriched.relation =
|
|
49328
|
+
enriched.relation = {
|
|
49329
|
+
entity: entityField.relation.entity,
|
|
49330
|
+
cardinality: entityField.relation.cardinality
|
|
49331
|
+
};
|
|
49085
49332
|
}
|
|
49086
49333
|
return enriched;
|
|
49087
49334
|
}
|
|
@@ -49096,7 +49343,12 @@ function enrichDetailFields(fields, entityDef) {
|
|
|
49096
49343
|
const meta = { type: entityField.type };
|
|
49097
49344
|
const values = entityField.values ?? entityField.enumValues;
|
|
49098
49345
|
if (values && values.length > 0) meta.values = values;
|
|
49099
|
-
if (entityField.relation)
|
|
49346
|
+
if (entityField.relation) {
|
|
49347
|
+
meta.relation = {
|
|
49348
|
+
entity: entityField.relation.entity,
|
|
49349
|
+
cardinality: entityField.relation.cardinality
|
|
49350
|
+
};
|
|
49351
|
+
}
|
|
49100
49352
|
return meta;
|
|
49101
49353
|
};
|
|
49102
49354
|
return fields.map((field) => {
|
|
@@ -49650,6 +49902,33 @@ function isPlainConfigObject(value) {
|
|
|
49650
49902
|
const proto = Object.getPrototypeOf(value);
|
|
49651
49903
|
return proto === Object.prototype || proto === null;
|
|
49652
49904
|
}
|
|
49905
|
+
function subtreeHasTraitRef(value) {
|
|
49906
|
+
if (isEvaluatorResolvedData(value)) return false;
|
|
49907
|
+
const cached = traitRefPresenceCache.get(value);
|
|
49908
|
+
if (cached !== void 0) return cached;
|
|
49909
|
+
let found = false;
|
|
49910
|
+
const children = Array.isArray(value) ? value : Object.values(value);
|
|
49911
|
+
for (const child of children) {
|
|
49912
|
+
if (typeof child === "string" && TRAIT_BINDING_RE.test(child)) {
|
|
49913
|
+
found = true;
|
|
49914
|
+
break;
|
|
49915
|
+
}
|
|
49916
|
+
if (isRenderBindingMarker(child)) continue;
|
|
49917
|
+
if (Array.isArray(child)) {
|
|
49918
|
+
if (subtreeHasTraitRef(child)) {
|
|
49919
|
+
found = true;
|
|
49920
|
+
break;
|
|
49921
|
+
}
|
|
49922
|
+
} else if (child !== null && typeof child === "object" && isPlainConfigObject(child)) {
|
|
49923
|
+
if (subtreeHasTraitRef(child)) {
|
|
49924
|
+
found = true;
|
|
49925
|
+
break;
|
|
49926
|
+
}
|
|
49927
|
+
}
|
|
49928
|
+
}
|
|
49929
|
+
traitRefPresenceCache.set(value, found);
|
|
49930
|
+
return found;
|
|
49931
|
+
}
|
|
49653
49932
|
function substituteTraitRefsDeep(value, pathKey) {
|
|
49654
49933
|
if (isRenderBindingMarker(value)) return value;
|
|
49655
49934
|
if (typeof value === "string") {
|
|
@@ -49664,11 +49943,13 @@ function substituteTraitRefsDeep(value, pathKey) {
|
|
|
49664
49943
|
return value;
|
|
49665
49944
|
}
|
|
49666
49945
|
if (Array.isArray(value)) {
|
|
49946
|
+
if (!subtreeHasTraitRef(value)) return value;
|
|
49667
49947
|
return value.map(
|
|
49668
49948
|
(item, i) => substituteTraitRefsDeep(item, `${pathKey}[${i}]`)
|
|
49669
49949
|
);
|
|
49670
49950
|
}
|
|
49671
49951
|
if (typeof value === "object" && isPlainConfigObject(value)) {
|
|
49952
|
+
if (!subtreeHasTraitRef(value)) return value;
|
|
49672
49953
|
const out = {};
|
|
49673
49954
|
for (const [k, v] of Object.entries(value)) {
|
|
49674
49955
|
out[k] = substituteTraitRefsDeep(v, `${pathKey}.${k}`);
|
|
@@ -49695,6 +49976,10 @@ function renderPatternProps(props, onDismiss, propsSchema) {
|
|
|
49695
49976
|
};
|
|
49696
49977
|
rendered[key] = /* @__PURE__ */ jsx(SlotContentRenderer, { content: childContent, onDismiss });
|
|
49697
49978
|
} else if (Array.isArray(value)) {
|
|
49979
|
+
if (!isEvaluatorResolvedData(value) && value.some((el) => isPatternConfig(el))) ; else if (!subtreeHasTraitRef(value)) {
|
|
49980
|
+
rendered[key] = value;
|
|
49981
|
+
continue;
|
|
49982
|
+
}
|
|
49698
49983
|
const isDataArray = propsSchema?.[key]?.items?.types?.includes("object") ?? false;
|
|
49699
49984
|
rendered[key] = value.map((item, i) => {
|
|
49700
49985
|
const el = item;
|
|
@@ -49957,7 +50242,7 @@ function UISlotRenderer({
|
|
|
49957
50242
|
}
|
|
49958
50243
|
return wrapped;
|
|
49959
50244
|
}
|
|
49960
|
-
var scopeWrapLog, TRAIT_BINDING_RE, SuspenseConfigContext, SlotContainedContext, SLOT_SKELETON_MAP, SELF_OVERLAY_PATTERNS, CONTENT_NODE_SLOTS, PATTERNS_WITH_CHILDREN;
|
|
50245
|
+
var scopeWrapLog, TRAIT_BINDING_RE, SuspenseConfigContext, SlotContainedContext, SLOT_SKELETON_MAP, SELF_OVERLAY_PATTERNS, CONTENT_NODE_SLOTS, PATTERNS_WITH_CHILDREN, traitRefPresenceCache;
|
|
49961
50246
|
var init_UISlotRenderer = __esm({
|
|
49962
50247
|
"components/core/organisms/UISlotRenderer.tsx"() {
|
|
49963
50248
|
"use client";
|
|
@@ -50031,6 +50316,7 @@ var init_UISlotRenderer = __esm({
|
|
|
50031
50316
|
"alert",
|
|
50032
50317
|
"dialog"
|
|
50033
50318
|
]);
|
|
50319
|
+
traitRefPresenceCache = /* @__PURE__ */ new WeakMap();
|
|
50034
50320
|
UISlotRenderer.displayName = "UISlotRenderer";
|
|
50035
50321
|
}
|
|
50036
50322
|
});
|
|
@@ -51135,6 +51421,53 @@ function useNavigationId2() {
|
|
|
51135
51421
|
|
|
51136
51422
|
// providers/ServerBridge.tsx
|
|
51137
51423
|
init_useEventBus();
|
|
51424
|
+
|
|
51425
|
+
// lib/tick-send-relay.ts
|
|
51426
|
+
function createTickSendRelay(send) {
|
|
51427
|
+
const lanes = /* @__PURE__ */ new Map();
|
|
51428
|
+
const flush = (key, lane) => {
|
|
51429
|
+
const next = lane.pending;
|
|
51430
|
+
lane.pending = void 0;
|
|
51431
|
+
if (next === void 0) {
|
|
51432
|
+
lane.inFlight = false;
|
|
51433
|
+
return;
|
|
51434
|
+
}
|
|
51435
|
+
lane.inFlight = true;
|
|
51436
|
+
void send(key, next).catch(() => void 0).then(() => flush(key, lane));
|
|
51437
|
+
};
|
|
51438
|
+
return {
|
|
51439
|
+
send(key, value) {
|
|
51440
|
+
const lane = lanes.get(key) ?? { inFlight: false };
|
|
51441
|
+
lanes.set(key, lane);
|
|
51442
|
+
if (lane.inFlight) {
|
|
51443
|
+
lane.pending = value;
|
|
51444
|
+
return;
|
|
51445
|
+
}
|
|
51446
|
+
lane.pending = value;
|
|
51447
|
+
flush(key, lane);
|
|
51448
|
+
},
|
|
51449
|
+
clear() {
|
|
51450
|
+
for (const lane of lanes.values()) {
|
|
51451
|
+
lane.pending = void 0;
|
|
51452
|
+
}
|
|
51453
|
+
}
|
|
51454
|
+
};
|
|
51455
|
+
}
|
|
51456
|
+
|
|
51457
|
+
// lib/command-send-pump.ts
|
|
51458
|
+
function createCommandSendPump() {
|
|
51459
|
+
let tail = Promise.resolve();
|
|
51460
|
+
return {
|
|
51461
|
+
enqueue(job) {
|
|
51462
|
+
const result = tail.then(job);
|
|
51463
|
+
tail = result.then(
|
|
51464
|
+
() => void 0,
|
|
51465
|
+
() => void 0
|
|
51466
|
+
);
|
|
51467
|
+
return result;
|
|
51468
|
+
}
|
|
51469
|
+
};
|
|
51470
|
+
}
|
|
51138
51471
|
var xOrbitalLog = createLogger("almadar:runtime:cross-orbital");
|
|
51139
51472
|
var serverBridgeLog = createLogger("almadar:ui:server-bridge");
|
|
51140
51473
|
function reEmitServerEvent(eventBus, emitted, origin) {
|
|
@@ -51223,8 +51556,8 @@ function createHttpTransport(serverUrl) {
|
|
|
51223
51556
|
} catch {
|
|
51224
51557
|
}
|
|
51225
51558
|
},
|
|
51226
|
-
sendEvent: async (orbitalName, event, payload, clientId) => {
|
|
51227
|
-
const body = { event, payload, clientId };
|
|
51559
|
+
sendEvent: async (orbitalName, event, payload, clientId, tick, sourceTrait) => {
|
|
51560
|
+
const body = { event, payload, clientId, tick, sourceTrait };
|
|
51228
51561
|
const res = await fetch(`${serverUrl}/${orbitalName}/events`, {
|
|
51229
51562
|
method: "POST",
|
|
51230
51563
|
headers: { "Content-Type": "application/json" },
|
|
@@ -51269,96 +51602,118 @@ function ServerBridgeProvider({
|
|
|
51269
51602
|
async () => transport.unregister(),
|
|
51270
51603
|
[transport]
|
|
51271
51604
|
);
|
|
51272
|
-
const
|
|
51605
|
+
const tickRelay = useMemo(
|
|
51606
|
+
() => createTickSendRelay(async (_key, snap) => {
|
|
51607
|
+
await transport.sendEvent(snap.orbitalName, snap.event, snap.payload, getTabClientId(), snap.tick, snap.sourceTrait);
|
|
51608
|
+
}),
|
|
51609
|
+
[transport]
|
|
51610
|
+
);
|
|
51611
|
+
useEffect(() => () => tickRelay.clear(), [tickRelay]);
|
|
51612
|
+
const commandPump = useMemo(createCommandSendPump, []);
|
|
51613
|
+
const disposedRef = useRef(false);
|
|
51614
|
+
useEffect(() => {
|
|
51615
|
+
disposedRef.current = false;
|
|
51616
|
+
return () => {
|
|
51617
|
+
disposedRef.current = true;
|
|
51618
|
+
};
|
|
51619
|
+
}, []);
|
|
51620
|
+
const sendEvent = useCallback(async (orbitalName, event, payload, tick, sourceTrait) => {
|
|
51273
51621
|
const emptyMeta = { success: false, clientEffects: 0, dataEntities: {}, emittedEvents: [] };
|
|
51274
51622
|
if (!connected) return { effects: [], meta: emptyMeta };
|
|
51275
|
-
|
|
51276
|
-
|
|
51277
|
-
|
|
51278
|
-
|
|
51279
|
-
|
|
51280
|
-
|
|
51281
|
-
|
|
51282
|
-
|
|
51283
|
-
|
|
51284
|
-
|
|
51285
|
-
|
|
51286
|
-
|
|
51287
|
-
|
|
51288
|
-
|
|
51289
|
-
|
|
51290
|
-
|
|
51291
|
-
|
|
51292
|
-
|
|
51293
|
-
|
|
51294
|
-
|
|
51295
|
-
|
|
51296
|
-
|
|
51297
|
-
|
|
51298
|
-
|
|
51299
|
-
|
|
51300
|
-
|
|
51301
|
-
|
|
51302
|
-
|
|
51303
|
-
|
|
51304
|
-
|
|
51305
|
-
|
|
51306
|
-
|
|
51307
|
-
|
|
51308
|
-
|
|
51309
|
-
|
|
51310
|
-
|
|
51311
|
-
|
|
51312
|
-
|
|
51313
|
-
|
|
51314
|
-
|
|
51315
|
-
|
|
51316
|
-
|
|
51317
|
-
|
|
51318
|
-
|
|
51319
|
-
|
|
51320
|
-
|
|
51321
|
-
|
|
51322
|
-
|
|
51323
|
-
|
|
51324
|
-
|
|
51325
|
-
|
|
51326
|
-
|
|
51327
|
-
|
|
51328
|
-
|
|
51329
|
-
|
|
51330
|
-
|
|
51331
|
-
|
|
51332
|
-
)
|
|
51623
|
+
if (tick !== void 0) {
|
|
51624
|
+
tickRelay.send(`${orbitalName}:${event}`, { orbitalName, event, payload, tick, sourceTrait });
|
|
51625
|
+
return { effects: [], meta: { ...emptyMeta, success: true } };
|
|
51626
|
+
}
|
|
51627
|
+
return commandPump.enqueue(async () => {
|
|
51628
|
+
if (disposedRef.current) return { effects: [], meta: emptyMeta };
|
|
51629
|
+
try {
|
|
51630
|
+
const result = await transport.sendEvent(orbitalName, event, payload, getTabClientId(), tick, sourceTrait);
|
|
51631
|
+
const effects = [];
|
|
51632
|
+
const responseData = result.data || {};
|
|
51633
|
+
const dataEntities = {};
|
|
51634
|
+
for (const [entityName, records] of Object.entries(responseData)) {
|
|
51635
|
+
dataEntities[entityName] = Array.isArray(records) ? records.length : 0;
|
|
51636
|
+
}
|
|
51637
|
+
const meta = {
|
|
51638
|
+
success: !!result.success,
|
|
51639
|
+
clientEffects: result.clientEffects?.length ?? 0,
|
|
51640
|
+
dataEntities,
|
|
51641
|
+
data: responseData,
|
|
51642
|
+
emittedEvents: result.emittedEvents?.map((e) => e.event) ?? [],
|
|
51643
|
+
error: result.error
|
|
51644
|
+
};
|
|
51645
|
+
if (result.success) {
|
|
51646
|
+
const tagged = result.clientEffectsByTrait;
|
|
51647
|
+
const tuples = tagged ? tagged.map((entry) => ({ effect: entry.effect, traitName: entry.traitName })) : (result.clientEffects ?? []).map((eff) => ({ effect: eff }));
|
|
51648
|
+
for (const { effect, traitName } of tuples) {
|
|
51649
|
+
const effectType = effect[0];
|
|
51650
|
+
if (effectType === "render-ui") {
|
|
51651
|
+
const slot = effect[1];
|
|
51652
|
+
const pattern = effect[2];
|
|
51653
|
+
effects.push({
|
|
51654
|
+
type: "render-ui",
|
|
51655
|
+
slot,
|
|
51656
|
+
pattern: pattern !== null && typeof pattern === "object" ? pattern : void 0,
|
|
51657
|
+
traitName
|
|
51658
|
+
});
|
|
51659
|
+
} else if (effectType === "navigate") {
|
|
51660
|
+
const route = effect[1];
|
|
51661
|
+
const rawParams = effect[2];
|
|
51662
|
+
const rawOptions = effect[3];
|
|
51663
|
+
const optionsObj = rawOptions !== null && rawOptions !== void 0 && typeof rawOptions === "object" && !Array.isArray(rawOptions) ? rawOptions : void 0;
|
|
51664
|
+
const crumb = typeof optionsObj?.crumb === "string" ? optionsObj.crumb : void 0;
|
|
51665
|
+
effects.push({
|
|
51666
|
+
type: "navigate",
|
|
51667
|
+
route,
|
|
51668
|
+
params: rawParams !== null && rawParams !== void 0 && typeof rawParams === "object" && !Array.isArray(rawParams) ? rawParams : void 0,
|
|
51669
|
+
crumb,
|
|
51670
|
+
traitName
|
|
51671
|
+
});
|
|
51672
|
+
} else if (effectType === "navigate-back") {
|
|
51673
|
+
effects.push({ type: "navigate-back", traitName });
|
|
51674
|
+
} else if (effectType === "notify") {
|
|
51675
|
+
const message = effect[1];
|
|
51676
|
+
effects.push({ type: "notify", message: typeof message === "string" ? message : void 0, traitName });
|
|
51677
|
+
}
|
|
51678
|
+
}
|
|
51679
|
+
if (result.emittedEvents) {
|
|
51680
|
+
for (const emitted of result.emittedEvents) {
|
|
51681
|
+
if (emitted.event === event) continue;
|
|
51682
|
+
reEmitServerEvent(
|
|
51683
|
+
eventBus,
|
|
51684
|
+
{ ...emitted, source: { ...emitted.source, dispatched: true } },
|
|
51685
|
+
orbitalName
|
|
51686
|
+
);
|
|
51687
|
+
}
|
|
51333
51688
|
}
|
|
51689
|
+
} else if (result.error) {
|
|
51690
|
+
xOrbitalLog.warn("response:fail", {
|
|
51691
|
+
orbital: orbitalName,
|
|
51692
|
+
event,
|
|
51693
|
+
error: result.error
|
|
51694
|
+
});
|
|
51334
51695
|
}
|
|
51335
|
-
|
|
51336
|
-
|
|
51337
|
-
|
|
51338
|
-
|
|
51339
|
-
|
|
51340
|
-
|
|
51341
|
-
|
|
51342
|
-
|
|
51343
|
-
|
|
51344
|
-
|
|
51345
|
-
|
|
51346
|
-
|
|
51347
|
-
|
|
51348
|
-
|
|
51349
|
-
|
|
51350
|
-
|
|
51351
|
-
}
|
|
51352
|
-
|
|
51353
|
-
xOrbitalLog.error("response:network", {
|
|
51354
|
-
orbital: orbitalName,
|
|
51355
|
-
event,
|
|
51356
|
-
error: msg
|
|
51357
|
-
});
|
|
51696
|
+
return { effects, meta };
|
|
51697
|
+
} catch (err) {
|
|
51698
|
+
const msg = err instanceof Error ? err.message : String(err);
|
|
51699
|
+
if (err instanceof TypeError) {
|
|
51700
|
+
xOrbitalLog.warn("response:network", {
|
|
51701
|
+
orbital: orbitalName,
|
|
51702
|
+
event,
|
|
51703
|
+
error: msg,
|
|
51704
|
+
reason: "peer endpoint unreachable (expected in standalone single-orbital mode)"
|
|
51705
|
+
});
|
|
51706
|
+
} else {
|
|
51707
|
+
xOrbitalLog.error("response:network", {
|
|
51708
|
+
orbital: orbitalName,
|
|
51709
|
+
event,
|
|
51710
|
+
error: msg
|
|
51711
|
+
});
|
|
51712
|
+
}
|
|
51713
|
+
return { effects: [], meta: { ...emptyMeta, error: msg } };
|
|
51358
51714
|
}
|
|
51359
|
-
|
|
51360
|
-
|
|
51361
|
-
}, [connected, transport, eventBus]);
|
|
51715
|
+
});
|
|
51716
|
+
}, [connected, transport, eventBus, tickRelay, commandPump]);
|
|
51362
51717
|
useEffect(() => {
|
|
51363
51718
|
if (!schema) return;
|
|
51364
51719
|
let cancelled = false;
|