@tutti-os/agent-gui 0.0.68 → 0.0.70

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.
Files changed (67) hide show
  1. package/README.md +4 -5
  2. package/dist/agent-conversation/index.d.ts +2 -2
  3. package/dist/agent-conversation/index.js +6 -6
  4. package/dist/agent-message-center/index.js +8 -8
  5. package/dist/{agentGuiNodeTypes-BTHu_g4m.d.ts → agentGuiNodeTypes-CmLUy5Jt.d.ts} +8 -6
  6. package/dist/app/renderer/agentactivity.css +209 -4
  7. package/dist/app/renderer/assets/icons/agents/opencode-flat-filled.svg +4 -0
  8. package/dist/{chunk-3QPN2Y7R.js → chunk-DGNKXT3Q.js} +23 -129
  9. package/dist/chunk-DGNKXT3Q.js.map +1 -0
  10. package/dist/{chunk-GXHZNIWT.js → chunk-DXENDZEF.js} +2 -2
  11. package/dist/{chunk-GOEL3BO7.js → chunk-FTSEVC6O.js} +2 -2
  12. package/dist/{chunk-J335PQ5H.js → chunk-ISQCYEUJ.js} +12 -27
  13. package/dist/chunk-ISQCYEUJ.js.map +1 -0
  14. package/dist/{chunk-C2M2ELXF.js → chunk-IZX2YQXY.js} +3 -3
  15. package/dist/{chunk-ZZBLWZJR.js → chunk-KS35VKHM.js} +1 -2
  16. package/dist/chunk-KS35VKHM.js.map +1 -0
  17. package/dist/{chunk-LQRD4X6R.js → chunk-KTIHLBCN.js} +2 -2
  18. package/dist/{chunk-A2KZVRUO.js → chunk-MVPSFOJZ.js} +2 -2
  19. package/dist/{chunk-YE5JSME7.js → chunk-N37A62BK.js} +17 -1
  20. package/dist/chunk-N37A62BK.js.map +1 -0
  21. package/dist/{chunk-VRV6GBF5.js → chunk-NROZAN34.js} +8 -1
  22. package/dist/chunk-NROZAN34.js.map +1 -0
  23. package/dist/{chunk-QGKK6FHC.js → chunk-QDWV5VTD.js} +5 -5
  24. package/dist/{chunk-DYX6466P.js → chunk-QJ42HQ24.js} +4 -4
  25. package/dist/{chunk-AIR6A4NP.js → chunk-SC3PS7AT.js} +2 -2
  26. package/dist/{chunk-D22A3KGQ.js → chunk-SG6A35BU.js} +2 -2
  27. package/dist/{chunk-KJLSZETD.js → chunk-WWY6MYMU.js} +3 -3
  28. package/dist/{chunk-TB7PKP6F.js → chunk-Y3C5EHSW.js} +61 -17
  29. package/dist/chunk-Y3C5EHSW.js.map +1 -0
  30. package/dist/context-mention-palette/index.js +7 -7
  31. package/dist/i18n/index.d.ts +22 -128
  32. package/dist/i18n/index.js +2 -2
  33. package/dist/index.d.ts +114 -109
  34. package/dist/index.js +599 -213
  35. package/dist/index.js.map +1 -1
  36. package/dist/opencode-flat-filled-CYAJPX45.svg +4 -0
  37. package/dist/queued-prompt-runtime.d.ts +2 -2
  38. package/dist/{types-BwDrG654.d.ts → types-DZ79b8Zn.d.ts} +6 -1
  39. package/dist/workbench/contribution.d.ts +9 -1
  40. package/dist/workbench/contribution.js +4 -4
  41. package/dist/workbench/index.d.ts +5 -2
  42. package/dist/workbench/index.js +7 -7
  43. package/dist/workbench/launch.d.ts +1 -1
  44. package/dist/workbench/providerCatalog.d.ts +1 -1
  45. package/dist/workbench/sessionTitle.d.ts +1 -1
  46. package/dist/workbench/sessionTitle.js +3 -3
  47. package/dist/workbench/state.d.ts +1 -1
  48. package/dist/workbench/state.js +2 -2
  49. package/dist/workbench/types.d.ts +1 -1
  50. package/dist/workspace-agent-generated-files.js +3 -3
  51. package/package.json +12 -12
  52. package/dist/chunk-3QPN2Y7R.js.map +0 -1
  53. package/dist/chunk-J335PQ5H.js.map +0 -1
  54. package/dist/chunk-TB7PKP6F.js.map +0 -1
  55. package/dist/chunk-VRV6GBF5.js.map +0 -1
  56. package/dist/chunk-YE5JSME7.js.map +0 -1
  57. package/dist/chunk-ZZBLWZJR.js.map +0 -1
  58. /package/dist/{chunk-GXHZNIWT.js.map → chunk-DXENDZEF.js.map} +0 -0
  59. /package/dist/{chunk-GOEL3BO7.js.map → chunk-FTSEVC6O.js.map} +0 -0
  60. /package/dist/{chunk-C2M2ELXF.js.map → chunk-IZX2YQXY.js.map} +0 -0
  61. /package/dist/{chunk-LQRD4X6R.js.map → chunk-KTIHLBCN.js.map} +0 -0
  62. /package/dist/{chunk-A2KZVRUO.js.map → chunk-MVPSFOJZ.js.map} +0 -0
  63. /package/dist/{chunk-QGKK6FHC.js.map → chunk-QDWV5VTD.js.map} +0 -0
  64. /package/dist/{chunk-DYX6466P.js.map → chunk-QJ42HQ24.js.map} +0 -0
  65. /package/dist/{chunk-AIR6A4NP.js.map → chunk-SC3PS7AT.js.map} +0 -0
  66. /package/dist/{chunk-D22A3KGQ.js.map → chunk-SG6A35BU.js.map} +0 -0
  67. /package/dist/{chunk-KJLSZETD.js.map → chunk-WWY6MYMU.js.map} +0 -0
package/dist/index.js CHANGED
@@ -10,7 +10,7 @@ import {
10
10
  resolveAgentGuiSessionProviderFlatIconUrl,
11
11
  resolveNextAgentGUIConversationRailWidthPx,
12
12
  shouldAutoCollapseAgentGUIConversationRail
13
- } from "./chunk-VRV6GBF5.js";
13
+ } from "./chunk-NROZAN34.js";
14
14
  import {
15
15
  agentGUIDefaultTargetProviders,
16
16
  agentGUIProviderTargetRefsEqual,
@@ -22,11 +22,11 @@ import {
22
22
  localAgentGUIProviderTargetId,
23
23
  normalizeAgentGUIProviderTargets,
24
24
  resolveAgentGUIProviderTarget
25
- } from "./chunk-YE5JSME7.js";
25
+ } from "./chunk-N37A62BK.js";
26
26
  import {
27
27
  AgentInteractivePromptSurface,
28
28
  approvalOptionDisplayLabel
29
- } from "./chunk-DYX6466P.js";
29
+ } from "./chunk-QJ42HQ24.js";
30
30
  import {
31
31
  PLAN_IMPLEMENTATION_ACTION_FEEDBACK,
32
32
  PLAN_IMPLEMENTATION_ACTION_IMPLEMENT,
@@ -45,7 +45,7 @@ import {
45
45
  resolveAgentGUIExplicitConversationTitle,
46
46
  resolveAgentGUIProviderDisplayLabel,
47
47
  resolveAgentGUIProviderIdentity
48
- } from "./chunk-D22A3KGQ.js";
48
+ } from "./chunk-SG6A35BU.js";
49
49
  import {
50
50
  AgentConversationFlow,
51
51
  Button,
@@ -66,14 +66,14 @@ import {
66
66
  skillTriggerForPrefix,
67
67
  toLocalShortDateTime,
68
68
  useProjectedAgentConversation
69
- } from "./chunk-J335PQ5H.js";
69
+ } from "./chunk-ISQCYEUJ.js";
70
70
  import {
71
71
  AgentMessageMarkdown,
72
72
  AgentTargetPresentationProvider,
73
73
  ZoomableImage,
74
74
  cn,
75
75
  resolveWorkspaceLinkAction
76
- } from "./chunk-KJLSZETD.js";
76
+ } from "./chunk-WWY6MYMU.js";
77
77
  import {
78
78
  openAgentEnvPanel
79
79
  } from "./chunk-PSLAWU25.js";
@@ -84,12 +84,12 @@ import {
84
84
  DEFAULT_AGENT_MENTION_FILTER,
85
85
  agentMentionItemKey,
86
86
  preloadAgentMentionBrowse
87
- } from "./chunk-QGKK6FHC.js";
87
+ } from "./chunk-QDWV5VTD.js";
88
88
  import {
89
89
  buildWorkspaceAgentActivityListViewModel,
90
90
  isWorkspaceAgentUntitledTask
91
- } from "./chunk-GXHZNIWT.js";
92
- import "./chunk-A2KZVRUO.js";
91
+ } from "./chunk-DXENDZEF.js";
92
+ import "./chunk-MVPSFOJZ.js";
93
93
  import {
94
94
  resolveWorkspaceAgentSessionSortTimeUnixMs
95
95
  } from "./chunk-IBIMGLCD.js";
@@ -100,7 +100,7 @@ import {
100
100
  mentionItemToAttrs,
101
101
  normalizeAgentSessionMentionTitle,
102
102
  parseMentionItemFromHref
103
- } from "./chunk-C2M2ELXF.js";
103
+ } from "./chunk-IZX2YQXY.js";
104
104
  import "./chunk-Y35GDLP2.js";
105
105
  import "./chunk-LUGELG5V.js";
106
106
  import {
@@ -124,7 +124,7 @@ import {
124
124
  useAgentHostApi,
125
125
  useOptionalAgentActivityRuntime,
126
126
  useOptionalAgentHostApi
127
- } from "./chunk-ZZBLWZJR.js";
127
+ } from "./chunk-KS35VKHM.js";
128
128
  import {
129
129
  WORKSPACE_AGENT_ACTIVITY_RUNTIME_SESSION_ORIGIN,
130
130
  createWorkspaceAgentActivityUserMessageIdFromClientSubmitId,
@@ -139,14 +139,14 @@ import {
139
139
  agentGuiI18nResources,
140
140
  translate,
141
141
  useTranslation
142
- } from "./chunk-AIR6A4NP.js";
142
+ } from "./chunk-SC3PS7AT.js";
143
143
  import "./chunk-PJP5BUU6.js";
144
144
  import {
145
145
  agentColorfulUrl,
146
146
  cursorColorfulUrl,
147
147
  normalizeManagedAgentProvider
148
148
  } from "./chunk-4I2VCAMW.js";
149
- import "./chunk-3QPN2Y7R.js";
149
+ import "./chunk-DGNKXT3Q.js";
150
150
  import {
151
151
  AGENT_CONTEXT_MENTION_PROVIDER_IDS
152
152
  } from "./chunk-JM24HADP.js";
@@ -3121,7 +3121,7 @@ function emptyAgentComposerDraft() {
3121
3121
  return { prompt: "", images: [], files: [] };
3122
3122
  }
3123
3123
  function agentComposerDraftHasContent(draft) {
3124
- return draft.prompt.trim() !== "" || draft.images.length > 0 || (draft.files?.length ?? 0) > 0;
3124
+ return draft.prompt.trim() !== "" || draft.images.length > 0 || (draft.files?.length ?? 0) > 0 || (draft.largeTexts?.some((item) => item.text.trim() !== "") ?? false);
3125
3125
  }
3126
3126
  function normalizeAgentPromptContentBlocks(content) {
3127
3127
  const result = [];
@@ -3229,9 +3229,35 @@ function agentComposerDraftToPromptContent(input) {
3229
3229
  ...file.sizeBytes ? { sizeBytes: file.sizeBytes } : {},
3230
3230
  name: file.name,
3231
3231
  kind: "file"
3232
- }))
3232
+ })),
3233
+ ...largeTextPromptContent(input.draft.largeTexts ?? [])
3233
3234
  ]);
3234
3235
  }
