@parhelia/core 0.1.12749 → 0.1.12752

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 (101) hide show
  1. package/dist/agents-view/AgentsView.js +1 -1
  2. package/dist/agents-view/AgentsView.js.map +1 -1
  3. package/dist/agents-view/AgentsWorkspaceView.js +41 -21
  4. package/dist/agents-view/AgentsWorkspaceView.js.map +1 -1
  5. package/dist/components/ui/PlaceholderInput.js +3 -3
  6. package/dist/components/ui/PlaceholderInput.js.map +1 -1
  7. package/dist/components/ui/PlaceholderInputTypes.js +2 -2
  8. package/dist/components/ui/PlaceholderInputTypes.js.map +1 -1
  9. package/dist/components/ui/PlaceholderItemSelector.js +2 -2
  10. package/dist/components/ui/PlaceholderItemSelector.js.map +1 -1
  11. package/dist/editor/LinkEditorDialog.js +2 -2
  12. package/dist/editor/LinkEditorDialog.js.map +1 -1
  13. package/dist/editor/ai/AgentBanners.d.ts +11 -0
  14. package/dist/editor/ai/AgentBanners.js +16 -0
  15. package/dist/editor/ai/AgentBanners.js.map +1 -0
  16. package/dist/editor/ai/AgentCostDisplay.d.ts +12 -0
  17. package/dist/editor/ai/AgentCostDisplay.js +24 -1
  18. package/dist/editor/ai/AgentCostDisplay.js.map +1 -1
  19. package/dist/editor/ai/AgentDocumentList.js +5 -4
  20. package/dist/editor/ai/AgentDocumentList.js.map +1 -1
  21. package/dist/editor/ai/AgentInlineDialogContent.d.ts +17 -0
  22. package/dist/editor/ai/AgentInlineDialogContent.js +32 -0
  23. package/dist/editor/ai/AgentInlineDialogContent.js.map +1 -0
  24. package/dist/editor/ai/AgentSharingSection.d.ts +6 -0
  25. package/dist/editor/ai/AgentSharingSection.js +149 -0
  26. package/dist/editor/ai/AgentSharingSection.js.map +1 -0
  27. package/dist/editor/ai/AgentTerminal.d.ts +2 -1
  28. package/dist/editor/ai/AgentTerminal.js +278 -969
  29. package/dist/editor/ai/AgentTerminal.js.map +1 -1
  30. package/dist/editor/ai/AgentTerminalStatusBar.d.ts +18 -0
  31. package/dist/editor/ai/AgentTerminalStatusBar.js +431 -126
  32. package/dist/editor/ai/AgentTerminalStatusBar.js.map +1 -1
  33. package/dist/editor/ai/Agents.js +1 -1
  34. package/dist/editor/ai/Agents.js.map +1 -1
  35. package/dist/editor/ai/HeartbeatMessage.d.ts +4 -0
  36. package/dist/editor/ai/HeartbeatMessage.js +7 -0
  37. package/dist/editor/ai/HeartbeatMessage.js.map +1 -0
  38. package/dist/editor/ai/InitialThinkingSplash.d.ts +3 -0
  39. package/dist/editor/ai/InitialThinkingSplash.js +9 -0
  40. package/dist/editor/ai/InitialThinkingSplash.js.map +1 -0
  41. package/dist/editor/ai/InlineAiDialog.js +49 -1
  42. package/dist/editor/ai/InlineAiDialog.js.map +1 -1
  43. package/dist/editor/ai/QueuedPromptsPanel.d.ts +4 -0
  44. package/dist/editor/ai/QueuedPromptsPanel.js +36 -0
  45. package/dist/editor/ai/QueuedPromptsPanel.js.map +1 -0
  46. package/dist/editor/ai/TodoListPanel.d.ts +5 -0
  47. package/dist/editor/ai/TodoListPanel.js +113 -0
  48. package/dist/editor/ai/TodoListPanel.js.map +1 -0
  49. package/dist/editor/ai/ToolCallDisplay.js +54 -10
  50. package/dist/editor/ai/ToolCallDisplay.js.map +1 -1
  51. package/dist/editor/ai/UserMessage.d.ts +4 -0
  52. package/dist/editor/ai/UserMessage.js +42 -0
  53. package/dist/editor/ai/UserMessage.js.map +1 -0
  54. package/dist/editor/ai/agentMessageConversion.d.ts +11 -0
  55. package/dist/editor/ai/agentMessageConversion.js +134 -0
  56. package/dist/editor/ai/agentMessageConversion.js.map +1 -0
  57. package/dist/editor/ai/agentMessageGrouping.d.ts +22 -0
  58. package/dist/editor/ai/agentMessageGrouping.js +103 -0
  59. package/dist/editor/ai/agentMessageGrouping.js.map +1 -0
  60. package/dist/editor/ai/agentMessageHelpers.d.ts +23 -0
  61. package/dist/editor/ai/agentMessageHelpers.js +124 -0
  62. package/dist/editor/ai/agentMessageHelpers.js.map +1 -0
  63. package/dist/editor/ai/agentMessageMarkdown.d.ts +2 -0
  64. package/dist/editor/ai/agentMessageMarkdown.js +14 -0
  65. package/dist/editor/ai/agentMessageMarkdown.js.map +1 -0
  66. package/dist/editor/ai/agentTodoExtraction.d.ts +12 -0
  67. package/dist/editor/ai/agentTodoExtraction.js +205 -0
  68. package/dist/editor/ai/agentTodoExtraction.js.map +1 -0
  69. package/dist/editor/client/editContext.d.ts +1 -0
  70. package/dist/editor/client/editContext.js.map +1 -1
  71. package/dist/editor/client/operations.d.ts +3 -1
  72. package/dist/editor/client/operations.js +20 -2
  73. package/dist/editor/client/operations.js.map +1 -1
  74. package/dist/editor/menubar/VersionPreviewCard.js +34 -3
  75. package/dist/editor/menubar/VersionPreviewCard.js.map +1 -1
  76. package/dist/editor/menubar/toolbar-sections/ViewportControls.js +2 -2
  77. package/dist/editor/menubar/toolbar-sections/ViewportControls.js.map +1 -1
  78. package/dist/editor/reviews/SuggestedEdit.js +65 -48
  79. package/dist/editor/reviews/SuggestedEdit.js.map +1 -1
  80. package/dist/editor/reviews/SuggestionDisplayPopover.js +5 -1
  81. package/dist/editor/reviews/SuggestionDisplayPopover.js.map +1 -1
  82. package/dist/editor/services/agentService.d.ts +24 -0
  83. package/dist/editor/services/agentService.js +40 -0
  84. package/dist/editor/services/agentService.js.map +1 -1
  85. package/dist/editor/services/aiService.d.ts +10 -0
  86. package/dist/editor/services/aiService.js.map +1 -1
  87. package/dist/editor/settings/panels/AgentProfileConfigPanel.js +1 -1
  88. package/dist/editor/settings/panels/AgentProfileConfigPanel.js.map +1 -1
  89. package/dist/revision.d.ts +2 -2
  90. package/dist/revision.js +2 -2
  91. package/dist/task-board/TaskBoardWorkspace.js +57 -26
  92. package/dist/task-board/TaskBoardWorkspace.js.map +1 -1
  93. package/dist/task-board/components/ProjectDashboard.js +2 -3
  94. package/dist/task-board/components/ProjectDashboard.js.map +1 -1
  95. package/dist/task-board/components/TaskBoardTitlebar.js +2 -1
  96. package/dist/task-board/components/TaskBoardTitlebar.js.map +1 -1
  97. package/dist/task-board/components/TaskDetailPanel.d.ts +8 -0
  98. package/dist/task-board/components/TaskDetailPanel.js +5 -3
  99. package/dist/task-board/components/TaskDetailPanel.js.map +1 -1
  100. package/package.json +1 -1
  101. package/styles.css +11 -10
