langchain_agentx_stream_ui 0.3.3 → 0.3.5
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/{chunk-6ORA5RMV.js → chunk-6PWGGGUK.js} +11 -2
- package/dist/chunk-6PWGGGUK.js.map +1 -0
- package/dist/{chunk-ISQ7JWGD.js → chunk-FT6UUKPS.js} +2 -2
- package/dist/index.d.ts +1 -0
- package/dist/index.js +196 -97
- package/dist/index.js.map +1 -1
- package/dist/multi-session.js +2 -2
- package/dist/virtual.js +1 -1
- package/package.json +1 -1
- package/dist/chunk-6ORA5RMV.js.map +0 -1
- /package/dist/{chunk-ISQ7JWGD.js.map → chunk-FT6UUKPS.js.map} +0 -0
|
@@ -24,7 +24,7 @@ import {
|
|
|
24
24
|
useSessionStatus,
|
|
25
25
|
useSessionViewOptions,
|
|
26
26
|
useToolDisplayOptions
|
|
27
|
-
} from "./chunk-
|
|
27
|
+
} from "./chunk-6PWGGGUK.js";
|
|
28
28
|
import {
|
|
29
29
|
createDefaultToolRegistry
|
|
30
30
|
} from "./chunk-FL2G7SV3.js";
|
|
@@ -1897,4 +1897,4 @@ export {
|
|
|
1897
1897
|
createActiveSessionBridge,
|
|
1898
1898
|
MultiAgentSession
|
|
1899
1899
|
};
|
|
1900
|
-
//# sourceMappingURL=chunk-
|
|
1900
|
+
//# sourceMappingURL=chunk-FT6UUKPS.js.map
|
package/dist/index.d.ts
CHANGED
package/dist/index.js
CHANGED
|
@@ -23,7 +23,7 @@ import {
|
|
|
23
23
|
fixDiagramSvg,
|
|
24
24
|
markEventIdSeen,
|
|
25
25
|
shouldSkipDuplicateEvent
|
|
26
|
-
} from "./chunk-
|
|
26
|
+
} from "./chunk-FT6UUKPS.js";
|
|
27
27
|
import {
|
|
28
28
|
DefaultToolBody,
|
|
29
29
|
InteractionBusContext,
|
|
@@ -110,7 +110,7 @@ import {
|
|
|
110
110
|
useSessionStatus,
|
|
111
111
|
useSessionViewOptions,
|
|
112
112
|
useTimeline
|
|
113
|
-
} from "./chunk-
|
|
113
|
+
} from "./chunk-6PWGGGUK.js";
|
|
114
114
|
import {
|
|
115
115
|
Agent,
|
|
116
116
|
AgentToolBody,
|
|
@@ -1127,20 +1127,26 @@ function computeDurationSeconds(tree) {
|
|
|
1127
1127
|
const seconds = Math.round((maxTs - started) / 1e3);
|
|
1128
1128
|
return seconds > 0 ? seconds : null;
|
|
1129
1129
|
}
|
|
1130
|
-
function
|
|
1130
|
+
function lastLoopTextContent(tree) {
|
|
1131
1131
|
const textNodes = Object.values(tree.byId).filter((node) => node.kind === "text");
|
|
1132
1132
|
if (textNodes.length === 0) return "";
|
|
1133
1133
|
return textNodes[textNodes.length - 1].accumulated.trim();
|
|
1134
1134
|
}
|
|
1135
|
+
function pickTeaserLine(fullText) {
|
|
1136
|
+
const lines = fullText.split("\n").map((line) => line.trim()).filter(Boolean);
|
|
1137
|
+
if (lines.length === 0) return "";
|
|
1138
|
+
const nonTableLine = lines.find((line) => !line.startsWith("|"));
|
|
1139
|
+
return nonTableLine ?? lines[0] ?? "";
|
|
1140
|
+
}
|
|
1135
1141
|
function buildStageDoneSummary(tree) {
|
|
1136
1142
|
if (tree.status !== "done" && tree.status !== "error") return null;
|
|
1137
1143
|
const toolUses = countToolUses(tree);
|
|
1138
1144
|
const duration = computeDurationSeconds(tree);
|
|
1139
1145
|
const durationSuffix = duration != null ? ` \xB7 ${duration}s` : "";
|
|
1140
1146
|
const label = toolUses > 0 ? `Done (${toolUses} tool use${toolUses === 1 ? "" : "s"}${durationSuffix})` : `Done (1 agent turn${durationSuffix})`;
|
|
1141
|
-
const fullText =
|
|
1147
|
+
const fullText = lastLoopTextContent(tree);
|
|
1142
1148
|
const lines = fullText.split("\n").map((line) => line.trim()).filter(Boolean);
|
|
1143
|
-
const teaser =
|
|
1149
|
+
const teaser = pickTeaserLine(fullText);
|
|
1144
1150
|
const extraLines = Math.max(0, lines.length - 1);
|
|
1145
1151
|
return { label, teaser, extraLines };
|
|
1146
1152
|
}
|
|
@@ -1214,7 +1220,7 @@ function evictInactiveLoopTrees(state, pinnedLoopSessionIds) {
|
|
|
1214
1220
|
if (container.status !== "completed" && container.status !== "failed") continue;
|
|
1215
1221
|
const summary = buildStageDoneSummary(tree);
|
|
1216
1222
|
if (summary) {
|
|
1217
|
-
nextSummaries[container.container_id] = summary;
|
|
1223
|
+
nextSummaries[container.container_id] = container.scope === "aggregate" ? { ...summary, fullMarkdown: lastLoopTextContent(tree) } : summary;
|
|
1218
1224
|
}
|
|
1219
1225
|
delete nextLoops[loopSessionId];
|
|
1220
1226
|
}
|
|
@@ -1257,7 +1263,7 @@ function evictCompletedLoopOverflow(state, maxHydratedCompletedLoops) {
|
|
|
1257
1263
|
if (container) {
|
|
1258
1264
|
const summary = buildStageDoneSummary(tree);
|
|
1259
1265
|
if (summary) {
|
|
1260
|
-
nextSummaries[container.container_id] = summary;
|
|
1266
|
+
nextSummaries[container.container_id] = container.scope === "aggregate" ? { ...summary, fullMarkdown: lastLoopTextContent(tree) } : summary;
|
|
1261
1267
|
}
|
|
1262
1268
|
}
|
|
1263
1269
|
delete nextLoops[id];
|
|
@@ -1455,6 +1461,17 @@ function sanitizeContainerTreeParentLinks(containersById) {
|
|
|
1455
1461
|
}
|
|
1456
1462
|
return next;
|
|
1457
1463
|
}
|
|
1464
|
+
function normalizeSnapshotContainerContentBlocks(containersById) {
|
|
1465
|
+
const next = {};
|
|
1466
|
+
for (const [containerId, node] of Object.entries(containersById)) {
|
|
1467
|
+
const loopSessionId = node.loopSessionId ?? null;
|
|
1468
|
+
next[containerId] = {
|
|
1469
|
+
...node,
|
|
1470
|
+
content_blocks: loopSessionId ? [] : node.content_blocks ?? []
|
|
1471
|
+
};
|
|
1472
|
+
}
|
|
1473
|
+
return next;
|
|
1474
|
+
}
|
|
1458
1475
|
function resolveContentScopeKey(data) {
|
|
1459
1476
|
for (const keyName of ["stage_key", "item_key", "branch_key", "aggregate_key", "debug_key"]) {
|
|
1460
1477
|
const value = readString(data, keyName);
|
|
@@ -1754,9 +1771,12 @@ function resolveContentTargetFromSnapshot(snapshot, workflowPath, scopeKey) {
|
|
|
1754
1771
|
function mergeRuntimeContainerNodes(prev, snapshot) {
|
|
1755
1772
|
const out = {};
|
|
1756
1773
|
for (const [containerId, node] of Object.entries(snapshot.containers)) {
|
|
1774
|
+
const loopSessionId = prev[containerId]?.loopSessionId ?? null;
|
|
1757
1775
|
out[containerId] = {
|
|
1758
1776
|
...node,
|
|
1759
|
-
loopSessionId
|
|
1777
|
+
loopSessionId,
|
|
1778
|
+
// D24:已绑定 loop 的容器不得保留 content_blocks 预览(过程层 SSOT 在 loop tree)。
|
|
1779
|
+
content_blocks: loopSessionId ? [] : node.content_blocks
|
|
1760
1780
|
};
|
|
1761
1781
|
}
|
|
1762
1782
|
return out;
|
|
@@ -2530,7 +2550,7 @@ function bindLoopSessionToContainerTree(tree, event, activeLoopSessionId) {
|
|
|
2530
2550
|
...nextTree,
|
|
2531
2551
|
containersById: {
|
|
2532
2552
|
...nextTree.containersById,
|
|
2533
|
-
[targetId]: { ...node, loopSessionId: sessionId }
|
|
2553
|
+
[targetId]: { ...node, loopSessionId: sessionId, content_blocks: [] }
|
|
2534
2554
|
}
|
|
2535
2555
|
};
|
|
2536
2556
|
}
|
|
@@ -2839,8 +2859,8 @@ function isAtOrBeforeProjectionCursor(projectionCursor, eventId) {
|
|
|
2839
2859
|
function hydrateWorkflowFromSnapshot(state, snapshot, options = {}) {
|
|
2840
2860
|
const authority = options.preserveAuthority ? state.authority : null;
|
|
2841
2861
|
const containerTree = structuredClone(snapshot.containerTree);
|
|
2842
|
-
containerTree.containersById =
|
|
2843
|
-
containerTree.containersById
|
|
2862
|
+
containerTree.containersById = normalizeSnapshotContainerContentBlocks(
|
|
2863
|
+
sanitizeContainerTreeParentLinks(containerTree.containersById)
|
|
2844
2864
|
);
|
|
2845
2865
|
return {
|
|
2846
2866
|
...createEmptyWorkflowSessionState(),
|
|
@@ -3263,6 +3283,7 @@ import { useMemo as useMemo7, useState as useState6 } from "react";
|
|
|
3263
3283
|
|
|
3264
3284
|
// src/view/workflow/WorkflowAggregateContainer.tsx
|
|
3265
3285
|
import { useCallback, useEffect as useEffect5, useMemo as useMemo2, useState, memo } from "react";
|
|
3286
|
+
import { useStore as useStore2 } from "zustand";
|
|
3266
3287
|
|
|
3267
3288
|
// src/view/workflow/WorkflowContainerLine.tsx
|
|
3268
3289
|
import { Fragment, jsx as jsx5, jsxs as jsxs2 } from "react/jsx-runtime";
|
|
@@ -3406,6 +3427,44 @@ function WorkflowMarkdownPreview({
|
|
|
3406
3427
|
return /* @__PURE__ */ jsx7("div", { className, "data-testid": testId, children: /* @__PURE__ */ jsx7(RichMarkdown, { content, deferDiagrams: true }) });
|
|
3407
3428
|
}
|
|
3408
3429
|
|
|
3430
|
+
// src/core/workflow/loopTreeUtils.ts
|
|
3431
|
+
function hasTimelineNodes(tree) {
|
|
3432
|
+
if (!tree) return false;
|
|
3433
|
+
return tree.rootChildren.length > 0 || Object.keys(tree.byId).length > 0;
|
|
3434
|
+
}
|
|
3435
|
+
|
|
3436
|
+
// src/view/workflow/workflowStageDoneBody.tsx
|
|
3437
|
+
import { jsx as jsx8 } from "react/jsx-runtime";
|
|
3438
|
+
function WorkflowStageDoneBody({
|
|
3439
|
+
loopTree,
|
|
3440
|
+
testId,
|
|
3441
|
+
virtualized,
|
|
3442
|
+
virtualizeThreshold,
|
|
3443
|
+
groupParallelTools,
|
|
3444
|
+
bodyClassName = "lax-workflow-stage-container__body"
|
|
3445
|
+
}) {
|
|
3446
|
+
if (loopTree && hasTimelineNodes(loopTree)) {
|
|
3447
|
+
return /* @__PURE__ */ jsx8("div", { className: bodyClassName, "data-testid": testId, children: /* @__PURE__ */ jsx8(
|
|
3448
|
+
AgentLoopView,
|
|
3449
|
+
{
|
|
3450
|
+
tree: loopTree,
|
|
3451
|
+
showTaskListFooter: false,
|
|
3452
|
+
virtualized,
|
|
3453
|
+
virtualizeThreshold,
|
|
3454
|
+
groupParallelTools
|
|
3455
|
+
}
|
|
3456
|
+
) });
|
|
3457
|
+
}
|
|
3458
|
+
return /* @__PURE__ */ jsx8(
|
|
3459
|
+
"div",
|
|
3460
|
+
{
|
|
3461
|
+
className: `${bodyClassName} lax-workflow-stage-container__empty-hint`,
|
|
3462
|
+
"data-testid": testId,
|
|
3463
|
+
children: /* @__PURE__ */ jsx8("span", { className: "lax-workflow-stage-container__empty-hint-text", children: "\uFF08\u6B64\u9636\u6BB5\u6682\u65E0 Agent \u65F6\u95F4\u7EBF\u5185\u5BB9\uFF09" })
|
|
3464
|
+
}
|
|
3465
|
+
);
|
|
3466
|
+
}
|
|
3467
|
+
|
|
3409
3468
|
// src/view/workflow/workflowStageListUtils.ts
|
|
3410
3469
|
var ACTIVE_CONTAINER_STATUSES = /* @__PURE__ */ new Set([
|
|
3411
3470
|
"running",
|
|
@@ -3648,12 +3707,23 @@ function workflowContainerViewPropsEqual(prev, next) {
|
|
|
3648
3707
|
}
|
|
3649
3708
|
|
|
3650
3709
|
// src/view/workflow/WorkflowAggregateContainer.tsx
|
|
3651
|
-
import { jsx as
|
|
3710
|
+
import { jsx as jsx9, jsxs as jsxs4 } from "react/jsx-runtime";
|
|
3652
3711
|
function mergeContentPreview(node) {
|
|
3653
3712
|
const blocks = node.content_blocks;
|
|
3654
3713
|
if (blocks.length === 0) return "";
|
|
3655
3714
|
return blocks.map((block) => block.preview?.trim() ?? "").filter(Boolean).join("\n\n");
|
|
3656
3715
|
}
|
|
3716
|
+
function resolveAggregateBodyMarkdown(node, loopTree, isDone, cachedFullMarkdown) {
|
|
3717
|
+
const staticPreview = mergeContentPreview(node);
|
|
3718
|
+
if (loopTree) {
|
|
3719
|
+
if (isDone) {
|
|
3720
|
+
return lastLoopTextContent(loopTree) || staticPreview;
|
|
3721
|
+
}
|
|
3722
|
+
return lastLoopTextContent(loopTree) || staticPreview;
|
|
3723
|
+
}
|
|
3724
|
+
if (isDone && cachedFullMarkdown) return cachedFullMarkdown;
|
|
3725
|
+
return staticPreview;
|
|
3726
|
+
}
|
|
3657
3727
|
function WorkflowAggregateContainerInner({
|
|
3658
3728
|
node,
|
|
3659
3729
|
loopTree,
|
|
@@ -3663,11 +3733,34 @@ function WorkflowAggregateContainerInner({
|
|
|
3663
3733
|
virtualizeThreshold,
|
|
3664
3734
|
groupParallelTools
|
|
3665
3735
|
}) {
|
|
3736
|
+
const { verbose } = useSessionViewOptions();
|
|
3737
|
+
const store = useWorkflowSessionStoreApi();
|
|
3738
|
+
const replayHandler = useWorkflowLoopReplayHandler();
|
|
3739
|
+
const cachedSummary = useStore2(
|
|
3740
|
+
store,
|
|
3741
|
+
(s) => s.state.stageDoneSummariesByContainerId[node.container_id]
|
|
3742
|
+
);
|
|
3743
|
+
const pinLoopSession = useStore2(store, (s) => s.pinLoopSession);
|
|
3666
3744
|
const isRunning = node.status === "running" || node.status === "retrying";
|
|
3667
3745
|
const isWaiting = node.status === "pending" || node.status === "blocked";
|
|
3668
3746
|
const isDone = node.status === "completed" || node.status === "failed";
|
|
3669
|
-
const
|
|
3670
|
-
const
|
|
3747
|
+
const usesScopedLoop = Boolean(node.loopSessionId);
|
|
3748
|
+
const bodyMarkdown = useMemo2(
|
|
3749
|
+
() => resolveAggregateBodyMarkdown(
|
|
3750
|
+
node,
|
|
3751
|
+
loopTree,
|
|
3752
|
+
isDone,
|
|
3753
|
+
cachedSummary?.fullMarkdown
|
|
3754
|
+
),
|
|
3755
|
+
[node, loopTree, isDone, cachedSummary?.fullMarkdown]
|
|
3756
|
+
);
|
|
3757
|
+
const waitingTeaser = isWaiting ? node.subtitle || bodyMarkdown || "" : "";
|
|
3758
|
+
const doneSummaryFromTree = useMemo2(
|
|
3759
|
+
() => loopTree && isDone ? buildStageDoneSummary(loopTree) : null,
|
|
3760
|
+
[loopTree, isDone]
|
|
3761
|
+
);
|
|
3762
|
+
const doneSummary = doneSummaryFromTree ?? (isDone ? cachedSummary : null);
|
|
3763
|
+
const expandHint = doneSummary ? formatTeaserExpandHint(doneSummary.extraLines, verbose) : null;
|
|
3671
3764
|
const testId = `lax-workflow-aggregate-${node.scope_key}`;
|
|
3672
3765
|
const uiStatus = mapAggregateUiStatus(node);
|
|
3673
3766
|
const statusLabel = buildAggregateStatusLabel(node, siblingItems);
|
|
@@ -3676,18 +3769,40 @@ function WorkflowAggregateContainerInner({
|
|
|
3676
3769
|
if (isRunning) setExpanded(true);
|
|
3677
3770
|
if (isDone) setExpanded(false);
|
|
3678
3771
|
}, [isRunning, isDone]);
|
|
3772
|
+
const requestLoopHydration = useCallback(() => {
|
|
3773
|
+
const loopSessionId = node.loopSessionId;
|
|
3774
|
+
if (!loopSessionId || loopTree) return;
|
|
3775
|
+
pinLoopSession(loopSessionId);
|
|
3776
|
+
void replayHandler?.(loopSessionId);
|
|
3777
|
+
}, [node.loopSessionId, loopTree, pinLoopSession, replayHandler]);
|
|
3679
3778
|
const toggleExpanded = useCallback(() => {
|
|
3680
|
-
setExpanded((prev) =>
|
|
3681
|
-
|
|
3682
|
-
|
|
3683
|
-
|
|
3779
|
+
setExpanded((prev) => {
|
|
3780
|
+
const next = !prev;
|
|
3781
|
+
if (next && isDone && node.loopSessionId && !loopTree) {
|
|
3782
|
+
requestLoopHydration();
|
|
3783
|
+
}
|
|
3784
|
+
return next;
|
|
3785
|
+
});
|
|
3786
|
+
}, [isDone, node.loopSessionId, loopTree, requestLoopHydration]);
|
|
3787
|
+
useEffect5(() => {
|
|
3788
|
+
const onKeyDown = (event) => {
|
|
3789
|
+
if (!(event.ctrlKey || event.metaKey) || event.key.toLowerCase() !== "o") return;
|
|
3790
|
+
setExpanded(true);
|
|
3791
|
+
requestLoopHydration();
|
|
3792
|
+
};
|
|
3793
|
+
window.addEventListener("keydown", onKeyDown);
|
|
3794
|
+
return () => window.removeEventListener("keydown", onKeyDown);
|
|
3795
|
+
}, [requestLoopHydration]);
|
|
3796
|
+
const shellToggle = isRunning ? toggleExpanded : isDone ? toggleExpanded : void 0;
|
|
3797
|
+
const markdownPreview = bodyMarkdown ? /* @__PURE__ */ jsx9(
|
|
3684
3798
|
WorkflowMarkdownPreview,
|
|
3685
3799
|
{
|
|
3686
|
-
content:
|
|
3800
|
+
content: bodyMarkdown,
|
|
3687
3801
|
testId: `${testId}-markdown`,
|
|
3688
3802
|
className: "lax-workflow-aggregate__markdown lax-workflow-markdown-preview"
|
|
3689
3803
|
}
|
|
3690
3804
|
) : null;
|
|
3805
|
+
const canExpandDone = isDone && (Boolean(loopTree) || Boolean(bodyMarkdown) || Boolean(node.loopSessionId));
|
|
3691
3806
|
return /* @__PURE__ */ jsxs4(
|
|
3692
3807
|
"div",
|
|
3693
3808
|
{
|
|
@@ -3696,7 +3811,7 @@ function WorkflowAggregateContainerInner({
|
|
|
3696
3811
|
"data-container-scope": "aggregate",
|
|
3697
3812
|
style: { "--lax-workflow-depth": depth },
|
|
3698
3813
|
children: [
|
|
3699
|
-
/* @__PURE__ */
|
|
3814
|
+
/* @__PURE__ */ jsx9(
|
|
3700
3815
|
WorkflowContainerLine,
|
|
3701
3816
|
{
|
|
3702
3817
|
title: node.title,
|
|
@@ -3705,15 +3820,15 @@ function WorkflowAggregateContainerInner({
|
|
|
3705
3820
|
meta: buildAggregateLineMeta(node),
|
|
3706
3821
|
statusLabel,
|
|
3707
3822
|
onToggle: shellToggle,
|
|
3708
|
-
interactive: isRunning,
|
|
3823
|
+
interactive: isRunning || isDone,
|
|
3709
3824
|
expanded,
|
|
3710
3825
|
titleTestId: `${testId}-title`,
|
|
3711
3826
|
descriptionTestId: `${testId}-desc`
|
|
3712
3827
|
}
|
|
3713
3828
|
),
|
|
3714
3829
|
isWaiting && waitingTeaser ? /* @__PURE__ */ jsxs4("div", { className: "lax-workflow-aggregate__waiting-teaser", "data-testid": `${testId}-waiting`, children: [
|
|
3715
|
-
/* @__PURE__ */
|
|
3716
|
-
/* @__PURE__ */
|
|
3830
|
+
/* @__PURE__ */ jsx9("span", { className: "lax-workflow-aggregate__waiting-prefix", children: "\u23BF " }),
|
|
3831
|
+
/* @__PURE__ */ jsx9(
|
|
3717
3832
|
WorkflowMarkdownPreview,
|
|
3718
3833
|
{
|
|
3719
3834
|
content: waitingTeaser,
|
|
@@ -3721,7 +3836,7 @@ function WorkflowAggregateContainerInner({
|
|
|
3721
3836
|
}
|
|
3722
3837
|
)
|
|
3723
3838
|
] }) : null,
|
|
3724
|
-
expanded && isRunning && loopTree ? /* @__PURE__ */
|
|
3839
|
+
expanded && isRunning && loopTree ? /* @__PURE__ */ jsx9("div", { className: "lax-workflow-stage-container__body", "data-testid": `${testId}-body`, children: /* @__PURE__ */ jsx9(
|
|
3725
3840
|
AgentLoopView,
|
|
3726
3841
|
{
|
|
3727
3842
|
tree: loopTree,
|
|
@@ -3731,7 +3846,7 @@ function WorkflowAggregateContainerInner({
|
|
|
3731
3846
|
groupParallelTools
|
|
3732
3847
|
}
|
|
3733
3848
|
) }) : null,
|
|
3734
|
-
expanded && isRunning && !loopTree &&
|
|
3849
|
+
expanded && isRunning && !loopTree && bodyMarkdown ? /* @__PURE__ */ jsx9(
|
|
3735
3850
|
"div",
|
|
3736
3851
|
{
|
|
3737
3852
|
className: "lax-workflow-stage-container__body lax-workflow-stage-container__content-preview",
|
|
@@ -3740,36 +3855,44 @@ function WorkflowAggregateContainerInner({
|
|
|
3740
3855
|
}
|
|
3741
3856
|
) : null,
|
|
3742
3857
|
isDone && !expanded ? /* @__PURE__ */ jsxs4("div", { className: "lax-workflow-aggregate__done", "data-testid": `${testId}-done`, children: [
|
|
3743
|
-
/* @__PURE__ */
|
|
3858
|
+
canExpandDone ? /* @__PURE__ */ jsx9(
|
|
3744
3859
|
WorkflowExpandTrigger,
|
|
3745
3860
|
{
|
|
3746
3861
|
summary: `${node.title} \xB7 done`,
|
|
3747
|
-
onToggle:
|
|
3862
|
+
onToggle: toggleExpanded,
|
|
3748
3863
|
expanded: false,
|
|
3749
|
-
expandHint:
|
|
3864
|
+
expandHint: bodyMarkdown || expandHint ? "(click to expand)" : void 0,
|
|
3750
3865
|
testId: `${testId}-done-trigger`
|
|
3751
3866
|
}
|
|
3752
|
-
),
|
|
3753
|
-
markdownPreview ? /* @__PURE__ */
|
|
3867
|
+
) : null,
|
|
3868
|
+
markdownPreview ? /* @__PURE__ */ jsx9("div", { className: "lax-workflow-aggregate__done-preview", "data-testid": `${testId}-teaser`, children: markdownPreview }) : null,
|
|
3869
|
+
!bodyMarkdown && expandHint ? /* @__PURE__ */ jsx9("span", { className: "lax-workflow-expand-trigger__hint", children: expandHint }) : null
|
|
3754
3870
|
] }) : null,
|
|
3755
|
-
isDone && expanded
|
|
3756
|
-
|
|
3871
|
+
isDone && expanded ? loopTree ? /* @__PURE__ */ jsx9(
|
|
3872
|
+
WorkflowStageDoneBody,
|
|
3757
3873
|
{
|
|
3758
|
-
|
|
3759
|
-
|
|
3874
|
+
node,
|
|
3875
|
+
loopTree,
|
|
3876
|
+
testId: `${testId}-body`,
|
|
3760
3877
|
virtualized,
|
|
3761
3878
|
virtualizeThreshold,
|
|
3762
3879
|
groupParallelTools
|
|
3763
3880
|
}
|
|
3764
|
-
)
|
|
3765
|
-
isDone && expanded && !loopTree && contentPreview ? /* @__PURE__ */ jsx8(
|
|
3881
|
+
) : bodyMarkdown ? /* @__PURE__ */ jsx9(
|
|
3766
3882
|
"div",
|
|
3767
3883
|
{
|
|
3768
3884
|
className: "lax-workflow-stage-container__body lax-workflow-stage-container__content-preview",
|
|
3769
3885
|
"data-testid": `${testId}-body`,
|
|
3770
3886
|
children: markdownPreview
|
|
3771
3887
|
}
|
|
3772
|
-
) :
|
|
3888
|
+
) : usesScopedLoop ? /* @__PURE__ */ jsx9(
|
|
3889
|
+
"div",
|
|
3890
|
+
{
|
|
3891
|
+
className: "lax-workflow-stage-container__body lax-workflow-loop-replay-pending",
|
|
3892
|
+
"data-testid": `${testId}-body`,
|
|
3893
|
+
children: /* @__PURE__ */ jsx9("p", { className: "lax-workflow-loop-replay-pending__hint", children: replayHandler ? "Loading loop details\u2026" : "Loop details evicted from memory." })
|
|
3894
|
+
}
|
|
3895
|
+
) : null : null
|
|
3773
3896
|
]
|
|
3774
3897
|
}
|
|
3775
3898
|
);
|
|
@@ -3886,47 +4009,7 @@ function formatParallelGroupSummary(metrics) {
|
|
|
3886
4009
|
|
|
3887
4010
|
// src/view/workflow/WorkflowStageContainer.tsx
|
|
3888
4011
|
import { useCallback as useCallback2, useEffect as useEffect6, useMemo as useMemo3, useState as useState2, memo as memo2 } from "react";
|
|
3889
|
-
import { useStore as
|
|
3890
|
-
|
|
3891
|
-
// src/core/workflow/loopTreeUtils.ts
|
|
3892
|
-
function hasTimelineNodes(tree) {
|
|
3893
|
-
if (!tree) return false;
|
|
3894
|
-
return tree.rootChildren.length > 0 || Object.keys(tree.byId).length > 0;
|
|
3895
|
-
}
|
|
3896
|
-
|
|
3897
|
-
// src/view/workflow/workflowStageDoneBody.tsx
|
|
3898
|
-
import { jsx as jsx9 } from "react/jsx-runtime";
|
|
3899
|
-
function WorkflowStageDoneBody({
|
|
3900
|
-
loopTree,
|
|
3901
|
-
testId,
|
|
3902
|
-
virtualized,
|
|
3903
|
-
virtualizeThreshold,
|
|
3904
|
-
groupParallelTools,
|
|
3905
|
-
bodyClassName = "lax-workflow-stage-container__body"
|
|
3906
|
-
}) {
|
|
3907
|
-
if (loopTree && hasTimelineNodes(loopTree)) {
|
|
3908
|
-
return /* @__PURE__ */ jsx9("div", { className: bodyClassName, "data-testid": testId, children: /* @__PURE__ */ jsx9(
|
|
3909
|
-
AgentLoopView,
|
|
3910
|
-
{
|
|
3911
|
-
tree: loopTree,
|
|
3912
|
-
showTaskListFooter: false,
|
|
3913
|
-
virtualized,
|
|
3914
|
-
virtualizeThreshold,
|
|
3915
|
-
groupParallelTools
|
|
3916
|
-
}
|
|
3917
|
-
) });
|
|
3918
|
-
}
|
|
3919
|
-
return /* @__PURE__ */ jsx9(
|
|
3920
|
-
"div",
|
|
3921
|
-
{
|
|
3922
|
-
className: `${bodyClassName} lax-workflow-stage-container__empty-hint`,
|
|
3923
|
-
"data-testid": testId,
|
|
3924
|
-
children: /* @__PURE__ */ jsx9("span", { className: "lax-workflow-stage-container__empty-hint-text", children: "\uFF08\u6B64\u9636\u6BB5\u6682\u65E0 Agent \u65F6\u95F4\u7EBF\u5185\u5BB9\uFF09" })
|
|
3925
|
-
}
|
|
3926
|
-
);
|
|
3927
|
-
}
|
|
3928
|
-
|
|
3929
|
-
// src/view/workflow/WorkflowStageContainer.tsx
|
|
4012
|
+
import { useStore as useStore3 } from "zustand";
|
|
3930
4013
|
import { jsx as jsx10, jsxs as jsxs5 } from "react/jsx-runtime";
|
|
3931
4014
|
function containerTestId(node) {
|
|
3932
4015
|
if (node.scope === "item") return `lax-workflow-parallel-${node.scope_key}`;
|
|
@@ -3950,13 +4033,13 @@ function WorkflowStageContainerInner({
|
|
|
3950
4033
|
const { verbose } = useSessionViewOptions();
|
|
3951
4034
|
const store = useWorkflowSessionStoreApi();
|
|
3952
4035
|
const replayHandler = useWorkflowLoopReplayHandler();
|
|
3953
|
-
const activeLoopSessionId =
|
|
3954
|
-
const activeContainerIds =
|
|
3955
|
-
const cachedSummary =
|
|
4036
|
+
const activeLoopSessionId = useStore3(store, (s) => s.state.activeLoopSessionId);
|
|
4037
|
+
const activeContainerIds = useStore3(store, (s) => s.state.containerTree.activeContainerIds);
|
|
4038
|
+
const cachedSummary = useStore3(
|
|
3956
4039
|
store,
|
|
3957
4040
|
(s) => s.state.stageDoneSummariesByContainerId[node.container_id]
|
|
3958
4041
|
);
|
|
3959
|
-
const pinLoopSession =
|
|
4042
|
+
const pinLoopSession = useStore3(store, (s) => s.pinLoopSession);
|
|
3960
4043
|
const isRunning = node.status === "running" || node.status === "retrying";
|
|
3961
4044
|
const isDone = node.status === "completed" || node.status === "failed";
|
|
3962
4045
|
const isSkipped = node.status === "skipped";
|
|
@@ -4050,12 +4133,21 @@ function WorkflowStageContainerInner({
|
|
|
4050
4133
|
}
|
|
4051
4134
|
),
|
|
4052
4135
|
effectivelyDone && !expanded && (teaserText || expandHint) ? /* @__PURE__ */ jsxs5("div", { className: "lax-workflow-stage-container__done-teaser", children: [
|
|
4053
|
-
teaserText ? /* @__PURE__ */
|
|
4054
|
-
"
|
|
4136
|
+
teaserText ? /* @__PURE__ */ jsxs5(
|
|
4137
|
+
"div",
|
|
4055
4138
|
{
|
|
4056
4139
|
className: "lax-workflow-stage-container__done-teaser-line",
|
|
4057
4140
|
"data-testid": `${testId}-teaser`,
|
|
4058
|
-
children:
|
|
4141
|
+
children: [
|
|
4142
|
+
/* @__PURE__ */ jsx10("span", { className: "lax-workflow-stage-container__done-teaser-prefix", children: "\u23BF" }),
|
|
4143
|
+
/* @__PURE__ */ jsx10(
|
|
4144
|
+
WorkflowMarkdownPreview,
|
|
4145
|
+
{
|
|
4146
|
+
content: teaserText,
|
|
4147
|
+
className: "lax-workflow-stage-container__done-teaser-markdown"
|
|
4148
|
+
}
|
|
4149
|
+
)
|
|
4150
|
+
]
|
|
4059
4151
|
}
|
|
4060
4152
|
) : null,
|
|
4061
4153
|
expandHint ? /* @__PURE__ */ jsx10("span", { className: "lax-workflow-expand-trigger__hint", children: expandHint }) : null
|
|
@@ -4066,10 +4158,10 @@ function WorkflowStageContainerInner({
|
|
|
4066
4158
|
className: "lax-workflow-stage-container__body lax-workflow-stage-container__content-preview",
|
|
4067
4159
|
"data-testid": bodyTestId(node),
|
|
4068
4160
|
children: node.content_blocks.map((block, index) => /* @__PURE__ */ jsx10(
|
|
4069
|
-
|
|
4161
|
+
WorkflowMarkdownPreview,
|
|
4070
4162
|
{
|
|
4071
|
-
|
|
4072
|
-
|
|
4163
|
+
content: block.preview,
|
|
4164
|
+
className: "lax-workflow-stage-container__teaser"
|
|
4073
4165
|
},
|
|
4074
4166
|
`${block.kind}-${index}`
|
|
4075
4167
|
))
|
|
@@ -4109,7 +4201,14 @@ function WorkflowStageContainerInner({
|
|
|
4109
4201
|
className: "lax-workflow-stage-container__body lax-workflow-loop-replay-pending",
|
|
4110
4202
|
"data-testid": bodyTestId(node),
|
|
4111
4203
|
children: [
|
|
4112
|
-
teaserText ? /* @__PURE__ */ jsx10(
|
|
4204
|
+
teaserText ? /* @__PURE__ */ jsx10(
|
|
4205
|
+
WorkflowMarkdownPreview,
|
|
4206
|
+
{
|
|
4207
|
+
content: teaserText,
|
|
4208
|
+
className: "lax-workflow-stage-container__teaser",
|
|
4209
|
+
testId: `${testId}-replay-teaser`
|
|
4210
|
+
}
|
|
4211
|
+
) : null,
|
|
4113
4212
|
/* @__PURE__ */ jsx10("p", { className: "lax-workflow-loop-replay-pending__hint", children: replayHandler ? "Loading loop details\u2026" : "Loop details evicted from memory." })
|
|
4114
4213
|
]
|
|
4115
4214
|
}
|
|
@@ -4755,11 +4854,11 @@ function WorkflowChrome({
|
|
|
4755
4854
|
}
|
|
4756
4855
|
|
|
4757
4856
|
// src/view/workflow/WorkflowGlobalSpinner.tsx
|
|
4758
|
-
import { useStore as
|
|
4857
|
+
import { useStore as useStore4 } from "zustand";
|
|
4759
4858
|
import { jsx as jsx16, jsxs as jsxs11 } from "react/jsx-runtime";
|
|
4760
4859
|
function WorkflowGlobalSpinner() {
|
|
4761
4860
|
const store = useWorkflowSessionStoreApi();
|
|
4762
|
-
const show =
|
|
4861
|
+
const show = useStore4(store, (s) => shouldShowGlobalSpinner(s.state));
|
|
4763
4862
|
if (!show) return null;
|
|
4764
4863
|
return /* @__PURE__ */ jsx16(
|
|
4765
4864
|
"div",
|
|
@@ -4869,7 +4968,7 @@ function WorkflowSessionBanners({ state }) {
|
|
|
4869
4968
|
|
|
4870
4969
|
// src/view/workflow/WorkflowTaskListFooter.tsx
|
|
4871
4970
|
import { useMemo as useMemo8, useState as useState7 } from "react";
|
|
4872
|
-
import { useStore as
|
|
4971
|
+
import { useStore as useStore5 } from "zustand";
|
|
4873
4972
|
|
|
4874
4973
|
// src/view/workflow/workflowTaskListMerge.ts
|
|
4875
4974
|
var STATUS_ORDER = {
|
|
@@ -4949,7 +5048,7 @@ function MessageResponse({ children }) {
|
|
|
4949
5048
|
}
|
|
4950
5049
|
function WorkflowTaskListFooter() {
|
|
4951
5050
|
const store = useWorkflowSessionStoreApi();
|
|
4952
|
-
const state =
|
|
5051
|
+
const state = useStore5(store, (s) => s.state);
|
|
4953
5052
|
const [expanded, setExpanded] = useState7(false);
|
|
4954
5053
|
const footerState = useMemo8(() => deriveWorkflowTaskFooterState(state), [state]);
|
|
4955
5054
|
const visible = shouldShowWorkflowTaskListFooter(state);
|
|
@@ -4989,7 +5088,7 @@ function WorkflowTaskListFooter() {
|
|
|
4989
5088
|
}
|
|
4990
5089
|
|
|
4991
5090
|
// src/view/workflow/WorkflowSession.tsx
|
|
4992
|
-
import { useStore as
|
|
5091
|
+
import { useStore as useStore6 } from "zustand";
|
|
4993
5092
|
import { jsx as jsx19, jsxs as jsxs14 } from "react/jsx-runtime";
|
|
4994
5093
|
function WorkflowSession({
|
|
4995
5094
|
source,
|
|
@@ -5031,8 +5130,8 @@ function WorkflowSession({
|
|
|
5031
5130
|
}
|
|
5032
5131
|
const store = storeRef.current;
|
|
5033
5132
|
useWorkflowAuthorityBinding(store, authoritySource, { onAuthorityTerminal });
|
|
5034
|
-
const streamEnded =
|
|
5035
|
-
const authorityStatus =
|
|
5133
|
+
const streamEnded = useStore6(store, (s) => s.state.display.streamEnded);
|
|
5134
|
+
const authorityStatus = useStore6(store, (s) => s.state.authority?.status);
|
|
5036
5135
|
useWorkflowAwaitingAuthorityTimers(store, streamEnded, authorityStatus);
|
|
5037
5136
|
useEffect10(() => {
|
|
5038
5137
|
if (snapshotBootstrap) {
|
|
@@ -5081,7 +5180,7 @@ function WorkflowSession({
|
|
|
5081
5180
|
workspaceRoot
|
|
5082
5181
|
]
|
|
5083
5182
|
);
|
|
5084
|
-
const sessionState =
|
|
5183
|
+
const sessionState = useStore6(store, (s) => s.state);
|
|
5085
5184
|
const containerTree = sessionState.containerTree;
|
|
5086
5185
|
const loopTreesBySessionId = sessionState.loopTreesBySessionId;
|
|
5087
5186
|
const onErrorRef = useRef4(onError);
|