3236
+ function agentComposerDraftSubmittedText(draft) {
3237
+ return agentPromptContentDisplayText(
3238
+ normalizeAgentPromptContentBlocks([
3239
+ ...textPromptContent(draft.prompt),
3240
+ ...largeTextPromptContent(draft.largeTexts ?? [])
3241
+ ])
3242
+ );
3243
+ }
3244
+ function agentComposerDraftDisplayPrompt(draft) {
3245
+ const largeTexts = draft.largeTexts?.filter(
3246
+ (item) => item.text.trim() !== ""
3247
+ );
3248
+ if (!largeTexts?.length) {
3249
+ return void 0;
3250
+ }
3251
+ const parts = [draft.prompt.trim()].filter(Boolean);
3252
+ parts.push(
3253
+ ...largeTexts.map((item, index) => {
3254
+ const name = item.name.trim() || `pasted-text-${index + 1}.txt`;
3255
+ const sizeLabel = typeof item.sizeBytes === "number" && Number.isFinite(item.sizeBytes) ? ` \xB7 ${formatAgentComposerDraftBytes(item.sizeBytes)}` : "";
3256
+ return `[${name}${sizeLabel}]`;
3257
+ })
3258
+ );
3259
+ return parts.join("\n");
3260
+ }
3235
3261
  function agentPromptFileBlocks(content) {
3236
3262
  return normalizeAgentPromptContentBlocks(content).filter(
3237
3263
  (block) => block.type === "file" && (typeof block.path === "string" || typeof block.hostPath === "string")
@@ -3269,6 +3295,30 @@ function textPromptContent(prompt) {
3269
3295
  const text = prompt.trim();
3270
3296
  return text ? [{ type: "text", text }] : [];
3271
3297
  }
3298
+ function largeTextPromptContent(largeTexts) {
3299
+ return largeTexts.filter((item) => item.text.trim() !== "").map((item, index) => {
3300
+ const name = item.name.trim() || `pasted-text-${index + 1}.txt`;
3301
+ return {
3302
+ type: "text",
3303
+ text: `${translate("agentHost.agentGui.pastedTextPromptAttachment", {
3304
+ name
3305
+ })}
3306
+
3307
+ ${item.text}`
3308
+ };
3309
+ });
3310
+ }
3311
+ function formatAgentComposerDraftBytes(sizeBytes) {
3312
+ if (sizeBytes < 1024) {
3313
+ return `${sizeBytes} B`;
3314
+ }
3315
+ const kib = sizeBytes / 1024;
3316
+ if (kib < 1024) {
3317
+ return `${kib.toFixed(kib >= 10 ? 0 : 1)} KB`;
3318
+ }
3319
+ const mib = kib / 1024;
3320
+ return `${mib.toFixed(mib >= 10 ? 0 : 1)} MB`;
3321
+ }
3272
3322
  function agentPromptImageBlockToDraftImage(image, idPrefix, index) {
3273
3323
  return {
3274
3324
  id: `${idPrefix}:image:${index}`,
@@ -6367,18 +6417,20 @@ function useAgentGUIActivation({
6367
6417
  [agentSessionId]: null
6368
6418
  }));
6369
6419
  try {
6420
+ const agentTargetId = input.agentTargetId?.trim() ?? "";
6421
+ if (input.mode === "new" && !agentTargetId) {
6422
+ throw new Error("agent_target_required");
6423
+ }
6370
6424
  const request = input.mode === "new" ? {
6371
6425
  mode: input.mode,
6372
6426
  workspaceId,
6373
6427
  agentSessionId,
6374
- agentTargetId: input.agentTargetId,
6375
- provider: input.provider,
6428
+ agentTargetId,
6376
6429
  cwd: input.cwd,
6377
6430
  initialContent: input.initialContent,
6378
6431
  initialDisplayPrompt: input.initialDisplayPrompt,
6379
6432
  metadata: input.metadata,
6380
6433
  title: input.title,
6381
- providerTargetRef: input.providerTargetRef,
6382
6434
  settings: input.settings,
6383
6435
  visible: input.visible,
6384
6436
  openclawGatewayReady: input.openclawGatewayReady
@@ -6419,7 +6471,7 @@ function useAgentGUIActivation({
6419
6471
  throw error;
6420
6472
  }
6421
6473
  },
6422
- [agentActivityRuntime, getErrorMessage, workspaceId]
6474
+ [agentActivityRuntime, getErrorCode, getErrorMessage, workspaceId]
6423
6475
  );
6424
6476
  const unactivate = useCallback3(
6425
6477
  async (agentSessionId) => {
@@ -6983,6 +7035,13 @@ function reportAgentGUIRuntimeError(input) {
6983
7035
  } catch {
6984
7036
  }
6985
7037
  }
7038
+ function showAgentGUIControllerErrorToast(hostToast, message) {
7039
+ if (hostToast?.error) {
7040
+ hostToast.error(message);
7041
+ return;
7042
+ }
7043
+ toast.error(message);
7044
+ }
6986
7045
  function reportAgentGUIConversationFilterTargetUnresolved(input) {
6987
7046
  const reportDiagnostic = input.runtime.reportDiagnostic;
6988
7047
  if (!reportDiagnostic) {
@@ -7309,7 +7368,7 @@ function shouldClearSubmittedDraft(input) {
7309
7368
  const submittedPrompt = agentPromptContentDisplayText(
7310
7369
  input.submittedContent
7311
7370
  ).trim();
7312
- if (currentDraft.prompt.trim() !== submittedPrompt) {
7371
+ if (agentComposerDraftSubmittedText(currentDraft).trim() !== submittedPrompt) {
7313
7372
  return false;
7314
7373
  }
7315
7374
  const submittedImages = input.submittedContent.filter(
@@ -8615,6 +8674,8 @@ var EMPTY_QUEUED_PROMPTS = Object.freeze(
8615
8674
  function areAgentComposerDraftsEqual(left, right) {
8616
8675
  const leftFiles = left.files ?? [];
8617
8676
  const rightFiles = right.files ?? [];
8677
+ const leftLargeTexts = left.largeTexts ?? [];
8678
+ const rightLargeTexts = right.largeTexts ?? [];
8618
8679
  return left.prompt === right.prompt && left.images.length === right.images.length && left.images.every((image, index) => {
8619
8680
  const other = right.images[index];
8620
8681
  if (!other) {
@@ -8627,6 +8688,12 @@ function areAgentComposerDraftsEqual(left, right) {
8627
8688
  return false;
8628
8689
  }
8629
8690
  return file.id === other.id && file.name === other.name && file.mimeType === other.mimeType && file.path === other.path && file.hostPath === other.hostPath && file.assetId === other.assetId && file.sizeBytes === other.sizeBytes && file.uploading === other.uploading && file.uploadError === other.uploadError;
8691
+ }) && leftLargeTexts.length === rightLargeTexts.length && leftLargeTexts.every((item, index) => {
8692
+ const other = rightLargeTexts[index];
8693
+ if (!other) {
8694
+ return false;
8695
+ }
8696
+ return item.id === other.id && item.name === other.name && item.text === other.text && item.sizeBytes === other.sizeBytes;
8630
8697
  });
8631
8698
  }
8632
8699
  function nodeDefaultDraftKey(agentProvider, agentTargetId) {
@@ -9043,7 +9110,6 @@ function useAgentGUINodeController({
9043
9110
  [homeComposerTargetOverride, normalizedExplicitProviderTargets]
9044
9111
  );
9045
9112
  const effectiveSelectedProviderTarget = homeComposerTargetOverride ?? selectedProviderTarget;
9046
- const effectiveSelectedProviderTargetIsExplicit = homeComposerTargetOverride ? homeComposerTargetOverrideIsExplicit : selectedProviderTargetIsExplicit;
9047
9113
  const firstReadyHomeComposerProviderTarget = useMemo3(() => {
9048
9114
  if (!providerReadinessGates) {
9049
9115
  return null;
@@ -9463,9 +9529,11 @@ function useAgentGUINodeController({
9463
9529
  const selectedProviderTargetRef = useRef4(effectiveSelectedProviderTarget);
9464
9530
  selectedProviderTargetRef.current = effectiveSelectedProviderTarget;
9465
9531
  const selectedProviderTargetIsExplicitRef = useRef4(
9466
- effectiveSelectedProviderTargetIsExplicit
9532
+ homeComposerTargetOverride ? homeComposerTargetOverrideIsExplicit : selectedProviderTargetIsExplicit
9467
9533
  );
9468
- selectedProviderTargetIsExplicitRef.current = effectiveSelectedProviderTargetIsExplicit;
9534
+ selectedProviderTargetIsExplicitRef.current = homeComposerTargetOverride ? homeComposerTargetOverrideIsExplicit : selectedProviderTargetIsExplicit;
9535
+ const providerTargetsProvidedRef = useRef4(providerTargets !== void 0);
9536
+ providerTargetsProvidedRef.current = providerTargets !== void 0;
9469
9537
  const selectedComposerTargetDataRef = useRef4(selectedComposerTargetData);
9470
9538
  selectedComposerTargetDataRef.current = selectedComposerTargetData;
9471
9539
  const draftSettingsBySessionIdRef = useRef4(draftSettingsBySessionId);
@@ -11825,7 +11893,7 @@ function useAgentGUINodeController({
11825
11893
  return;
11826
11894
  }
11827
11895
  const agentTargetId = targetData.agentTargetId ?? "";
11828
- if (!agentTargetId && selectedProviderTargetIsExplicitRef.current) {
11896
+ if (!agentTargetId || providerTargetsProvidedRef.current && !selectedProviderTargetIsExplicitRef.current) {
11829
11897
  setDetailError(translate("agentHost.agentGui.agentTargetRequired"));
11830
11898
  return;
11831
11899
  }
@@ -12012,8 +12080,6 @@ function useAgentGUINodeController({
12012
12080
  mode: "new",
12013
12081
  agentSessionId,
12014
12082
  agentTargetId: agentTargetId2 || null,
12015
- provider,
12016
- providerTargetRef: targetData.providerTargetRef,
12017
12083
  cwd: selectedProjectPath2 ?? "",
12018
12084
  initialContent: normalizedInitialContent,
12019
12085
  initialDisplayPrompt,
@@ -13867,7 +13933,7 @@ function useAgentGUINodeController({
13867
13933
  const handleRemoveError = (error) => {
13868
13934
  const message = getAgentGUIErrorMessage(error);
13869
13935
  setListError(message);
13870
- toast.error(message);
13936
+ showAgentGUIControllerErrorToast(agentHostApi.toast, message);
13871
13937
  };
13872
13938
  try {
13873
13939
  void Promise.resolve(remove({ path: normalizedPath })).then(() => {
@@ -13881,7 +13947,7 @@ function useAgentGUINodeController({
13881
13947
  handleRemoveError(error);
13882
13948
  }
13883
13949
  },
13884
- [agentHostApi.userProjects, setUserProjectsSnapshot]
13950
+ [agentHostApi.toast, agentHostApi.userProjects, setUserProjectsSnapshot]
13885
13951
  );
13886
13952
  const requestDeleteProjectConversations = useCallback4(
13887
13953
  (path) => {
@@ -13995,8 +14061,7 @@ function useAgentGUINodeController({
13995
14061
  runtime: agentActivityRuntime,
13996
14062
  workspaceId
13997
14063
  });
13998
- toast.error(message);
13999
- setDetailError(message);
14064
+ showAgentGUIControllerErrorToast(agentHostApi.toast, message);
14000
14065
  if (activeConversationIdRef.current === target.id) {
14001
14066
  setIsLoadingMessages(false);
14002
14067
  setAgentSessionViewMessagesLoading(sessionViewRef(target.id), false);
@@ -14015,6 +14080,7 @@ function useAgentGUINodeController({
14015
14080
  workspaceId,
14016
14081
  sessionViewRef,
14017
14082
  agentActivityRuntime,
14083
+ agentHostApi.toast,
14018
14084
  agentQueuedPromptRuntime,
14019
14085
  removeConversations
14020
14086
  ]);
@@ -14154,8 +14220,7 @@ function useAgentGUINodeController({
14154
14220
  }
14155
14221
  });
14156
14222
  setListError(message);
14157
- toast.error(message);
14158
- setDetailError(message);
14223
+ showAgentGUIControllerErrorToast(agentHostApi.toast, message);
14159
14224
  if (activeDeletedConversationId && activeConversationIdRef.current === activeDeletedConversationId) {
14160
14225
  setIsLoadingMessages(false);
14161
14226
  setAgentSessionViewMessagesLoading(
@@ -14180,6 +14245,7 @@ function useAgentGUINodeController({
14180
14245
  sessionViewRef,
14181
14246
  setTransientConversation,
14182
14247
  removeConversations,
14248
+ agentHostApi.toast,
14183
14249
  workspaceId
14184
14250
  ]
14185
14251
  );
@@ -14232,8 +14298,7 @@ function useAgentGUINodeController({
14232
14298
  }
14233
14299
  });
14234
14300
  setListError(message);
14235
- toast.error(message);
14236
- setDetailError(message);
14301
+ showAgentGUIControllerErrorToast(agentHostApi.toast, message);
14237
14302
  if (activeDeletedConversationId && activeConversationIdRef.current === activeDeletedConversationId) {
14238
14303
  setIsLoadingMessages(false);
14239
14304
  setAgentSessionViewMessagesLoading(
@@ -14252,6 +14317,7 @@ function useAgentGUINodeController({
14252
14317
  finalizeConversationBatchDeletion,
14253
14318
  isDeletingProjectConversations,
14254
14319
  sessionViewRef,
14320
+ agentHostApi.toast,
14255
14321
  workspaceId
14256
14322
  ]
14257
14323
  );
@@ -14291,8 +14357,7 @@ function useAgentGUINodeController({
14291
14357
  runtime: agentActivityRuntime,
14292
14358
  workspaceId
14293
14359
  });
14294
- toast.error(message);
14295
- setDetailError(message);
14360
+ showAgentGUIControllerErrorToast(agentHostApi.toast, message);
14296
14361
  const previous = previousConversations.find(
14297
14362
  (conversation2) => conversation2.id === normalizedAgentSessionId
14298
14363
  );
@@ -14304,7 +14369,7 @@ function useAgentGUINodeController({
14304
14369
  );
14305
14370
  });
14306
14371
  },
14307
- [agentActivityRuntime, patchConversation, workspaceId]
14372
+ [agentActivityRuntime, agentHostApi.toast, patchConversation, workspaceId]
14308
14373
  );
14309
14374
  const activeConversation = useMemo3(() => {
14310
14375
  const resolved = resolveConversationSummaryById(
@@ -17421,6 +17486,9 @@ var styles3 = {
17421
17486
  composerFooterRight: "agent-gui-node__composer-footer-right",
17422
17487
  composerHero: "agent-gui-node__composer-hero",
17423
17488
  composerFloatingPrompt: "agent-gui-node__composer-floating-prompt",
17489
+ composerFileDropOverlay: "agent-gui-node__composer-file-drop-overlay",
17490
+ composerFileDropOverlayActive: "agent-gui-node__composer-file-drop-overlay--active",
17491
+ composerFileDropOverlayCard: "agent-gui-node__composer-file-drop-overlay-card",
17424
17492
  composerHandoffIcon: "agent-gui-node__composer-handoff-icon",
17425
17493
  composerHandoffAnimatedIcon: "agent-gui-node__composer-handoff-icon-animated",
17426
17494
  composerHandoffMenuContent: "agent-gui-node__composer-handoff-menu-content",
@@ -17537,7 +17605,10 @@ var styles3 = {
17537
17605
  providerRailAvatar: "agent-gui-node__provider-rail-avatar",
17538
17606
  providerRailAvatarIcon: "agent-gui-node__provider-rail-avatar-icon",
17539
17607
  providerRailAvatarImage: "agent-gui-node__provider-rail-avatar-image",
17608
+ providerRailBadge: "agent-gui-node__provider-rail-badge",
17609
+ providerRailBadgeImage: "agent-gui-node__provider-rail-badge-image",
17540
17610
  providerRailLaunchpadIcon: "agent-gui-node__provider-rail-launchpad-icon",
17611
+ emptyHeroIconSlot: "agent-gui-node__empty-hero-icon-slot",
17541
17612
  emptyHeroLaunchpadIcon: "agent-gui-node__empty-hero-launchpad-icon",
17542
17613
  providerRailLaunchpadItem: "agent-gui-node__provider-rail-launchpad-item",
17543
17614
  providerRailConfigButton: "agent-gui-node__provider-rail-config-button",
@@ -19240,6 +19311,16 @@ function fileToBase64(file) {
19240
19311
 
19241
19312
  // agent-gui/agentGuiNode/agentRichText/AgentRichTextEditor.tsx
19242
19313
  import { jsx as jsx26, jsxs as jsxs15 } from "react/jsx-runtime";
19314
+ var AGENT_RICH_TEXT_LARGE_PASTE_MIN_CHARS = 2e3;
19315
+ var AGENT_RICH_TEXT_LARGE_PASTE_MIN_LINES = 12;
19316
+ function isAgentRichTextLargeTextPaste(text) {
19317
+ const trimmed = text.trim();
19318
+ if (trimmed.length < AGENT_RICH_TEXT_LARGE_PASTE_MIN_CHARS) {
19319
+ const lineCount = trimmed ? trimmed.split(/\r\n|\r|\n/).length : 0;
19320
+ return lineCount >= AGENT_RICH_TEXT_LARGE_PASTE_MIN_LINES;
19321
+ }
19322
+ return true;
19323
+ }
19243
19324
  function buildWorkspaceFileMentionDropContent(entries, options = {}) {
19244
19325
  return entries.flatMap((entry, index) => [
19245
19326
  ...index === 0 && options.prefixCaretAnchor ? [
@@ -19525,6 +19606,7 @@ var AgentRichTextEditor = forwardRef3(function AgentRichTextEditor2({
19525
19606
  promptImagesSupported = true,
19526
19607
  onPromptImagesUnsupported,
19527
19608
  onPasteImages,
19609
+ onPasteLargeText,
19528
19610
  getReferenceForFile,
19529
19611
  onDropFiles
19530
19612
  }, ref) {
@@ -19545,6 +19627,7 @@ var AgentRichTextEditor = forwardRef3(function AgentRichTextEditor2({
19545
19627
  const onLinkClickRef = useRef8(onLinkClick);
19546
19628
  const onPromptImagesUnsupportedRef = useRef8(onPromptImagesUnsupported);
19547
19629
  const onPasteImagesRef = useRef8(onPasteImages);
19630
+ const onPasteLargeTextRef = useRef8(onPasteLargeText);
19548
19631
  const onDropFilesRef = useRef8(onDropFiles);
19549
19632
  const promptImagesSupportedRef = useRef8(promptImagesSupported);
19550
19633
  const getReferenceForFileRef = useRef8(getReferenceForFile);
@@ -19563,6 +19646,10 @@ var AgentRichTextEditor = forwardRef3(function AgentRichTextEditor2({
19563
19646
  if (!currentEditor || currentEditor.isDestroyed || !text) {
19564
19647
  return;
19565
19648
  }
19649
+ if (onPasteLargeTextRef.current && isAgentRichTextLargeTextPaste(text)) {
19650
+ onPasteLargeTextRef.current(text);
19651
+ return;
19652
+ }
19566
19653
  suppressPastedAtSuggestionRef.current = text.includes("@") && !text.endsWith("@");
19567
19654
  if (suppressPastedAtSuggestionRef.current) {
19568
19655
  window.setTimeout(() => {
@@ -19662,6 +19749,7 @@ var AgentRichTextEditor = forwardRef3(function AgentRichTextEditor2({
19662
19749
  onLinkClickRef.current = onLinkClick;
19663
19750
  onPromptImagesUnsupportedRef.current = onPromptImagesUnsupported;
19664
19751
  onPasteImagesRef.current = onPasteImages;
19752
+ onPasteLargeTextRef.current = onPasteLargeText;
19665
19753
  onDropFilesRef.current = onDropFiles;
19666
19754
  promptImagesSupportedRef.current = promptImagesSupported;
19667
19755
  getReferenceForFileRef.current = getReferenceForFile;
@@ -19822,6 +19910,10 @@ var AgentRichTextEditor = forwardRef3(function AgentRichTextEditor2({
19822
19910
  return false;
19823
19911
  }
19824
19912
  event.preventDefault();
19913
+ if (onPasteLargeTextRef.current && isAgentRichTextLargeTextPaste(text)) {
19914
+ onPasteLargeTextRef.current(text);
19915
+ return true;
19916
+ }
19825
19917
  const currentEditor = editorRef.current;
19826
19918
  if (!currentEditor) {
19827
19919
  return true;
@@ -21039,6 +21131,13 @@ var DOCK_COMPOSER_TEXT_VIEWPORT_MAX_HEIGHT = DOCK_COMPOSER_TEXT_LINE_HEIGHT * DO
21039
21131
  var DOCK_COMPOSER_INPUT_MAX_HEIGHT = DOCK_COMPOSER_INPUT_TEXT_CHROME_HEIGHT + DOCK_COMPOSER_TEXT_VIEWPORT_MAX_HEIGHT;
21040
21132
  var DOCK_COMPOSER_INPUT_BORDER_HEIGHT = 2;
21041
21133
  var DOCK_COMPOSER_INPUT_PADDING_BLOCK_HEIGHT = 24;
21134
+ var AGENT_COMPOSER_PASTED_TEXT_FILE_PREFIX = "pasted-text";
21135
+ function agentComposerTextByteLength(text) {
21136
+ if (typeof TextEncoder !== "undefined") {
21137
+ return new TextEncoder().encode(text).byteLength;
21138
+ }
21139
+ return text.length;
21140
+ }
21042
21141
  function agentUsageChipLevel(percentUsed) {
21043
21142
  if (percentUsed >= USAGE_CRITICAL_PERCENT) {
21044
21143
  return "critical";
@@ -21194,8 +21293,10 @@ function AgentUsageChip({
21194
21293
  PopoverContent,
21195
21294
  {
21196
21295
  ref: usagePopoverContentRef,
21197
- side: "bottom",
21198
- align: "end",
21296
+ side: "top",
21297
+ align: "center",
21298
+ sideOffset: 8,
21299
+ collisionPadding: 16,
21199
21300
  className: "w-[320px] max-w-[calc(100vw-32px)] gap-3 text-xs",
21200
21301
  "data-testid": "agent-gui-usage-popover",
21201
21302
  onOpenAutoFocus: (event) => event.preventDefault(),
@@ -21302,6 +21403,13 @@ function hasInlineOverflow(element) {
21302
21403
  }
21303
21404
  return element.scrollWidth > element.clientWidth + 1;
21304
21405
  }
21406
+ function isPointInsideElement(element, clientX, clientY) {
21407
+ if (!element) {
21408
+ return false;
21409
+ }
21410
+ const bounds = element.getBoundingClientRect();
21411
+ return clientX >= bounds.left && clientX <= bounds.right && clientY >= bounds.top && clientY <= bounds.bottom;
21412
+ }
21305
21413
  function AgentComposerMaskIcon({
21306
21414
  iconUrl,
21307
21415
  marker
@@ -21488,6 +21596,7 @@ function AgentComposer({
21488
21596
  const isGoalModeActive = goalDraftObjective !== null;
21489
21597
  const draftImages = draftContent.images;
21490
21598
  const draftFiles = draftContent.files ?? [];
21599
+ const draftLargeTexts = draftContent.largeTexts ?? [];
21491
21600
  const agentActivityRuntime = useOptionalAgentActivityRuntime();
21492
21601
  const agentHostApi = useOptionalAgentHostApi();
21493
21602
  const getReferenceForFile = agentHostApi?.workspace.getReferenceForFile;
@@ -21535,6 +21644,8 @@ function AgentComposer({
21535
21644
  const draftPromptRef = useRef11(draftPrompt);
21536
21645
  const draftImagesRef = useRef11(draftImages);
21537
21646
  const draftFilesRef = useRef11(draftFiles);
21647
+ const draftLargeTextsRef = useRef11(draftLargeTexts);
21648
+ const nextDraftLargeTextIndexRef = useRef11(draftLargeTexts.length);
21538
21649
  const promptTipRef = useRef11(null);
21539
21650
  const mentionControllerRef = useRef11(
21540
21651
  null
@@ -21777,6 +21888,13 @@ function AgentComposer({
21777
21888
  useEffect13(() => {
21778
21889
  draftFilesRef.current = draftFiles;
21779
21890
  }, [draftFiles]);
21891
+ useEffect13(() => {
21892
+ draftLargeTextsRef.current = draftLargeTexts;
21893
+ nextDraftLargeTextIndexRef.current = Math.max(
21894
+ nextDraftLargeTextIndexRef.current,
21895
+ draftLargeTexts.length
21896
+ );
21897
+ }, [draftLargeTexts]);
21780
21898
  useEffect13(() => {
21781
21899
  if (previousSlashStatusAgentSessionIdRef.current === slashStatusAgentSessionId) {
21782
21900
  return;
@@ -21978,6 +22096,7 @@ function AgentComposer({
21978
22096
  const canSubmitWhileSending = canQueueWhileBusy && isSendingTurn;
21979
22097
  const currentDraftImages = draftImagesRef.current;
21980
22098
  const currentDraftFiles = draftFilesRef.current;
22099
+ const currentDraftLargeTexts = draftLargeTextsRef.current;
21981
22100
  const hasUploadingImages = currentDraftImages.some(
21982
22101
  (image) => image.uploading
21983
22102
  );
@@ -21996,7 +22115,8 @@ function AgentComposer({
21996
22115
  ...draftContent,
21997
22116
  prompt: nextPrompt,
21998
22117
  images: currentDraftImages,
21999
- files: currentDraftFiles
22118
+ files: currentDraftFiles,
22119
+ largeTexts: currentDraftLargeTexts
22000
22120
  };
22001
22121
  if (!agentComposerDraftHasContent(nextDraftContent)) {
22002
22122
  return;
@@ -22031,18 +22151,28 @@ function AgentComposer({
22031
22151
  provider,
22032
22152
  skills: availableSkills
22033
22153
  });
22154
+ const submitDisplayPrompt = agentComposerDraftDisplayPrompt(nextDraftContent);
22034
22155
  if (options?.guidance === true) {
22035
22156
  if (!onSubmitGuidance) {
22036
22157
  return;
22037
22158
  }
22038
- onSubmitGuidance(submitContent);
22159
+ if (submitDisplayPrompt) {
22160
+ onSubmitGuidance(submitContent, submitDisplayPrompt);
22161
+ } else {
22162
+ onSubmitGuidance(submitContent);
22163
+ }
22039
22164
  } else {
22040
- onSubmit(submitContent);
22165
+ if (submitDisplayPrompt) {
22166
+ onSubmit(submitContent, submitDisplayPrompt);
22167
+ } else {
22168
+ onSubmit(submitContent);
22169
+ }
22041
22170
  }
22042
22171
  if (hasActiveConversation) {
22043
22172
  draftPromptRef.current = "";
22044
22173
  draftImagesRef.current = [];
22045
22174
  draftFilesRef.current = [];
22175
+ draftLargeTextsRef.current = [];
22046
22176
  setPaletteDraftPrompt("");
22047
22177
  onDraftContentChange(emptyAgentComposerDraft());
22048
22178
  }
@@ -22441,7 +22571,8 @@ function AgentComposer({
22441
22571
  onDraftContentChange({
22442
22572
  prompt: draftPromptRef.current,
22443
22573
  images: nextDraftImages,
22444
- files: draftFilesRef.current
22574
+ files: draftFilesRef.current,
22575
+ largeTexts: draftLargeTextsRef.current
22445
22576
  });
22446
22577
  if (!uploadPromptContent) {
22447
22578
  return;
@@ -22479,7 +22610,8 @@ function AgentComposer({
22479
22610
  onDraftContentChange({
22480
22611
  prompt: draftPromptRef.current,
22481
22612
  images: uploadedDraftImages,
22482
- files: draftFilesRef.current
22613
+ files: draftFilesRef.current,
22614
+ largeTexts: draftLargeTextsRef.current
22483
22615
  });
22484
22616
  }).catch((error) => {
22485
22617
  const message = error instanceof Error ? error.message : String(error);
@@ -22494,7 +22626,8 @@ function AgentComposer({
22494
22626
  onDraftContentChange({
22495
22627
  prompt: draftPromptRef.current,
22496
22628
  images: failedDraftImages,
22497
- files: draftFilesRef.current
22629
+ files: draftFilesRef.current,
22630
+ largeTexts: draftLargeTextsRef.current
22498
22631
  });
22499
22632
  });
22500
22633
  }
@@ -22516,7 +22649,8 @@ function AgentComposer({
22516
22649
  onDraftContentChange({
22517
22650
  prompt: draftPromptRef.current,
22518
22651
  images: nextDraftImages,
22519
- files: draftFilesRef.current
22652
+ files: draftFilesRef.current,
22653
+ largeTexts: draftLargeTextsRef.current
22520
22654
  });
22521
22655
  },
22522
22656
  [onDraftContentChange]
@@ -22530,7 +22664,50 @@ function AgentComposer({
22530
22664
  onDraftContentChange({
22531
22665
  prompt: draftPromptRef.current,
22532
22666
  images: draftImagesRef.current,
22533
- files: nextDraftFiles
22667
+ files: nextDraftFiles,
22668
+ largeTexts: draftLargeTextsRef.current
22669
+ });
22670
+ },
22671
+ [onDraftContentChange]
22672
+ );
22673
+ const removeDraftLargeText = useCallback9(
22674
+ (id) => {
22675
+ const nextDraftLargeTexts = draftLargeTextsRef.current.filter(
22676
+ (item) => item.id !== id
22677
+ );
22678
+ draftLargeTextsRef.current = nextDraftLargeTexts;
22679
+ onDraftContentChange({
22680
+ prompt: draftPromptRef.current,
22681
+ images: draftImagesRef.current,
22682
+ files: draftFilesRef.current,
22683
+ largeTexts: nextDraftLargeTexts
22684
+ });
22685
+ },
22686
+ [onDraftContentChange]
22687
+ );
22688
+ const handlePastedLargeText = useCallback9(
22689
+ (text) => {
22690
+ const normalizedText = text.replace(/\r\n/g, "\n").replace(/\r/g, "\n");
22691
+ if (!normalizedText.trim()) {
22692
+ return;
22693
+ }
22694
+ const nextIndex = nextDraftLargeTextIndexRef.current + 1;
22695
+ nextDraftLargeTextIndexRef.current = nextIndex;
22696
+ const nextDraftLargeTexts = [
22697
+ ...draftLargeTextsRef.current,
22698
+ {
22699
+ id: `${AGENT_COMPOSER_PASTED_TEXT_FILE_PREFIX}-${nextIndex}`,
22700
+ name: `${AGENT_COMPOSER_PASTED_TEXT_FILE_PREFIX}-${nextIndex}.txt`,
22701
+ text: normalizedText,
22702
+ sizeBytes: agentComposerTextByteLength(normalizedText)
22703
+ }
22704
+ ];
22705
+ draftLargeTextsRef.current = nextDraftLargeTexts;
22706
+ onDraftContentChange({
22707
+ prompt: draftPromptRef.current,
22708
+ images: draftImagesRef.current,
22709
+ files: draftFilesRef.current,
22710
+ largeTexts: nextDraftLargeTexts
22534
22711
  });
22535
22712
  },
22536
22713
  [onDraftContentChange]
@@ -22766,6 +22943,8 @@ function AgentComposer({
22766
22943
  },
22767
22944
  [addDraftImages, scheduleComposerFocus]
22768
22945
  );
22946
+ const [fileDropOverlayHost, setFileDropOverlayHost] = useState12(null);
22947
+ const [fileDropOverlayActive, setFileDropOverlayActive] = useState12(false);
22769
22948
  useEffect13(() => {
22770
22949
  const composer = composerRef.current;
22771
22950
  const dropTarget = composer?.closest("#agent-gui-detail") ?? composer;
@@ -22773,7 +22952,13 @@ function AgentComposer({
22773
22952
  return void 0;
22774
22953
  }
22775
22954
  let isDisposed = false;
22955
+ setFileDropOverlayHost(dropTarget);
22776
22956
  const isDragEvent = (event) => "dataTransfer" in event;
22957
+ const clearDropOverlay = () => {
22958
+ if (!isDisposed) {
22959
+ setFileDropOverlayActive(false);
22960
+ }
22961
+ };
22777
22962
  const containsEventTarget = (event) => {
22778
22963
  const target = event.target;
22779
22964
  return target instanceof Node && dropTarget.contains(target);
@@ -22813,11 +22998,15 @@ function AgentComposer({
22813
22998
  }
22814
22999
  event.preventDefault();
22815
23000
  if (!drag.hasRegularFiles && drag.hasImageFiles && !promptImagesSupported) {
23001
+ clearDropOverlay();
22816
23002
  return;
22817
23003
  }
22818
23004
  if (event.dataTransfer) {
22819
23005
  event.dataTransfer.dropEffect = "copy";
22820
23006
  }
23007
+ if (!isDisposed) {
23008
+ setFileDropOverlayActive(true);
23009
+ }
22821
23010
  };
22822
23011
  const handleDrop = (event) => {
22823
23012
  if (!isDragEvent(event)) {
@@ -22829,6 +23018,7 @@ function AgentComposer({
22829
23018
  }
22830
23019
  event.preventDefault();
22831
23020
  event.stopPropagation();
23021
+ clearDropOverlay();
22832
23022
  if (drop.regularFiles.length > 0) {
22833
23023
  editorHandleRef.current?.focusAtEnd();
22834
23024
  void applyDroppedFileReferences(drop.regularFiles).then(() => {
@@ -22852,12 +23042,46 @@ function AgentComposer({
22852
23042
  scheduleComposerFocus();
22853
23043
  });
22854
23044
  };
23045
+ const handleDocumentDragOver = (event) => {
23046
+ if (!isDragEvent(event)) {
23047
+ return;
23048
+ }
23049
+ if (isPointInsideElement(
23050
+ dropTarget,
23051
+ event.clientX,
23052
+ event.clientY
23053
+ )) {
23054
+ return;
23055
+ }
23056
+ clearDropOverlay();
23057
+ };
23058
+ const handleDocumentDragLeave = (event) => {
23059
+ if (!isDragEvent(event)) {
23060
+ return;
23061
+ }
23062
+ const leftWindow = event.relatedTarget === null || event.clientX <= 0 || event.clientY <= 0 || event.clientX >= window.innerWidth || event.clientY >= window.innerHeight;
23063
+ if (leftWindow) {
23064
+ clearDropOverlay();
23065
+ }
23066
+ };
22855
23067
  dropTarget.addEventListener("dragover", handleDragOver);
22856
23068
  dropTarget.addEventListener("drop", handleDrop);
23069
+ document.addEventListener("dragover", handleDocumentDragOver, true);
23070
+ document.addEventListener("dragleave", handleDocumentDragLeave, true);
23071
+ window.addEventListener("dragend", clearDropOverlay);
23072
+ window.addEventListener("drop", clearDropOverlay);
23073
+ window.addEventListener("blur", clearDropOverlay);
22857
23074
  return () => {
22858
23075
  isDisposed = true;
23076
+ setFileDropOverlayHost(null);
23077
+ setFileDropOverlayActive(false);
22859
23078
  dropTarget.removeEventListener("dragover", handleDragOver);
22860
23079
  dropTarget.removeEventListener("drop", handleDrop);
23080
+ document.removeEventListener("dragover", handleDocumentDragOver, true);
23081
+ document.removeEventListener("dragleave", handleDocumentDragLeave, true);
23082
+ window.removeEventListener("dragend", clearDropOverlay);
23083
+ window.removeEventListener("drop", clearDropOverlay);
23084
+ window.removeEventListener("blur", clearDropOverlay);
22861
23085
  };
22862
23086
  }, [
22863
23087
  addDraftImages,
@@ -23048,7 +23272,13 @@ function AgentComposer({
23048
23272
  resizeObserver?.disconnect();
23049
23273
  window.removeEventListener("resize", measure);
23050
23274
  };
23051
- }, [draftFiles.length, draftImages.length, isHeroLayout, paletteDraftPrompt]);
23275
+ }, [
23276
+ draftFiles.length,
23277
+ draftImages.length,
23278
+ draftLargeTexts.length,
23279
+ isHeroLayout,
23280
+ paletteDraftPrompt
23281
+ ]);
23052
23282
  const inputShellStyle = useMemo8(
23053
23283
  () => showFileMentionPalette || showFloatingCommandMenu ? { zIndex: composerPaletteZIndex } : void 0,
23054
23284
  [showFileMentionPalette, showFloatingCommandMenu]
@@ -23086,6 +23316,7 @@ function AgentComposer({
23086
23316
  const disabledReasonText = disabledReason?.trim() ?? "";
23087
23317
  const effectivePlaceholder = disabledReasonText || placeholder;
23088
23318
  const visibleDraftFiles = draftFiles;
23319
+ const visibleDraftLargeTexts = draftLargeTexts;
23089
23320
  useEffect13(() => {
23090
23321
  if (previousSelectedProjectPathRef.current === selectedProjectPath) {
23091
23322
  return;
@@ -23191,6 +23422,22 @@ function AgentComposer({
23191
23422
  },
23192
23423
  activePromptTip.id
23193
23424
  ) : null;
23425
+ const fileDropOverlay = fileDropOverlayHost !== null ? createPortal3(
23426
+ /* @__PURE__ */ jsx30(
23427
+ "div",
23428
+ {
23429
+ "aria-hidden": "true",
23430
+ "data-testid": "agent-gui-composer-file-drop-overlay",
23431
+ "data-active": fileDropOverlayActive ? "true" : "false",
23432
+ className: cn(
23433
+ AgentGUINode_styles_default.composerFileDropOverlay,
23434
+ fileDropOverlayActive && AgentGUINode_styles_default.composerFileDropOverlayActive
23435
+ ),
23436
+ children: /* @__PURE__ */ jsx30("span", { className: AgentGUINode_styles_default.composerFileDropOverlayCard, children: labels.fileDropHint })
23437
+ }
23438
+ ),
23439
+ fileDropOverlayHost
23440
+ ) : null;
23194
23441
  return /* @__PURE__ */ jsxs18(
23195
23442
  "form",
23196
23443
  {
@@ -23199,6 +23446,7 @@ function AgentComposer({
23199
23446
  "data-layout": layoutMode,
23200
23447
  onSubmit: submit,
23201
23448
  children: [
23449
+ fileDropOverlay,
23202
23450
  visibleActivePrompt ? /* @__PURE__ */ jsx30(
23203
23451
  "div",
23204
23452
  {
@@ -23347,54 +23595,86 @@ function AgentComposer({
23347
23595
  ))
23348
23596
  }
23349
23597
  ) : null,
23350
- visibleDraftFiles.length > 0 ? /* @__PURE__ */ jsx30(
23598
+ visibleDraftFiles.length > 0 || visibleDraftLargeTexts.length > 0 ? /* @__PURE__ */ jsxs18(
23351
23599
  "div",
23352
23600
  {
23353
23601
  className: "mb-2 flex max-w-[520px] flex-wrap gap-2",
23354
23602
  "data-testid": "agent-gui-composer-file-drafts",
23355
- children: visibleDraftFiles.map((file) => /* @__PURE__ */ jsxs18(
23356
- "div",
23357
- {
23358
- className: cn(
23359
- "group inline-flex max-w-full items-center gap-2 rounded-[6px] border border-[var(--line-1)] bg-[var(--background-fronted)] px-2 py-1 text-xs text-[var(--text-primary)]",
23360
- file.uploadError && "border-[color:color-mix(in_srgb,var(--danger)_55%,var(--line-1))]"
23361
- ),
23362
- "data-uploading": file.uploading ? "true" : void 0,
23363
- "data-upload-error": file.uploadError ? "true" : void 0,
23364
- title: file.hostPath ?? file.path ?? file.name,
23365
- children: [
23366
- file.uploading ? /* @__PURE__ */ jsx30(
23367
- Spinner,
23368
- {
23369
- className: "shrink-0 text-[var(--text-primary)]",
23370
- size: 14,
23371
- strokeWidth: 2.4,
23372
- trackColor: "var(--transparency-hover)",
23373
- testId: "agent-gui-composer-file-upload-spinner"
23374
- }
23375
- ) : /* @__PURE__ */ jsx30(
23376
- "span",
23377
- {
23378
- className: "size-2 shrink-0 rounded-full bg-[var(--text-tertiary)]",
23379
- "aria-hidden": true
23380
- }
23603
+ children: [
23604
+ visibleDraftLargeTexts.map((item) => /* @__PURE__ */ jsxs18(
23605
+ "div",
23606
+ {
23607
+ className: "group inline-flex max-w-full items-center gap-2 rounded-[6px] border border-[var(--line-1)] bg-[var(--background-fronted)] px-2 py-1 text-xs text-[var(--text-primary)]",
23608
+ "data-testid": "agent-gui-composer-large-text-draft",
23609
+ title: item.name,
23610
+ children: [
23611
+ /* @__PURE__ */ jsx30(
23612
+ "span",
23613
+ {
23614
+ className: "size-2 shrink-0 rounded-full bg-[var(--text-tertiary)]",
23615
+ "aria-hidden": true
23616
+ }
23617
+ ),
23618
+ /* @__PURE__ */ jsx30("span", { className: "min-w-0 max-w-[220px] truncate", children: item.name }),
23619
+ /* @__PURE__ */ jsx30(
23620
+ "button",
23621
+ {
23622
+ type: "button",
23623
+ className: "inline-flex size-5 shrink-0 items-center justify-center rounded-full text-[var(--text-secondary)] transition hover:bg-[var(--transparency-hover)] hover:text-[var(--text-primary)] focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-[color:color-mix(in_srgb,var(--text-primary)_34%,transparent)]",
23624
+ "aria-label": labels.removeMention,
23625
+ title: labels.removeMention,
23626
+ onClick: () => removeDraftLargeText(item.id),
23627
+ children: /* @__PURE__ */ jsx30(X, { size: 12, strokeWidth: 2.4, "aria-hidden": true })
23628
+ }
23629
+ )
23630
+ ]
23631
+ },
23632
+ item.id
23633
+ )),
23634
+ visibleDraftFiles.map((file) => /* @__PURE__ */ jsxs18(
23635
+ "div",
23636
+ {
23637
+ className: cn(
23638
+ "group inline-flex max-w-full items-center gap-2 rounded-[6px] border border-[var(--line-1)] bg-[var(--background-fronted)] px-2 py-1 text-xs text-[var(--text-primary)]",
23639
+ file.uploadError && "border-[color:color-mix(in_srgb,var(--danger)_55%,var(--line-1))]"
23381
23640
  ),
23382
- /* @__PURE__ */ jsx30("span", { className: "min-w-0 max-w-[220px] truncate", children: file.name }),
23383
- /* @__PURE__ */ jsx30(
23384
- "button",
23385
- {
23386
- type: "button",
23387
- className: "inline-flex size-5 shrink-0 items-center justify-center rounded-full text-[var(--text-secondary)] transition hover:bg-[var(--transparency-hover)] hover:text-[var(--text-primary)] focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-[color:color-mix(in_srgb,var(--text-primary)_34%,transparent)]",
23388
- "aria-label": labels.removeMention,
23389
- title: labels.removeMention,
23390
- onClick: () => removeDraftFile(file.id),
23391
- children: /* @__PURE__ */ jsx30(X, { size: 12, strokeWidth: 2.4, "aria-hidden": true })
23392
- }
23393
- )
23394
- ]
23395
- },
23396
- file.id
23397
- ))
23641
+ "data-uploading": file.uploading ? "true" : void 0,
23642
+ "data-upload-error": file.uploadError ? "true" : void 0,
23643
+ title: file.hostPath ?? file.path ?? file.name,
23644
+ children: [
23645
+ file.uploading ? /* @__PURE__ */ jsx30(
23646
+ Spinner,
23647
+ {
23648
+ className: "shrink-0 text-[var(--text-primary)]",
23649
+ size: 14,
23650
+ strokeWidth: 2.4,
23651
+ trackColor: "var(--transparency-hover)",
23652
+ testId: "agent-gui-composer-file-upload-spinner"
23653
+ }
23654
+ ) : /* @__PURE__ */ jsx30(
23655
+ "span",
23656
+ {
23657
+ className: "size-2 shrink-0 rounded-full bg-[var(--text-tertiary)]",
23658
+ "aria-hidden": true
23659
+ }
23660
+ ),
23661
+ /* @__PURE__ */ jsx30("span", { className: "min-w-0 max-w-[220px] truncate", children: file.name }),
23662
+ /* @__PURE__ */ jsx30(
23663
+ "button",
23664
+ {
23665
+ type: "button",
23666
+ className: "inline-flex size-5 shrink-0 items-center justify-center rounded-full text-[var(--text-secondary)] transition hover:bg-[var(--transparency-hover)] hover:text-[var(--text-primary)] focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-[color:color-mix(in_srgb,var(--text-primary)_34%,transparent)]",
23667
+ "aria-label": labels.removeMention,
23668
+ title: labels.removeMention,
23669
+ onClick: () => removeDraftFile(file.id),
23670
+ children: /* @__PURE__ */ jsx30(X, { size: 12, strokeWidth: 2.4, "aria-hidden": true })
23671
+ }
23672
+ )
23673
+ ]
23674
+ },
23675
+ file.id
23676
+ ))
23677
+ ]
23398
23678
  }
23399
23679
  ) : null,
23400
23680
  /* @__PURE__ */ jsxs18(
@@ -23426,6 +23706,7 @@ function AgentComposer({
23426
23706
  promptImagesSupported,
23427
23707
  onPromptImagesUnsupported,
23428
23708
  onPasteImages: handlePastedImages,
23709
+ onPasteLargeText: handlePastedLargeText,
23429
23710
  getReferenceForFile,
23430
23711
  onDropFiles: promptFilesSupported ? applyDroppedFileReferences : void 0
23431
23712
  }
@@ -23667,93 +23948,98 @@ function AgentComposer({
23667
23948
  /* @__PURE__ */ jsx30(TooltipContent3, { side: "top", children: labels.mentionPalette })
23668
23949
  ] }) })
23669
23950
  ] }),
23670
- showHandoffSelect ? /* @__PURE__ */ jsxs18(
23671
- Select2,
23672
- {
23673
- value: HANDOFF_SELECT_IDLE_VALUE,
23674
- disabled: handoffDisabled,
23675
- onValueChange: (nextTargetId) => {
23676
- const target = handoffMenuTargets.find(
23677
- (candidate) => candidate.targetId === nextTargetId
23678
- );
23679
- if (!target || target.disabled === true) {
23680
- return;
23681
- }
23682
- onHandoffConversation?.(target);
23683
- },
23684
- children: [
23685
- /* @__PURE__ */ jsx30(
23686
- SelectTrigger2,
23687
- {
23688
- size: "sm",
23689
- "aria-label": effectiveHandoffLabel,
23690
- title: effectiveHandoffLabel,
23691
- onBlur: () => {
23692
- setIsHandoffIconPlaying(false);
23693
- },
23694
- onFocus: () => {
23695
- setIsHandoffIconPlaying(true);
23696
- },
23697
- onMouseEnter: () => {
23698
- setIsHandoffIconPlaying(true);
23699
- },
23700
- onMouseLeave: () => {
23701
- setIsHandoffIconPlaying(false);
23702
- },
23703
- className: cn(
23704
- AgentGUINode_styles_default.composerMenuTrigger,
23705
- AgentGUINode_styles_default.composerProviderSelect,
23706
- AgentGUINode_styles_default.composerHandoffTrigger,
23707
- "w-auto max-w-[180px] [&>svg:last-child]:hidden"
23708
- ),
23709
- children: /* @__PURE__ */ jsxs18("span", { className: "flex min-w-0 items-center gap-1.5", children: [
23710
- /* @__PURE__ */ jsx30(
23711
- AgentComposerHandoffIcon,
23712
- {
23713
- disabled: handoffDisabled,
23714
- isPlaying: isHandoffIconPlaying
23715
- }
23716
- ),
23717
- /* @__PURE__ */ jsx30("span", { className: "min-w-0 truncate", children: effectiveHandoffLabel })
23718
- ] })
23951
+ showHandoffSelect ? /* @__PURE__ */ jsx30(TooltipProvider2, { children: /* @__PURE__ */ jsxs18(Tooltip3, { children: [
23952
+ /* @__PURE__ */ jsxs18(
23953
+ Select2,
23954
+ {
23955
+ value: HANDOFF_SELECT_IDLE_VALUE,
23956
+ disabled: handoffDisabled,
23957
+ onValueChange: (nextTargetId) => {
23958
+ const target = handoffMenuTargets.find(
23959
+ (candidate) => candidate.targetId === nextTargetId
23960
+ );
23961
+ if (!target || target.disabled === true) {
23962
+ return;
23719
23963
  }
23720
- ),
23721
- /* @__PURE__ */ jsx30(
23722
- SelectContent2,
23723
- {
23724
- align: "start",
23725
- className: cn(
23726
- AgentGUINode_styles_default.composerMenuContent,
23727
- AgentGUINode_styles_default.composerHandoffMenuContent,
23728
- "min-w-[190px]"
23729
- ),
23730
- "aria-label": effectiveHandoffMenuLabel,
23731
- children: handoffMenuTargets.map((target) => /* @__PURE__ */ jsx30(
23732
- SelectItem2,
23733
- {
23734
- value: target.targetId,
23735
- className: cn(AgentGUINode_styles_default.composerMenuItem, "gap-2"),
23736
- disabled: target.disabled === true,
23737
- children: /* @__PURE__ */ jsxs18("span", { className: "flex min-w-0 items-center gap-1.5", children: [
23738
- /* @__PURE__ */ jsx30(
23739
- "img",
23740
- {
23741
- alt: "",
23742
- "aria-hidden": "true",
23743
- className: "size-4 shrink-0 rounded-[4px]",
23744
- src: resolveComposerProviderTargetIconUrl(target)
23745
- }
23746
- ),
23747
- /* @__PURE__ */ jsx30("span", { className: "min-w-0 truncate", children: target.label })
23748
- ] })
23964
+ onHandoffConversation?.(target);
23965
+ },
23966
+ children: [
23967
+ /* @__PURE__ */ jsx30(TooltipTrigger3, { asChild: true, children: /* @__PURE__ */ jsx30(
23968
+ SelectTrigger2,
23969
+ {
23970
+ size: "sm",
23971
+ "aria-label": effectiveHandoffLabel,
23972
+ title: labels.handoffConversationTooltip,
23973
+ onBlur: () => {
23974
+ setIsHandoffIconPlaying(false);
23749
23975
  },
23750
- `${target.provider}:${target.targetId}`
23751
- ))
23752
- }
23753
- )
23754
- ]
23755
- }
23756
- ) : showProviderSelect && selectedProviderSwitchTarget ? /* @__PURE__ */ jsxs18(
23976
+ onFocus: () => {
23977
+ setIsHandoffIconPlaying(true);
23978
+ },
23979
+ onMouseEnter: () => {
23980
+ setIsHandoffIconPlaying(true);
23981
+ },
23982
+ onMouseLeave: () => {
23983
+ setIsHandoffIconPlaying(false);
23984
+ },
23985
+ className: cn(
23986
+ AgentGUINode_styles_default.composerMenuTrigger,
23987
+ AgentGUINode_styles_default.composerProviderSelect,
23988
+ AgentGUINode_styles_default.composerHandoffTrigger,
23989
+ "w-auto max-w-[180px] [&>svg:last-child]:hidden"
23990
+ ),
23991
+ children: /* @__PURE__ */ jsxs18("span", { className: "flex min-w-0 items-center gap-1.5", children: [
23992
+ /* @__PURE__ */ jsx30(
23993
+ AgentComposerHandoffIcon,
23994
+ {
23995
+ disabled: handoffDisabled,
23996
+ isPlaying: isHandoffIconPlaying
23997
+ }
23998
+ ),
23999
+ /* @__PURE__ */ jsx30("span", { className: "min-w-0 truncate", children: effectiveHandoffLabel })
24000
+ ] })
24001
+ }
24002
+ ) }),
24003
+ /* @__PURE__ */ jsx30(
24004
+ SelectContent2,
24005
+ {
24006
+ align: "start",
24007
+ className: cn(
24008
+ AgentGUINode_styles_default.composerMenuContent,
24009
+ AgentGUINode_styles_default.composerHandoffMenuContent,
24010
+ "min-w-[190px]"
24011
+ ),
24012
+ "aria-label": effectiveHandoffMenuLabel,
24013
+ children: handoffMenuTargets.map((target) => /* @__PURE__ */ jsx30(
24014
+ SelectItem2,
24015
+ {
24016
+ value: target.targetId,
24017
+ className: cn(AgentGUINode_styles_default.composerMenuItem, "gap-2"),
24018
+ disabled: target.disabled === true,
24019
+ children: /* @__PURE__ */ jsxs18("span", { className: "flex min-w-0 items-center gap-1.5", children: [
24020
+ /* @__PURE__ */ jsx30(
24021
+ "img",
24022
+ {
24023
+ alt: "",
24024
+ "aria-hidden": "true",
24025
+ className: "size-4 shrink-0 rounded-[4px]",
24026
+ src: resolveComposerProviderTargetIconUrl(
24027
+ target
24028
+ )
24029
+ }
24030
+ ),
24031
+ /* @__PURE__ */ jsx30("span", { className: "min-w-0 truncate", children: target.label })
24032
+ ] })
24033
+ },
24034
+ `${target.provider}:${target.targetId}`
24035
+ ))
24036
+ }
24037
+ )
24038
+ ]
24039
+ }
24040
+ ),
24041
+ /* @__PURE__ */ jsx30(TooltipContent3, { side: "top", children: labels.handoffConversationTooltip })
24042
+ ] }) }) : showProviderSelect && selectedProviderSwitchTarget ? /* @__PURE__ */ jsxs18(
23757
24043
  Select2,
23758
24044
  {
23759
24045
  value: selectedProviderSwitchTarget.targetId,
@@ -24912,6 +25198,7 @@ function AgentGUINodeView({
24912
25198
  isAgentProviderReady,
24913
25199
  slashStatusLimits = [],
24914
25200
  slashStatusLimitsLoading = false,
25201
+ providerAuthAccountLabels,
24915
25202
  railConfigProvider,
24916
25203
  railSlashStatusLimits,
24917
25204
  slashStatusUsageCapturedAtUnixMs = null,
@@ -25071,7 +25358,7 @@ function AgentGUINodeView({
25071
25358
  [viewModel.data.provider, viewModel.openclawGateway]
25072
25359
  );
25073
25360
  const isOpenclawGatewayBlocking = openclawGateway !== null && openclawGateway.status !== "ready";
25074
- const createConversationDisabled = viewModel.isCreatingConversation || isOpenclawGatewayBlocking;
25361
+ const createConversationDisabled = viewModel.isCreatingConversation || viewModel.selectedProviderTarget.disabled === true || isOpenclawGatewayBlocking;
25075
25362
  const createConversationAction = useStableEventCallback2(
25076
25363
  actions.createConversation
25077
25364
  );
@@ -25273,7 +25560,20 @@ function AgentGUINodeView({
25273
25560
  };
25274
25561
  const effectiveRailConfigProvider = railConfigProvider === void 0 ? viewModel.data.provider : railConfigProvider;
25275
25562
  const effectiveRailSlashStatusLimits = railSlashStatusLimits ?? slashStatusLimits;
25276
- const shouldShowProviderRailConfigMenu = viewModel.conversationFilter.kind !== "all" && viewModel.selectedProviderTarget?.disabled !== true;
25563
+ const shouldShowProviderRailConfigButton = viewModel.conversationFilter.kind === "all" || viewModel.selectedProviderTarget?.disabled !== true;
25564
+ const shouldShowProviderRailConfigMenu = shouldShowProviderRailConfigButton && viewModel.conversationFilter.kind !== "all";
25565
+ const effectiveProviderAuthAccountLabel = useMemo9(() => {
25566
+ const provider = (effectiveRailConfigProvider ?? viewModel.data.provider)?.trim() ?? "";
25567
+ if (!provider) {
25568
+ return null;
25569
+ }
25570
+ const label = providerAuthAccountLabels?.[provider]?.trim();
25571
+ return label || null;
25572
+ }, [
25573
+ effectiveRailConfigProvider,
25574
+ providerAuthAccountLabels,
25575
+ viewModel.data.provider
25576
+ ]);
25277
25577
  const enabledProviderTargets = viewModel.providerTargets.filter(
25278
25578
  (target) => target.disabled !== true && ((target.agentTargetId?.trim() ?? "") || (target.targetId?.trim() ?? ""))
25279
25579
  );
@@ -25415,12 +25715,12 @@ function AgentGUINodeView({
25415
25715
  onRequestComposerFocus: requestComposerFocus
25416
25716
  }
25417
25717
  ),
25418
- shouldShowProviderRailConfigMenu ? /* @__PURE__ */ jsx33(
25718
+ shouldShowProviderRailConfigButton ? /* @__PURE__ */ jsx33(
25419
25719
  "div",
25420
25720
  {
25421
25721
  className: `${AgentGUINode_styles_default.providerRailFooter} nodrag tsh-desktop-no-drag`,
25422
25722
  "data-testid": "agent-gui-config-footer",
25423
- children: /* @__PURE__ */ jsx33(
25723
+ children: shouldShowProviderRailConfigMenu ? /* @__PURE__ */ jsx33(
25424
25724
  AgentGUIConfigMenu,
25425
25725
  {
25426
25726
  labels,
@@ -25430,11 +25730,30 @@ function AgentGUINodeView({
25430
25730
  slashStatusUsageCapturedAtUnixMs,
25431
25731
  slashStatusUsageDidFail,
25432
25732
  slashStatusUsageAttempted,
25733
+ providerAuthAccountLabel: effectiveProviderAuthAccountLabel,
25433
25734
  onAgentConfigMenuOpen,
25434
25735
  onAgentUsageRefresh,
25435
25736
  onOpenAgentEnvSetup: openAgentEnvSetup,
25436
25737
  onOpenAgentSettings: openAgentSettings
25437
25738
  }
25739
+ ) : /* @__PURE__ */ jsx33(
25740
+ "button",
25741
+ {
25742
+ type: "button",
25743
+ "aria-label": labels.agentSettingsMenu,
25744
+ className: `${AgentGUINode_styles_default.providerRailConfigButton} nodrag tsh-desktop-no-drag`,
25745
+ title: labels.agentSettingsMenu,
25746
+ disabled: previewMode,
25747
+ onClick: openAgentSettings,
25748
+ children: /* @__PURE__ */ jsx33(
25749
+ SettingsLinedIcon,
25750
+ {
25751
+ "aria-hidden": "true",
25752
+ width: 18,
25753
+ height: 18
25754
+ }
25755
+ )
25756
+ }
25438
25757
  )
25439
25758
  }
25440
25759
  ) : null,
@@ -25658,6 +25977,8 @@ var AgentGUIDetailPane = memo(function AgentGUIDetailPane2({
25658
25977
  const timelineScrollAnchorRef = useRef12(null);
25659
25978
  const submittedPromptScrollConversationRef = useRef12(null);
25660
25979
  const pendingPrependScrollAnchorRef = useRef12(null);
25980
+ const timelineScrollPositionsRef = useRef12(/* @__PURE__ */ new Map());
25981
+ const pendingRestoreScrollRef = useRef12(null);
25661
25982
  const [isTimelineScrolledToTop, setIsTimelineScrolledToTop] = useState13(true);
25662
25983
  const [isTimelineScrolledToBottom, setIsTimelineScrolledToBottom] = useState13(true);
25663
25984
  const [
@@ -25972,6 +26293,7 @@ var AgentGUIDetailPane = memo(function AgentGUIDetailPane2({
25972
26293
  slashStatusBaseUrl: labels.slashStatusBaseUrl,
25973
26294
  slashStatusContext: labels.slashStatusContext,
25974
26295
  slashStatusLimits: labels.slashStatusLimits,
26296
+ slashStatusAccount: labels.slashStatusAccount,
25975
26297
  slashStatusClose: labels.slashStatusClose,
25976
26298
  slashStatusContextValue: labels.slashStatusContextValue,
25977
26299
  slashStatusContextUnavailable: labels.slashStatusContextUnavailable,
@@ -25988,12 +26310,14 @@ var AgentGUIDetailPane = memo(function AgentGUIDetailPane2({
25988
26310
  fileMentionEmpty: labels.fileMentionEmpty,
25989
26311
  fileMentionError: labels.fileMentionError,
25990
26312
  fileMentionTabHint: labels.fileMentionTabHint,
26313
+ fileDropHint: labels.fileDropHint,
25991
26314
  mentionPalette: labels.mentionPalette,
25992
26315
  removeMention: labels.removeMention,
25993
26316
  addReference: labels.addReference,
25994
26317
  addContent: labels.addContent,
25995
26318
  referenceWorkspaceFiles: labels.referenceWorkspaceFiles,
25996
26319
  handoffConversation: labels.handoffConversation,
26320
+ handoffConversationTooltip: labels.handoffConversationTooltip,
25997
26321
  handoffConversationMenu: labels.handoffConversationMenu,
25998
26322
  providerSwitchLabel: labels.providerSwitchLabel,
25999
26323
  projectLocked: labels.projectLocked,
@@ -26014,7 +26338,9 @@ var AgentGUIDetailPane = memo(function AgentGUIDetailPane2({
26014
26338
  labels.fileMentionLoading,
26015
26339
  labels.fileMentionPalette,
26016
26340
  labels.fileMentionTabHint,
26341
+ labels.fileDropHint,
26017
26342
  labels.handoffConversation,
26343
+ labels.handoffConversationTooltip,
26018
26344
  labels.handoffConversationMenu,
26019
26345
  labels.inheritedUnavailable,
26020
26346
  labels.loadingConversation,
@@ -26315,6 +26641,7 @@ var AgentGUIDetailPane = memo(function AgentGUIDetailPane2({
26315
26641
  isComposerSending,
26316
26642
  labels.followupPlaceholder,
26317
26643
  labels.handoffConversation,
26644
+ labels.handoffConversationTooltip,
26318
26645
  labels.handoffConversationMenu,
26319
26646
  labels.initialPlaceholder,
26320
26647
  labels.promptTips,
@@ -26348,6 +26675,7 @@ var AgentGUIDetailPane = memo(function AgentGUIDetailPane2({
26348
26675
  viewModel.activeConversationId,
26349
26676
  viewModel.availableCommands,
26350
26677
  viewModel.availableSkills,
26678
+ viewModel.activeConversationId,
26351
26679
  viewModel.compactSupported,
26352
26680
  viewModel.composerSettings,
26353
26681
  viewModel.currentUserId,
@@ -26445,13 +26773,40 @@ var AgentGUIDetailPane = memo(function AgentGUIDetailPane2({
26445
26773
  const prependAnchor = pendingPrependScrollAnchorRef.current;
26446
26774
  const shouldScrollSubmittedPromptToBottom = submittedPromptScrollConversationRef.current === activeConversationId;
26447
26775
  let nextScrollTop = timeline.scrollTop;
26776
+ const savedScrollPosition = shouldScrollSubmittedPromptToBottom ? void 0 : timelineScrollPositionsRef.current.get(activeConversationId);
26448
26777
  if (!anchor || anchor.conversationId !== activeConversationId || shouldScrollSubmittedPromptToBottom) {
26449
- setTimelineScrollTopInstantly(timeline, maxScrollTop);
26450
- nextScrollTop = maxScrollTop;
26778
+ if (savedScrollPosition && !savedScrollPosition.atBottom && !showTimelineSkeleton) {
26779
+ nextScrollTop = Math.min(maxScrollTop, savedScrollPosition.scrollTop);
26780
+ timeline.scrollTop = nextScrollTop;
26781
+ pendingRestoreScrollRef.current = null;
26782
+ } else if (savedScrollPosition && !savedScrollPosition.atBottom) {
26783
+ pendingRestoreScrollRef.current = {
26784
+ conversationId: activeConversationId,
26785
+ scrollTop: savedScrollPosition.scrollTop
26786
+ };
26787
+ setTimelineScrollTopInstantly(timeline, maxScrollTop);
26788
+ nextScrollTop = maxScrollTop;
26789
+ } else {
26790
+ setTimelineScrollTopInstantly(timeline, maxScrollTop);
26791
+ nextScrollTop = maxScrollTop;
26792
+ pendingRestoreScrollRef.current = null;
26793
+ }
26451
26794
  submittedPromptScrollConversationRef.current = null;
26452
26795
  if (shouldScrollSubmittedPromptToBottom) {
26453
26796
  pendingPrependScrollAnchorRef.current = null;
26454
26797
  }
26798
+ } else if (pendingRestoreScrollRef.current?.conversationId === activeConversationId) {
26799
+ if (showTimelineSkeleton) {
26800
+ setTimelineScrollTopInstantly(timeline, maxScrollTop);
26801
+ nextScrollTop = maxScrollTop;
26802
+ } else {
26803
+ nextScrollTop = Math.min(
26804
+ maxScrollTop,
26805
+ pendingRestoreScrollRef.current.scrollTop
26806
+ );
26807
+ timeline.scrollTop = nextScrollTop;
26808
+ pendingRestoreScrollRef.current = null;
26809
+ }
26455
26810
  } else if (prependAnchor?.conversationId === activeConversationId) {
26456
26811
  const nextScrollHeight = timeline.scrollHeight;
26457
26812
  const delta = nextScrollHeight - prependAnchor.scrollHeight;
@@ -26604,12 +26959,17 @@ var AgentGUIDetailPane = memo(function AgentGUIDetailPane2({
26604
26959
  scrollTop,
26605
26960
  clientHeight: timeline.clientHeight
26606
26961
  };
26962
+ const atBottom = timeline.scrollHeight - scrollTop - timeline.clientHeight <= AGENT_GUI_STICK_TO_BOTTOM_THRESHOLD_PX;
26607
26963
  setIsTimelineScrolledToTop(
26608
26964
  scrollTop <= AGENT_GUI_TOP_MASK_SCROLL_EPSILON_PX
26609
26965
  );
26610
- setIsTimelineScrolledToBottom(
26611
- timeline.scrollHeight - scrollTop - timeline.clientHeight <= AGENT_GUI_STICK_TO_BOTTOM_THRESHOLD_PX
26612
- );
26966
+ setIsTimelineScrolledToBottom(atBottom);
26967
+ if (pendingRestoreScrollRef.current?.conversationId !== activeConversationId) {
26968
+ timelineScrollPositionsRef.current.set(activeConversationId, {
26969
+ scrollTop,
26970
+ atBottom
26971
+ });
26972
+ }
26613
26973
  if (viewModel.hasOlderMessages && !viewModel.isLoadingOlderMessages && scrollTop <= AGENT_GUI_TOP_HISTORY_PREFETCH_THRESHOLD_PX) {
26614
26974
  pendingPrependScrollAnchorRef.current = {
26615
26975
  conversationId: activeConversationId,
@@ -26895,7 +27255,7 @@ var AgentGUIEmptyHeroPane = memo(function AgentGUIEmptyHeroPane2({
26895
27255
  const heroIconPresentations = iconPresentations.length > 0 ? iconPresentations : [agentGUIProviderIconPresentation(provider)];
26896
27256
  const heroIconAnimationKey = heroIconPresentations.map((icon) => `${icon.provider}:${icon.iconUrl}`).join("|");
26897
27257
  return /* @__PURE__ */ jsx33("div", { className: AgentGUINode_styles_default.emptyHero, children: /* @__PURE__ */ jsxs20("div", { className: AgentGUINode_styles_default.emptyHeroBody, children: [
26898
- heroIconPresentations.length > 1 ? /* @__PURE__ */ jsx33(
27258
+ /* @__PURE__ */ jsx33("div", { className: AgentGUINode_styles_default.emptyHeroIconSlot, children: heroIconPresentations.length > 1 ? /* @__PURE__ */ jsx33(
26899
27259
  AgentGUIAllProviderGridIcon,
26900
27260
  {
26901
27261
  activeProvider: provider,
@@ -26911,7 +27271,7 @@ var AgentGUIEmptyHeroPane = memo(function AgentGUIEmptyHeroPane2({
26911
27271
  icon: heroIconPresentations[0]
26912
27272
  },
26913
27273
  heroIconAnimationKey
26914
- ),
27274
+ ) }),
26915
27275
  /* @__PURE__ */ jsx33("h2", { className: AgentGUINode_styles_default.emptyHeroTitle, children: /* @__PURE__ */ jsx33(
26916
27276
  EmptyHeroTitle,
26917
27277
  {
@@ -26984,7 +27344,7 @@ var AgentGUIProviderReadinessGatePane = memo(
26984
27344
  ),
26985
27345
  /* @__PURE__ */ jsx33("h2", { className: AgentGUINode_styles_default.emptyHeroTitle, children: content.title }),
26986
27346
  /* @__PURE__ */ jsx33("p", { className: AgentGUINode_styles_default.emptyProviderGateDescription, children: content.description }),
26987
- pendingLabel ? /* @__PURE__ */ jsx33(
27347
+ pendingLabel && !action ? /* @__PURE__ */ jsx33(
26988
27348
  "div",
26989
27349
  {
26990
27350
  className: AgentGUINode_styles_default.emptyProviderGateStatus,
@@ -27726,6 +28086,13 @@ function agentGUIProviderRailLabel(provider, targetLabel, labels) {
27726
28086
  }
27727
28087
  return targetLabel;
27728
28088
  }
28089
+ function agentGUIProviderRailAriaLabel(label, badgeLabel) {
28090
+ const normalizedBadgeLabel = badgeLabel?.trim() ?? "";
28091
+ if (!normalizedBadgeLabel || normalizedBadgeLabel === label) {
28092
+ return label;
28093
+ }
28094
+ return `${label}, ${normalizedBadgeLabel}`;
28095
+ }
27729
28096
  function agentGUIProviderTargetMatchesConversationFilter(target, filter) {
27730
28097
  return filter.kind === "agentTarget" && (target.agentTargetId?.trim() ?? "") === filter.agentTargetId;
27731
28098
  }
@@ -28128,12 +28495,16 @@ var AgentGUIProviderRail = memo(function AgentGUIProviderRail2({
28128
28495
  target.label,
28129
28496
  labels
28130
28497
  );
28498
+ const ariaLabel = agentGUIProviderRailAriaLabel(
28499
+ label,
28500
+ target.badge?.label
28501
+ );
28131
28502
  const tile = /* @__PURE__ */ jsx33(
28132
28503
  "button",
28133
28504
  {
28134
28505
  type: "button",
28135
28506
  role: "tab",
28136
- "aria-label": label,
28507
+ "aria-label": ariaLabel,
28137
28508
  "aria-selected": providerSelected,
28138
28509
  className: AgentGUINode_styles_default.providerRailTile,
28139
28510
  "data-disabled": target.disabled === true ? "true" : void 0,
@@ -28148,17 +28519,28 @@ var AgentGUIProviderRail = memo(function AgentGUIProviderRail2({
28148
28519
  onDragEnd: clearProviderRailDragState,
28149
28520
  onDragOver: (event) => handleProviderRailDragOver(event, target),
28150
28521
  onDragStart: (event) => handleProviderRailDragStart(event, target),
28151
- children: /* @__PURE__ */ jsx33("span", { className: AgentGUINode_styles_default.providerRailAvatar, children: /* @__PURE__ */ jsx33(
28152
- AgentGUIProviderIconVisual,
28153
- {
28154
- ariaHidden: true,
28155
- imageClassName: AgentGUINode_styles_default.providerRailAvatarImage,
28156
- icon: agentGUIProviderRailIconPresentation(
28157
- target.provider,
28158
- target.iconUrl
28159
- )
28160
- }
28161
- ) })
28522
+ children: /* @__PURE__ */ jsxs20("span", { className: AgentGUINode_styles_default.providerRailAvatar, children: [
28523
+ /* @__PURE__ */ jsx33(
28524
+ AgentGUIProviderIconVisual,
28525
+ {
28526
+ ariaHidden: true,
28527
+ imageClassName: AgentGUINode_styles_default.providerRailAvatarImage,
28528
+ icon: agentGUIProviderRailIconPresentation(
28529
+ target.provider,
28530
+ target.iconUrl
28531
+ )
28532
+ }
28533
+ ),
28534
+ target.badge?.iconUrl ? /* @__PURE__ */ jsx33("span", { "aria-hidden": "true", className: AgentGUINode_styles_default.providerRailBadge, children: /* @__PURE__ */ jsx33(
28535
+ "img",
28536
+ {
28537
+ alt: "",
28538
+ className: AgentGUINode_styles_default.providerRailBadgeImage,
28539
+ draggable: false,
28540
+ src: target.badge.iconUrl
28541
+ }
28542
+ ) }) : null
28543
+ ] })
28162
28544
  },
28163
28545
  `${target.provider}:${target.targetId}`
28164
28546
  );
@@ -28447,6 +28829,7 @@ function AgentGUIConfigMenu({
28447
28829
  slashStatusUsageCapturedAtUnixMs,
28448
28830
  slashStatusUsageDidFail,
28449
28831
  slashStatusUsageAttempted,
28832
+ providerAuthAccountLabel,
28450
28833
  onAgentConfigMenuOpen,
28451
28834
  onAgentUsageRefresh,
28452
28835
  onOpenAgentEnvSetup,
@@ -28480,6 +28863,13 @@ function AgentGUIConfigMenu({
28480
28863
  className: "w-[300px] max-w-[calc(100vw-32px)] gap-3 p-1 text-xs",
28481
28864
  "data-testid": "agent-gui-config-menu",
28482
28865
  children: /* @__PURE__ */ jsxs20("div", { className: "flex min-w-0 flex-col gap-3", children: [
28866
+ providerAuthAccountLabel ? /* @__PURE__ */ jsxs20(Fragment9, { children: [
28867
+ /* @__PURE__ */ jsxs20("div", { className: "flex min-w-0 flex-col gap-2 p-2", children: [
28868
+ /* @__PURE__ */ jsx33("span", { className: "text-[13px] font-semibold leading-4", children: labels.slashStatusAccount }),
28869
+ /* @__PURE__ */ jsx33("span", { className: "text-[13px] leading-5 text-[var(--text-secondary)]", children: providerAuthAccountLabel })
28870
+ ] }),
28871
+ slashStatusLimits.length > 0 || slashStatusUsageAttempted || slashStatusLimitsLoading ? /* @__PURE__ */ jsx33("div", { className: "px-2", children: /* @__PURE__ */ jsx33("span", { className: "block h-px bg-[var(--border-1)]" }) }) : null
28872
+ ] }) : null,
28483
28873
  slashStatusLimits.length > 0 || slashStatusUsageAttempted || slashStatusLimitsLoading ? /* @__PURE__ */ jsxs20(Fragment9, { children: [
28484
28874
  /* @__PURE__ */ jsxs20("div", { className: "flex min-w-0 flex-col gap-2 p-2", children: [
28485
28875
  /* @__PURE__ */ jsxs20("div", { className: "flex min-w-0 items-center justify-between gap-2", children: [
@@ -29046,18 +29436,7 @@ var AgentGUIConversationRailPane = memo(
29046
29436
  }
29047
29437
  )
29048
29438
  ] }),
29049
- openclawGateway?.status === "starting" ? /* @__PURE__ */ jsxs20("div", { className: AgentGUINode_styles_default.gatewayStatus, "data-state": "starting", children: [
29050
- /* @__PURE__ */ jsx33(
29051
- StatusDot,
29052
- {
29053
- tone: "blue",
29054
- pulse: true,
29055
- size: "sm",
29056
- ariaLabel: labels.openclawGatewayStarting
29057
- }
29058
- ),
29059
- /* @__PURE__ */ jsx33("span", { children: labels.openclawGatewayStarting })
29060
- ] }) : openclawGateway?.status === "failed" ? /* @__PURE__ */ jsxs20("div", { className: AgentGUINode_styles_default.gatewayStatus, "data-state": "failed", children: [
29439
+ openclawGateway?.status === "failed" ? /* @__PURE__ */ jsxs20("div", { className: AgentGUINode_styles_default.gatewayStatus, "data-state": "failed", children: [
29061
29440
  /* @__PURE__ */ jsx33("span", { children: openclawGateway.error || labels.openclawGatewayFailed }),
29062
29441
  /* @__PURE__ */ jsx33(
29063
29442
  "button",
@@ -30601,7 +30980,7 @@ function composerOverridesByAgentTargetIdEqual(left, right) {
30601
30980
  return true;
30602
30981
  }
30603
30982
  function areAgentGUINodePropsEqual(previous, next) {
30604
- return previous.nodeId === next.nodeId && previous.workspaceId === next.workspaceId && previous.currentUserId === next.currentUserId && previous.workspacePath === next.workspacePath && previous.workspaceFileReferenceAdapter === next.workspaceFileReferenceAdapter && previous.resolveDroppedFileReferences === next.resolveDroppedFileReferences && previous.selectProjectDirectory === next.selectProjectDirectory && previous.referenceSourceAggregator === next.referenceSourceAggregator && previous.resolveWorkspaceReferenceEntryIconUrl === next.resolveWorkspaceReferenceEntryIconUrl && previous.resolveMentionReferenceTarget === next.resolveMentionReferenceTarget && previous.resolveWorkspaceReferenceInitialTarget === next.resolveWorkspaceReferenceInitialTarget && previous.onWorkspaceFileReferencesAdded === next.onWorkspaceFileReferencesAdded && previous.agentSettings.avoidGroupingEdits === next.agentSettings.avoidGroupingEdits && previous.title === next.title && agentGuiStateEquals(previous.state, next.state) && previous.position.x === next.position.x && previous.position.y === next.position.y && previous.width === next.width && previous.height === next.height && previous.desktopSize.width === next.desktopSize.width && previous.desktopSize.height === next.desktopSize.height && previous.onLinkAction === next.onLinkAction && previous.onHandoffConversation === next.onHandoffConversation && previous.onCapabilitySettingsRequest === next.onCapabilitySettingsRequest && previous.onAgentProviderLogin === next.onAgentProviderLogin && previous.accountMenuState === next.accountMenuState && previous.providerTargets === next.providerTargets && previous.providerTargetsLoading === next.providerTargetsLoading && previous.renderSidebarFooter === next.renderSidebarFooter && previous.providerRailMode === next.providerRailMode && previous.renderProviderRailEmpty === next.renderProviderRailEmpty && previous.comingSoonProviders === next.comingSoonProviders && previous.providerReadinessGates === next.providerReadinessGates && previous.defaultProviderTargetId === next.defaultProviderTargetId && previous.onClose === next.onClose && previous.onResize === next.onResize && previous.onUpdateNode === next.onUpdateNode && previous.onRememberComposerDefaults === next.onRememberComposerDefaults && previous.onOpenConversationWindow === next.onOpenConversationWindow && previous.isMaximized === next.isMaximized && previous.isMuted === next.isMuted && previous.onMinimize === next.onMinimize && previous.onToggleMaximize === next.onToggleMaximize && previous.onShowMessage === next.onShowMessage && previous.workspaceAgentProbes === next.workspaceAgentProbes && previous.onAgentProbeDemandChange === next.onAgentProbeDemandChange && previous.onAgentProbeRefreshRequest === next.onAgentProbeRefreshRequest && previous.managedAgentsState === next.managedAgentsState && previous.contextMentionProviders === next.contextMentionProviders && previous.workspaceAppIcons === next.workspaceAppIcons && previous.embedded === next.embedded && previous.previewMode === next.previewMode && previous.isActive === next.isActive && previous.composerFocusRequestSequence === next.composerFocusRequestSequence && previous.newConversationRequestSequence === next.newConversationRequestSequence && previous.openSessionRequest === next.openSessionRequest && previous.prefillPromptRequest === next.prefillPromptRequest;
30983
+ return previous.nodeId === next.nodeId && previous.workspaceId === next.workspaceId && previous.currentUserId === next.currentUserId && previous.workspacePath === next.workspacePath && previous.workspaceFileReferenceAdapter === next.workspaceFileReferenceAdapter && previous.resolveDroppedFileReferences === next.resolveDroppedFileReferences && previous.selectProjectDirectory === next.selectProjectDirectory && previous.referenceSourceAggregator === next.referenceSourceAggregator && previous.resolveWorkspaceReferenceEntryIconUrl === next.resolveWorkspaceReferenceEntryIconUrl && previous.resolveMentionReferenceTarget === next.resolveMentionReferenceTarget && previous.resolveWorkspaceReferenceInitialTarget === next.resolveWorkspaceReferenceInitialTarget && previous.onWorkspaceFileReferencesAdded === next.onWorkspaceFileReferencesAdded && previous.agentSettings.avoidGroupingEdits === next.agentSettings.avoidGroupingEdits && previous.title === next.title && agentGuiStateEquals(previous.state, next.state) && previous.position.x === next.position.x && previous.position.y === next.position.y && previous.width === next.width && previous.height === next.height && previous.desktopSize.width === next.desktopSize.width && previous.desktopSize.height === next.desktopSize.height && previous.onLinkAction === next.onLinkAction && previous.onHandoffConversation === next.onHandoffConversation && previous.onCapabilitySettingsRequest === next.onCapabilitySettingsRequest && previous.onAgentProviderLogin === next.onAgentProviderLogin && previous.accountMenuState === next.accountMenuState && previous.providerTargets === next.providerTargets && previous.providerTargetsLoading === next.providerTargetsLoading && previous.renderSidebarFooter === next.renderSidebarFooter && previous.providerRailMode === next.providerRailMode && previous.renderProviderRailEmpty === next.renderProviderRailEmpty && previous.comingSoonProviders === next.comingSoonProviders && previous.providerReadinessGates === next.providerReadinessGates && previous.defaultProviderTargetId === next.defaultProviderTargetId && previous.onClose === next.onClose && previous.onResize === next.onResize && previous.onUpdateNode === next.onUpdateNode && previous.onRememberComposerDefaults === next.onRememberComposerDefaults && previous.onOpenConversationWindow === next.onOpenConversationWindow && previous.isMaximized === next.isMaximized && previous.isMuted === next.isMuted && previous.onMinimize === next.onMinimize && previous.onToggleMaximize === next.onToggleMaximize && previous.onShowMessage === next.onShowMessage && previous.workspaceAgentProbes === next.workspaceAgentProbes && previous.onAgentProbeDemandChange === next.onAgentProbeDemandChange && previous.onAgentProbeRefreshRequest === next.onAgentProbeRefreshRequest && previous.providerAuthAccountLabels === next.providerAuthAccountLabels && previous.managedAgentsState === next.managedAgentsState && previous.contextMentionProviders === next.contextMentionProviders && previous.workspaceAppIcons === next.workspaceAppIcons && previous.embedded === next.embedded && previous.previewMode === next.previewMode && previous.isActive === next.isActive && previous.composerFocusRequestSequence === next.composerFocusRequestSequence && previous.newConversationRequestSequence === next.newConversationRequestSequence && previous.openSessionRequest === next.openSessionRequest && previous.prefillPromptRequest === next.prefillPromptRequest;
30605
30984
  }
30606
30985
  var AgentGUINode = memo2(function AgentGUINode2({
30607
30986
  nodeId,
@@ -30656,6 +31035,7 @@ var AgentGUINode = memo2(function AgentGUINode2({
30656
31035
  workspaceAgentProbes,
30657
31036
  onAgentProbeDemandChange,
30658
31037
  onAgentProbeRefreshRequest,
31038
+ providerAuthAccountLabels,
30659
31039
  managedAgentsState,
30660
31040
  contextMentionProviders,
30661
31041
  workspaceAppIcons,
@@ -31013,6 +31393,7 @@ var AgentGUINode = memo2(function AgentGUINode2({
31013
31393
  slashStatusBaseUrl: t("agentHost.agentGui.slashStatusBaseUrl"),
31014
31394
  slashStatusContext: t("agentHost.agentGui.slashStatusContext"),
31015
31395
  slashStatusLimits: t("agentHost.agentGui.slashStatusLimits"),
31396
+ slashStatusAccount: t("agentHost.agentGui.slashStatusAccount"),
31016
31397
  slashStatusClose: t("agentHost.agentGui.slashStatusClose"),
31017
31398
  slashStatusContextValue: (input) => t("agentHost.agentGui.slashStatusContextValue", {
31018
31399
  percentLeft: input.percentLeft,
@@ -31425,12 +31806,16 @@ var AgentGUINode = memo2(function AgentGUINode2({
31425
31806
  fileMentionEmpty: t("agentHost.agentGui.fileMentionEmpty"),
31426
31807
  fileMentionError: t("agentHost.agentGui.fileMentionError"),
31427
31808
  fileMentionTabHint: t("agentHost.agentGui.fileMentionTabHint"),
31809
+ fileDropHint: t("agentHost.agentGui.fileDropHint"),
31428
31810
  mentionPalette: t("agentHost.agentGui.mentionPalette"),
31429
31811
  removeMention: t("common.remove"),
31430
31812
  addReference: t("agentHost.agentGui.addReference"),
31431
31813
  addContent: t("agentHost.agentGui.addContent"),
31432
31814
  referenceWorkspaceFiles: t("agentHost.issue.referenceWorkspaceFiles"),
31433
31815
  handoffConversation: t("agentHost.agentGui.handoffConversation"),
31816
+ handoffConversationTooltip: t(
31817
+ "agentHost.agentGui.handoffConversationTooltip"
31818
+ ),
31434
31819
  handoffConversationMenu: t("agentHost.agentGui.handoffConversationMenu")
31435
31820
  }),
31436
31821
  [displayProviderLabel, fallbackAgentTitle, t]
@@ -31666,6 +32051,7 @@ var AgentGUINode = memo2(function AgentGUINode2({
31666
32051
  slashStatusUsageCapturedAtUnixMs,
31667
32052
  slashStatusUsageDidFail,
31668
32053
  slashStatusUsageAttempted,
32054
+ providerAuthAccountLabels,
31669
32055
  onAgentConfigMenuOpen: handleAgentConfigMenuOpen,
31670
32056
  onAgentUsageRefresh: handleAgentUsageRefresh,
31671
32057
  previewMode,