@@ -3,7 +3,7 @@ import { useEffect, useMemo, useState } from "react";
3
3
  import { Bug } from "lucide-react";
4
4
  import { Popover, PopoverContent, PopoverTrigger, } from "../../components/ui/popover";
5
5
  import { Tooltip, TooltipContent, TooltipTrigger, } from "../../components/ui/tooltip";
6
- import { getAgentDiagnostics, getLastPayload, } from "../services/agentService";
6
+ import { getAgentDiagnostics, getAgentOperationAllowances, getLastPayload, } from "../services/agentService";
7
7
  import { AgentCostDisplay } from "./AgentCostDisplay";
8
8
  import { ContentInspectorPopover, } from "./ContentInspectorPopover";
9
9
  import { formatAgentDiagnosticsEvent, formatSeqRanges, interpretAgentRunDiagnostics, } from "./agentDiagnostics";
@@ -19,6 +19,12 @@ function yesNo(value) {
19
19
  function lines(values) {
20
20
  return values.filter(Boolean).join("\n");
21
21
  }
22
+ function joinSubsections(subsections) {
23
+ return subsections
24
+ .map((s) => (s && s.content ? `── ${s.title} ──\n${s.content}` : null))
25
+ .filter((v) => Boolean(v))
26
+ .join("\n\n");
27
+ }
22
28
  const CLIENT_SOCKET_RAW_MESSAGE_MAX_LENGTH = 10_000;
23
29
  function formatClientSocketMessageEvent(event) {
24
30
  const header = formatAgentDiagnosticsEvent(event);
@@ -118,6 +124,39 @@ function joinExtractedText(value) {
118
124
  .trim();
119
125
  return text.length > 0 ? text : null;
120
126
  }
127
+ const LARGE_STRING_TRUNCATE_THRESHOLD = 300;
128
+ const LARGE_STRING_HEAD_TAIL_BYTES = 100;
129
+ function truncateLargeStrings(value) {
130
+ if (typeof value === "string") {
131
+ if (value.length > LARGE_STRING_TRUNCATE_THRESHOLD) {
132
+ return `${value.slice(0, LARGE_STRING_HEAD_TAIL_BYTES)}...${value.slice(-LARGE_STRING_HEAD_TAIL_BYTES)}`;
133
+ }
134
+ return value;
135
+ }
136
+ if (Array.isArray(value)) {
137
+ return value.map(truncateLargeStrings);
138
+ }
139
+ if (value && typeof value === "object") {
140
+ const result = {};
141
+ for (const [key, entry] of Object.entries(value)) {
142
+ result[key] = truncateLargeStrings(entry);
143
+ }
144
+ return result;
145
+ }
146
+ return value;
147
+ }
148
+ function stripLargeDocumentsFromPayload(payload) {
149
+ try {
150
+ const parsed = JSON.parse(payload);
151
+ return JSON.stringify(truncateLargeStrings(parsed), null, 2);
152
+ }
153
+ catch {
154
+ if (payload.length > LARGE_STRING_TRUNCATE_THRESHOLD) {
155
+ return `${payload.slice(0, LARGE_STRING_HEAD_TAIL_BYTES)}...${payload.slice(-LARGE_STRING_HEAD_TAIL_BYTES)}`;
156
+ }
157
+ return payload;
158
+ }
159
+ }
121
160
  function extractLastPromptFromPayload(payload) {
122
161
  const normalizedPayload = normalizeInspectorText(payload);
123
162
  if (!normalizedPayload)
@@ -267,8 +306,224 @@ function buildPersistentLogsSection(persistentLogs) {
267
306
  : undefined,
268
307
  };
269
308
  }
309
+ function formatNumber(value) {
310
+ if (value == null || !Number.isFinite(value))
311
+ return "—";
312
+ return value.toLocaleString();
313
+ }
314
+ function formatCost(value, currency) {
315
+ if (value == null || !Number.isFinite(value))
316
+ return "—";
317
+ return `${value.toFixed(4)} ${currency}`;
318
+ }
319
+ function formatPercent(value) {
320
+ if (value == null || !Number.isFinite(value))
321
+ return "—";
322
+ return `${value.toFixed(1)}%`;
323
+ }
324
+ function buildAgentSection(agent, resolvedModelName) {
325
+ if (!agent) {
326
+ return {
327
+ title: "Agent",
328
+ content: "Agent details are not available.",
329
+ };
330
+ }
331
+ return {
332
+ title: "Agent",
333
+ content: lines([
334
+ `Name: ${agent.name || "—"}`,
335
+ `ID: ${agent.id}`,
336
+ `Status: ${agent.status || "—"}`,
337
+ agent.statusMessage ? `Status message: ${agent.statusMessage}` : null,
338
+ `Profile: ${agent.profileName || "—"}${agent.profileId ? ` (${agent.profileId})` : ""}`,
339
+ `Model: ${resolvedModelName || agent.model || "—"}`,
340
+ `Owner: ${agent.ownerName || agent.userId || "—"}`,
341
+ agent.visibilityMode ? `Visibility: ${agent.visibilityMode}` : null,
342
+ agent.effectiveAccessLevel
343
+ ? `Access level: ${agent.effectiveAccessLevel}`
344
+ : null,
345
+ agent.parentAgentId ? `Parent agent: ${agent.parentAgentId}` : null,
346
+ `Created: ${formatDiagnosticTime(agent.createdDate)}`,
347
+ `Updated: ${formatDiagnosticTime(agent.updatedDate)}`,
348
+ `Last message: ${formatDiagnosticTime(agent.lastMessageDate)}`,
349
+ agent.nextRunAt
350
+ ? `Next scheduled run: ${formatDiagnosticTime(agent.nextRunAt)}`
351
+ : null,
352
+ `Messages in conversation: ${agent.messageCount ?? 0}`,
353
+ agent.compressionMarkerIndex != null
354
+ ? `Compression marker index: ${agent.compressionMarkerIndex}`
355
+ : null,
356
+ agent.triggerSubscriptionCount != null
357
+ ? `Trigger subscriptions: ${agent.triggerSubscriptionCount}`
358
+ : null,
359
+ agent.assignedSkillIds && agent.assignedSkillIds.length > 0
360
+ ? `Assigned skills (${agent.assignedSkillIds.length}): ${agent.assignedSkillIds.join(", ")}`
361
+ : `Assigned skills: none`,
362
+ ]),
363
+ };
364
+ }
365
+ function buildTokensSection(params) {
366
+ const { agent, liveTotals, totalTokens, contextWindowStatus, costLimit, resolvedModelName, } = params;
367
+ const currency = liveTotals?.currency || agent?.currency || "USD";
368
+ const breakdown = liveTotals ?? totalTokens;
369
+ const totalCost = breakdown?.totalCost ?? agent?.totalCost ?? 0;
370
+ const limitPercent = costLimit && costLimit > 0 ? (totalCost / costLimit) * 100 : null;
371
+ const liveSection = breakdown
372
+ ? joinSubsections([
373
+ {
374
+ title: "Current run / live totals",
375
+ content: lines([
376
+ `Input tokens: ${formatNumber(breakdown.input)} (${formatCost(breakdown.inputCost, currency)})`,
377
+ `Output tokens: ${formatNumber(breakdown.output)} (${formatCost(breakdown.outputCost, currency)})`,
378
+ `Cached input tokens: ${formatNumber(breakdown.cached)} (${formatCost(breakdown.cachedCost, currency)})`,
379
+ breakdown.cacheWrite || breakdown.cacheWriteCost
380
+ ? `Cache write tokens: ${formatNumber(breakdown.cacheWrite ?? 0)} (${formatCost(breakdown.cacheWriteCost ?? 0, currency)})`
381
+ : null,
382
+ breakdown.reasoning
383
+ ? `Reasoning tokens: ${formatNumber(breakdown.reasoning)}`
384
+ : null,
385
+ breakdown.inputAudio || breakdown.inputAudioCost
386
+ ? `Input audio tokens: ${formatNumber(breakdown.inputAudio ?? 0)} (${formatCost(breakdown.inputAudioCost ?? 0, currency)})`
387
+ : null,
388
+ breakdown.outputAudio || breakdown.outputAudioCost
389
+ ? `Output audio tokens: ${formatNumber(breakdown.outputAudio ?? 0)} (${formatCost(breakdown.outputAudioCost ?? 0, currency)})`
390
+ : null,
391
+ breakdown.outputImage || breakdown.outputImageCost
392
+ ? `Output image tokens: ${formatNumber(breakdown.outputImage ?? 0)} (${formatCost(breakdown.outputImageCost ?? 0, currency)})`
393
+ : null,
394
+ breakdown.imageCost
395
+ ? `Image cost: ${formatCost(breakdown.imageCost, currency)}`
396
+ : null,
397
+ "markupCost" in breakdown && breakdown.markupCost
398
+ ? `Provider markup: ${formatCost(breakdown.markupCost, currency)}`
399
+ : null,
400
+ "reportedTotalCost" in breakdown &&
401
+ breakdown.reportedTotalCost != null
402
+ ? `Provider-reported total: ${formatCost(breakdown.reportedTotalCost, currency)}`
403
+ : null,
404
+ ]),
405
+ },
406
+ ])
407
+ : "No token usage has been recorded for the current run yet.";
408
+ const cumulativeSection = agent
409
+ ? joinSubsections([
410
+ {
411
+ title: "Cumulative (entire conversation)",
412
+ content: lines([
413
+ `Total tokens used: ${formatNumber(agent.totalTokensUsed)}`,
414
+ `Input tokens: ${formatNumber(agent.totalInputTokens)} (${formatCost(agent.totalInputTokenCost, currency)})`,
415
+ `Output tokens: ${formatNumber(agent.totalOutputTokens)} (${formatCost(agent.totalOutputTokenCost, currency)})`,
416
+ `Cached input tokens: ${formatNumber(agent.totalCachedInputTokens)} (${formatCost(agent.totalCachedInputTokenCost, currency)})`,
417
+ agent.totalImageCost
418
+ ? `Image cost: ${formatCost(agent.totalImageCost, currency)}`
419
+ : null,
420
+ `Total cost: ${formatCost(agent.totalCost, currency)}`,
421
+ ]),
422
+ },
423
+ ])
424
+ : "";
425
+ const limitSection = joinSubsections([
426
+ {
427
+ title: "Cost limit",
428
+ content: lines([
429
+ `Cost limit: ${costLimit != null && costLimit > 0 ? formatCost(costLimit, currency) : "Unlimited"}`,
430
+ limitPercent != null
431
+ ? `Used: ${formatCost(totalCost, currency)} (${formatPercent(limitPercent)})`
432
+ : `Used: ${formatCost(totalCost, currency)}`,
433
+ ]),
434
+ },
435
+ ]);
436
+ const contextSection = contextWindowStatus
437
+ ? joinSubsections([
438
+ {
439
+ title: "Context window",
440
+ content: lines([
441
+ resolvedModelName ? `Model: ${resolvedModelName}` : null,
442
+ `Window size: ${formatNumber(contextWindowStatus.contextWindowTokens)} tokens`,
443
+ `Estimated input tokens: ${formatNumber(contextWindowStatus.estimatedInputTokens)}`,
444
+ `Used: ${formatPercent(contextWindowStatus.contextUsedPercent)}`,
445
+ agent?.contextUsedTokens != null
446
+ ? `Persisted context tokens: ${formatNumber(agent.contextUsedTokens)}`
447
+ : null,
448
+ agent?.contextWindowTokens != null
449
+ ? `Persisted window size: ${formatNumber(agent.contextWindowTokens)}`
450
+ : null,
451
+ ]),
452
+ },
453
+ ])
454
+ : agent?.contextUsedTokens != null || agent?.contextWindowTokens != null
455
+ ? joinSubsections([
456
+ {
457
+ title: "Context window",
458
+ content: lines([
459
+ resolvedModelName ? `Model: ${resolvedModelName}` : null,
460
+ agent?.contextWindowTokens != null
461
+ ? `Window size: ${formatNumber(agent.contextWindowTokens)} tokens`
462
+ : null,
463
+ agent?.contextUsedTokens != null
464
+ ? `Used tokens: ${formatNumber(agent.contextUsedTokens)}`
465
+ : null,
466
+ ]),
467
+ },
468
+ ])
469
+ : "";
470
+ const content = [liveSection, cumulativeSection, limitSection, contextSection]
471
+ .filter((s) => s && s.length > 0)
472
+ .join("\n\n");
473
+ return {
474
+ title: "Tokens & cost",
475
+ content: content || "No token or cost information is available yet.",
476
+ };
477
+ }
478
+ function buildAllowancesSection(allowances) {
479
+ if (!allowances) {
480
+ return {
481
+ title: "Allowances",
482
+ content: "Operation allowances could not be loaded.",
483
+ };
484
+ }
485
+ const sitecore = allowances.sitecore ?? [];
486
+ const filesystem = allowances.filesystem ?? [];
487
+ const sitecoreBlock = sitecore.length > 0
488
+ ? sitecore
489
+ .map((a) => lines([
490
+ `• ${a.itemPath}`,
491
+ ` ID: ${a.itemId}`,
492
+ ` Operation: ${a.operationType}`,
493
+ ` Scope: ${a.scopeType}`,
494
+ a.source ? ` Source: ${a.source}` : null,
495
+ a.grantedBy ? ` Granted by: ${a.grantedBy}` : null,
496
+ a.grantedAt ? ` Granted at: ${formatDiagnosticTime(a.grantedAt)}` : null,
497
+ ]))
498
+ .join("\n")
499
+ : "No Sitecore item allowances granted.";
500
+ const filesystemBlock = filesystem.length > 0
501
+ ? filesystem
502
+ .map((a) => lines([
503
+ `• ${a.normalizedPath}`,
504
+ ` Operation: ${a.operationType}`,
505
+ a.source ? ` Source: ${a.source}` : null,
506
+ a.grantedBy ? ` Granted by: ${a.grantedBy}` : null,
507
+ a.grantedAt ? ` Granted at: ${formatDiagnosticTime(a.grantedAt)}` : null,
508
+ ]))
509
+ .join("\n")
510
+ : "No filesystem allowances granted.";
511
+ return {
512
+ title: `Allowances (${sitecore.length + filesystem.length})`,
513
+ content: joinSubsections([
514
+ {
515
+ title: `Sitecore items (${sitecore.length})`,
516
+ content: sitecoreBlock,
517
+ },
518
+ {
519
+ title: `Filesystem paths (${filesystem.length})`,
520
+ content: filesystemBlock,
521
+ },
522
+ ]),
523
+ };
524
+ }
270
525
  function buildDiagnosticsSections(params) {
271
- const { socketDiagnostics, runDiagnosticsSnapshot, serverDiagnostics, messages, payload, rawResponse, } = params;
526
+ const { agent, socketDiagnostics, runDiagnosticsSnapshot, serverDiagnostics, allowances, liveTotals, totalTokens, contextWindowStatus, costLimit, resolvedModelName = "", messages, payload, rawResponse, } = params;
272
527
  const summary = interpretAgentRunDiagnostics({
273
528
  socketDiagnostics,
274
529
  localSnapshot: runDiagnosticsSnapshot,
@@ -279,19 +534,7 @@ function buildDiagnosticsSections(params) {
279
534
  const lastResponse = extractLastResponseFromRawResponse(rawResponse) ||
280
535
  extractLastMessageByRole(messages, "assistant");
281
536
  const machineCapacitySection = buildMachineCapacitySection(params.agentId, serverDiagnostics);
282
- const sections = [
283
- {
284
- title: "Summary",
285
- content: lines([
286
- `Diagnosis: ${summary.title}`,
287
- summary.detail,
288
- `Socket: ${socketDiagnostics.readyStateLabel}`,
289
- `Session connected: ${yesNo(serverDiagnostics.currentSession.isConnected)}`,
290
- `Session subscribed: ${yesNo(serverDiagnostics.currentSession.isSubscribed)}`,
291
- `Server status: ${serverDiagnostics.execution.status || "unknown"}`,
292
- `Last seq: ${serverDiagnostics.transport.lastSeq ?? runDiagnosticsSnapshot.lastSeq ?? "—"}`,
293
- ]),
294
- },
537
+ const connectionContent = joinSubsections([
295
538
  {
296
539
  title: "Client connection",
297
540
  content: lines([
@@ -315,7 +558,31 @@ function buildDiagnosticsSections(params) {
315
558
  ]),
316
559
  },
317
560
  {
318
- title: "Agent stream",
561
+ title: "Current session",
562
+ content: lines([
563
+ `Session found: ${yesNo(serverDiagnostics.currentSession.sessionFound)}`,
564
+ `Browser matched: ${yesNo(serverDiagnostics.currentSession.browserMatched)}`,
565
+ `Connected: ${yesNo(serverDiagnostics.currentSession.isConnected)}`,
566
+ `Subscribed: ${yesNo(serverDiagnostics.currentSession.isSubscribed)}`,
567
+ `Connected at: ${formatDiagnosticTime(serverDiagnostics.currentSession.connectedAt)}`,
568
+ `Last delivery attempt: ${formatDiagnosticTime(serverDiagnostics.currentSession.lastDelivery?.lastAttemptAt)}`,
569
+ `Last delivery success: ${formatDiagnosticTime(serverDiagnostics.currentSession.lastDelivery?.lastSuccessAt)}`,
570
+ `Last delivery failure: ${formatDiagnosticTime(serverDiagnostics.currentSession.lastDelivery?.lastFailureAt)}`,
571
+ serverDiagnostics.currentSession.lastDelivery?.lastFailureReason
572
+ ? `Failure reason: ${serverDiagnostics.currentSession.lastDelivery.lastFailureReason}`
573
+ : null,
574
+ serverDiagnostics.currentSession.lastDelivery?.lastMessageType
575
+ ? `Last delivered message: ${serverDiagnostics.currentSession.lastDelivery.lastMessageType}`
576
+ : null,
577
+ serverDiagnostics.currentSession.lastDelivery?.lastSeq != null
578
+ ? `Last delivered seq: ${serverDiagnostics.currentSession.lastDelivery.lastSeq}`
579
+ : null,
580
+ ]),
581
+ },
582
+ ]);
583
+ const runContent = joinSubsections([
584
+ {
585
+ title: "Agent stream (client)",
319
586
  content: lines([
320
587
  `Submitting: ${yesNo(runDiagnosticsSnapshot.isSubmitting)}`,
321
588
  `Connecting: ${yesNo(runDiagnosticsSnapshot.isConnecting)}`,
@@ -340,17 +607,6 @@ function buildDiagnosticsSections(params) {
340
607
  `Last local event: ${runDiagnosticsSnapshot.lastEventType || "—"} @ ${formatDiagnosticTime(runDiagnosticsSnapshot.lastEventAt)}`,
341
608
  ]),
342
609
  },
343
- {
344
- title: "Tool UI state",
345
- content: lines([
346
- `Assistant messages: ${runDiagnosticsSnapshot.assistantMessageCount}`,
347
- `Assistant groups: ${runDiagnosticsSnapshot.assistantGroupCount}`,
348
- `Groups with renderable tool calls: ${runDiagnosticsSnapshot.assistantGroupsWithRenderableToolCalls}`,
349
- `Messages with tool calls: ${runDiagnosticsSnapshot.messagesWithToolCalls}`,
350
- `Total tool calls in local state: ${runDiagnosticsSnapshot.totalToolCallCount}`,
351
- `Incomplete tool calls in local state: ${runDiagnosticsSnapshot.incompleteToolCallCount}`,
352
- ]),
353
- },
354
610
  {
355
611
  title: "Server execution",
356
612
  content: lines([
@@ -376,8 +632,6 @@ function buildDiagnosticsSections(params) {
376
632
  : null,
377
633
  ]),
378
634
  },
379
- ...(machineCapacitySection ? [machineCapacitySection] : []),
380
- buildPersistentLogsSection(serverDiagnostics.persistentLogs ?? []),
381
635
  {
382
636
  title: "Run telemetry",
383
637
  content: lines([
@@ -405,112 +659,152 @@ function buildDiagnosticsSections(params) {
405
659
  ]),
406
660
  },
407
661
  {
408
- title: "Current session",
662
+ title: "Tool UI state",
409
663
  content: lines([
410
- `Session found: ${yesNo(serverDiagnostics.currentSession.sessionFound)}`,
411
- `Browser matched: ${yesNo(serverDiagnostics.currentSession.browserMatched)}`,
412
- `Connected: ${yesNo(serverDiagnostics.currentSession.isConnected)}`,
413
- `Subscribed: ${yesNo(serverDiagnostics.currentSession.isSubscribed)}`,
414
- `Connected at: ${formatDiagnosticTime(serverDiagnostics.currentSession.connectedAt)}`,
415
- `Last delivery attempt: ${formatDiagnosticTime(serverDiagnostics.currentSession.lastDelivery?.lastAttemptAt)}`,
416
- `Last delivery success: ${formatDiagnosticTime(serverDiagnostics.currentSession.lastDelivery?.lastSuccessAt)}`,
417
- `Last delivery failure: ${formatDiagnosticTime(serverDiagnostics.currentSession.lastDelivery?.lastFailureAt)}`,
418
- serverDiagnostics.currentSession.lastDelivery?.lastFailureReason
419
- ? `Failure reason: ${serverDiagnostics.currentSession.lastDelivery.lastFailureReason}`
420
- : null,
421
- serverDiagnostics.currentSession.lastDelivery?.lastMessageType
422
- ? `Last delivered message: ${serverDiagnostics.currentSession.lastDelivery.lastMessageType}`
423
- : null,
424
- serverDiagnostics.currentSession.lastDelivery?.lastSeq != null
425
- ? `Last delivered seq: ${serverDiagnostics.currentSession.lastDelivery.lastSeq}`
426
- : null,
664
+ `Assistant messages: ${runDiagnosticsSnapshot.assistantMessageCount}`,
665
+ `Assistant groups: ${runDiagnosticsSnapshot.assistantGroupCount}`,
666
+ `Groups with renderable tool calls: ${runDiagnosticsSnapshot.assistantGroupsWithRenderableToolCalls}`,
667
+ `Messages with tool calls: ${runDiagnosticsSnapshot.messagesWithToolCalls}`,
668
+ `Total tool calls in local state: ${runDiagnosticsSnapshot.totalToolCallCount}`,
669
+ `Incomplete tool calls in local state: ${runDiagnosticsSnapshot.incompleteToolCallCount}`,
427
670
  ]),
428
671
  },
672
+ ]);
673
+ const clientEventsBlock = (() => {
674
+ const events = runDiagnosticsSnapshot.recentEvents;
675
+ if (events.length === 0) {
676
+ return "No recent client-side agent stream events were captured for this terminal.";
677
+ }
678
+ const total = runDiagnosticsSnapshot.currentRunTotalEventCount;
679
+ const header = total > events.length
680
+ ? `Showing last ${events.length} of ${total} agent:run:* events received in current run.`
681
+ : `Showing all ${events.length} agent:run:* events received in current run.`;
682
+ const body = events
683
+ .slice()
684
+ .reverse()
685
+ .map((event) => formatAgentDiagnosticsEvent(event))
686
+ .join("\n");
687
+ return `${header}\n${body}`;
688
+ })();
689
+ const clientWebSocketBlock = (() => {
690
+ const events = runDiagnosticsSnapshot.recentEvents;
691
+ if (events.length === 0) {
692
+ return "No raw client-side agent WebSocket messages were captured for this terminal.";
693
+ }
694
+ const total = runDiagnosticsSnapshot.currentRunTotalEventCount;
695
+ const header = total > events.length
696
+ ? `Showing last ${events.length} of ${total} agent:run:* messages received in current run.`
697
+ : `Showing all ${events.length} agent:run:* messages received in current run.`;
698
+ const body = events
699
+ .slice()
700
+ .reverse()
701
+ .map((event) => formatClientSocketMessageEvent(event))
702
+ .join("\n\n");
703
+ return `${header}\n\n${body}`;
704
+ })();
705
+ const toolUiEventsBlock = runDiagnosticsSnapshot.recentToolUiEvents.length > 0
706
+ ? runDiagnosticsSnapshot.recentToolUiEvents
707
+ .slice()
708
+ .reverse()
709
+ .map((event) => formatAgentDiagnosticsEvent(event))
710
+ .join("\n")
711
+ : "No recent tool-specific UI events were captured for this terminal.";
712
+ const serverEventsBlock = serverDiagnostics.transport.recentEvents.length > 0
713
+ ? serverDiagnostics.transport.recentEvents
714
+ .map((event) => formatAgentDiagnosticsEvent(event))
715
+ .join("\n")
716
+ : "No recent server-side agent transport events were recorded.";
717
+ const eventsContent = joinSubsections([
718
+ { title: "Client events", content: clientEventsBlock },
719
+ { title: "Server events", content: serverEventsBlock },
720
+ { title: "Tool UI events", content: toolUiEventsBlock },
721
+ { title: "Client WebSocket messages (raw)", content: clientWebSocketBlock },
722
+ ]);
723
+ const promptContent = joinSubsections([
429
724
  {
430
- title: "Recent client events",
431
- content: (() => {
432
- const events = runDiagnosticsSnapshot.recentEvents;
433
- if (events.length === 0) {
434
- return "No recent client-side agent stream events were captured for this terminal.";
435
- }
436
- const total = runDiagnosticsSnapshot.currentRunTotalEventCount;
437
- const header = total > events.length
438
- ? `Showing last ${events.length} of ${total} agent:run:* events received in current run.`
439
- : `Showing all ${events.length} agent:run:* events received in current run.`;
440
- const body = events
441
- .slice()
442
- .reverse()
443
- .map((event) => formatAgentDiagnosticsEvent(event))
444
- .join("\n");
445
- return `${header}\n${body}`;
446
- })(),
447
- },
448
- {
449
- title: "Recent client WebSocket messages",
450
- content: (() => {
451
- const events = runDiagnosticsSnapshot.recentEvents;
452
- if (events.length === 0) {
453
- return "No raw client-side agent WebSocket messages were captured for this terminal.";
454
- }
455
- const total = runDiagnosticsSnapshot.currentRunTotalEventCount;
456
- const header = total > events.length
457
- ? `Showing last ${events.length} of ${total} agent:run:* messages received in current run.`
458
- : `Showing all ${events.length} agent:run:* messages received in current run.`;
459
- const body = events
460
- .slice()
461
- .reverse()
462
- .map((event) => formatClientSocketMessageEvent(event))
463
- .join("\n\n");
464
- return `${header}\n\n${body}`;
465
- })(),
725
+ title: "Last prompt",
726
+ content: lastPrompt ?? "No prompt was captured for this agent run yet.",
466
727
  },
728
+ payload
729
+ ? {
730
+ title: "Raw full prompt",
731
+ content: stripLargeDocumentsFromPayload(payload),
732
+ }
733
+ : null,
734
+ ]);
735
+ const assembledResponse = rawResponse
736
+ ? extractLastResponseFromRawResponse(rawResponse)
737
+ : null;
738
+ const responseContent = joinSubsections([
467
739
  {
468
- title: "Recent tool UI events",
469
- content: runDiagnosticsSnapshot.recentToolUiEvents.length > 0
470
- ? runDiagnosticsSnapshot.recentToolUiEvents
471
- .slice()
472
- .reverse()
473
- .map((event) => formatAgentDiagnosticsEvent(event))
474
- .join("\n")
475
- : "No recent tool-specific UI events were captured for this terminal.",
740
+ title: "Last response",
741
+ content: lastResponse ??
742
+ "No assistant response was captured for this agent run yet.",
476
743
  },
744
+ assembledResponse ? { title: "Response", content: assembledResponse } : null,
745
+ rawResponse ? { title: "Raw response", content: rawResponse } : null,
746
+ ]);
747
+ const summaryCurrency = liveTotals?.currency || agent?.currency || "USD";
748
+ const summaryTotalCost = liveTotals?.totalCost ?? totalTokens?.totalCost ?? agent?.totalCost ?? null;
749
+ const summaryLimitPercent = summaryTotalCost != null && costLimit && costLimit > 0
750
+ ? (summaryTotalCost / costLimit) * 100
751
+ : null;
752
+ const tokensSection = buildTokensSection({
753
+ agent,
754
+ liveTotals: liveTotals ?? null,
755
+ totalTokens: totalTokens ?? null,
756
+ contextWindowStatus: contextWindowStatus ?? null,
757
+ costLimit,
758
+ resolvedModelName,
759
+ });
760
+ const allowancesSection = buildAllowancesSection(allowances ?? null);
761
+ const agentSection = buildAgentSection(agent, resolvedModelName);
762
+ const sections = [
477
763
  {
478
- title: "Recent server events",
479
- content: serverDiagnostics.transport.recentEvents.length > 0
480
- ? serverDiagnostics.transport.recentEvents
481
- .map((event) => formatAgentDiagnosticsEvent(event))
482
- .join("\n")
483
- : "No recent server-side agent transport events were recorded.",
764
+ title: "Summary",
765
+ content: lines([
766
+ `Diagnosis: ${summary.title}`,
767
+ summary.detail,
768
+ agent?.name ? `Agent: ${agent.name}` : null,
769
+ `Agent ID: ${params.agentId}`,
770
+ agent?.profileName
771
+ ? `Profile: ${agent.profileName}${agent.profileId ? ` (${agent.profileId})` : ""}`
772
+ : agent?.profileId
773
+ ? `Profile ID: ${agent.profileId}`
774
+ : null,
775
+ serverDiagnostics.execution.runId
776
+ ? `Run ID: ${serverDiagnostics.execution.runId}`
777
+ : null,
778
+ resolvedModelName ? `Model: ${resolvedModelName}` : null,
779
+ `Socket: ${socketDiagnostics.readyStateLabel}`,
780
+ `Session connected: ${yesNo(serverDiagnostics.currentSession.isConnected)}`,
781
+ `Session subscribed: ${yesNo(serverDiagnostics.currentSession.isSubscribed)}`,
782
+ `Server status: ${serverDiagnostics.execution.status || "unknown"}`,
783
+ `Last seq: ${serverDiagnostics.transport.lastSeq ?? runDiagnosticsSnapshot.lastSeq ?? "—"}`,
784
+ agent?.messageCount != null
785
+ ? `Messages: ${agent.messageCount}`
786
+ : null,
787
+ summaryTotalCost != null
788
+ ? `Total cost: ${formatCost(summaryTotalCost, summaryCurrency)}${costLimit && costLimit > 0
789
+ ? ` / ${formatCost(costLimit, summaryCurrency)}${summaryLimitPercent != null ? ` (${formatPercent(summaryLimitPercent)})` : ""}`
790
+ : ""}`
791
+ : null,
792
+ contextWindowStatus
793
+ ? `Context: ${formatNumber(contextWindowStatus.estimatedInputTokens)} / ${formatNumber(contextWindowStatus.contextWindowTokens)} (${formatPercent(contextWindowStatus.contextUsedPercent)})`
794
+ : null,
795
+ ]),
484
796
  },
797
+ agentSection,
798
+ tokensSection,
799
+ { title: "Connection", content: connectionContent },
800
+ { title: "Run", content: runContent },
801
+ { title: "Events", content: eventsContent },
802
+ buildPersistentLogsSection(serverDiagnostics.persistentLogs ?? []),
803
+ allowancesSection,
804
+ ...(machineCapacitySection ? [machineCapacitySection] : []),
805
+ { title: "Prompt", content: promptContent },
806
+ { title: "Response", content: responseContent },
485
807
  ];
486
- if (payload) {
487
- sections.splice(1, 0, {
488
- title: "Raw full prompt",
489
- content: payload,
490
- });
491
- }
492
- if (rawResponse) {
493
- const rawInsertAt = payload ? 2 : 1;
494
- sections.splice(rawInsertAt, 0, {
495
- title: "Raw response",
496
- content: rawResponse,
497
- });
498
- const assembledResponse = extractLastResponseFromRawResponse(rawResponse);
499
- if (assembledResponse) {
500
- sections.splice(rawInsertAt + 1, 0, {
501
- title: "Response",
502
- content: assembledResponse,
503
- });
504
- }
505
- }
506
- sections.push({
507
- title: "Last prompt",
508
- content: lastPrompt ?? "No prompt was captured for this agent run yet.",
509
- });
510
- sections.push({
511
- title: "Last response",
512
- content: lastResponse ?? "No assistant response was captured for this agent run yet.",
513
- });
514
808
  return sections;
515
809
  }
516
810
  export function AgentTerminalStatusBar({ agent, contextWindowStatus, effectiveModelName, socketDiagnostics, runDiagnosticsSnapshot, liveTotals, totalTokens, costLimit, messages, showCompressionPopover, setShowCompressionPopover, }) {
@@ -590,9 +884,10 @@ export function AgentTerminalStatusBar({ agent, contextWindowStatus, effectiveMo
590
884
  : totalTokens, costLimit: costLimit }), agent?.id && (_jsxs(Tooltip, { children: [_jsx(ContentInspectorPopover, { title: "Run diagnostics", emptyMessage: "No diagnostics are available for this agent yet.", downloadFileName: `agent-${agent.id}-diagnostics.txt`, loadSections: async () => {
591
885
  if (!agent?.id)
592
886
  return [];
593
- const [diagnosticsResult, payloadResult] = await Promise.allSettled([
887
+ const [diagnosticsResult, payloadResult, allowancesResult] = await Promise.allSettled([
594
888
  getAgentDiagnostics(agent.id, socketDiagnostics.sessionId),
595
889
  getLastPayload(agent.id),
890
+ getAgentOperationAllowances(agent.id),
596
891
  ]);
597
892
  if (diagnosticsResult.status !== "fulfilled") {
598
893
  throw diagnosticsResult.reason;
@@ -603,11 +898,21 @@ export function AgentTerminalStatusBar({ agent, contextWindowStatus, effectiveMo
603
898
  const rawResponse = payloadResult.status === "fulfilled"
604
899
  ? payloadResult.value.rawResponse
605
900
  : "";
901
+ const allowances = allowancesResult.status === "fulfilled"
902
+ ? allowancesResult.value
903
+ : null;
606
904
  return buildDiagnosticsSections({
607
905
  agentId: agent.id,
906
+ agent,
608
907
  socketDiagnostics,
609
908
  runDiagnosticsSnapshot,
610
909
  serverDiagnostics: diagnosticsResult.value,
910
+ allowances,
911
+ liveTotals,
912
+ totalTokens,
913
+ contextWindowStatus,
914
+ costLimit,
915
+ resolvedModelName,
611
916
  messages,
612
917
  payload,
613
918
  rawResponse,