@workerdeck/ui 0.23.0 → 1.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (145) hide show
  1. package/build/{SessionPanel-DUt2VzXG.mjs → SessionPanel-I5QSLLb0.mjs} +2266 -3459
  2. package/build/SessionPanel-I5QSLLb0.mjs.map +1 -0
  3. package/build/SessionPanel-yNO60Tzw.d.mts +151 -0
  4. package/build/format-C_lpFq0l.d.mts +16 -0
  5. package/build/format.d.mts +8 -76
  6. package/build/format.mjs +2 -2
  7. package/build/index.d.mts +291 -1695
  8. package/build/index.mjs +6 -301
  9. package/build/index.mjs.map +1 -1
  10. package/build/scoped.css +32 -23
  11. package/build/{status-BE-zg88x.mjs → status-Dm9INVTt.mjs} +17 -88
  12. package/build/status-Dm9INVTt.mjs.map +1 -0
  13. package/build/workspace.d.mts +8 -187
  14. package/build/workspace.mjs +13 -144
  15. package/build/workspace.mjs.map +1 -1
  16. package/package.json +24 -24
  17. package/src/components/agent/CodeEditor.tsx +31 -103
  18. package/src/components/agent/Composer.tsx +114 -333
  19. package/src/components/agent/ContextDialog.tsx +20 -41
  20. package/src/components/agent/ContextRing.tsx +6 -28
  21. package/src/components/agent/Conversation.tsx +21 -33
  22. package/src/components/agent/EditorTabs.tsx +39 -67
  23. package/src/components/agent/EngineIcon.tsx +29 -72
  24. package/src/components/agent/EntryIcon.tsx +16 -0
  25. package/src/components/agent/FileCard.tsx +10 -16
  26. package/src/components/agent/FileTree.tsx +52 -125
  27. package/src/components/agent/FileViewer.tsx +30 -60
  28. package/src/components/agent/HostFilesDialog.tsx +40 -69
  29. package/src/components/agent/Loader.tsx +3 -24
  30. package/src/components/agent/McpDialog.tsx +64 -137
  31. package/src/components/agent/Message.tsx +2 -21
  32. package/src/components/agent/ModelSelect.tsx +33 -62
  33. package/src/components/agent/PermissionModeSelect.tsx +21 -79
  34. package/src/components/agent/PermissionPrompt.tsx +59 -63
  35. package/src/components/agent/ProjectIcon.tsx +228 -93
  36. package/src/components/agent/PromptTokenText.tsx +10 -16
  37. package/src/components/agent/QuestionPrompt.tsx +43 -64
  38. package/src/components/agent/Reasoning.tsx +13 -16
  39. package/src/components/agent/Response.tsx +3 -9
  40. package/src/components/agent/Scrubber.tsx +31 -80
  41. package/src/components/agent/SessionBrowser.tsx +64 -243
  42. package/src/components/agent/SessionEmptyState.tsx +10 -40
  43. package/src/components/agent/SessionInfoDialog.tsx +46 -78
  44. package/src/components/agent/SessionItem.tsx +53 -320
  45. package/src/components/agent/SessionList.tsx +23 -39
  46. package/src/components/agent/SessionPanel.tsx +315 -996
  47. package/src/components/agent/SessionStatusIcon.tsx +14 -28
  48. package/src/components/agent/SessionSteps.tsx +34 -187
  49. package/src/components/agent/SessionWorkspace.tsx +104 -219
  50. package/src/components/agent/SkillsDialog.tsx +35 -80
  51. package/src/components/agent/StatusBar.tsx +51 -136
  52. package/src/components/agent/SubagentStrip.tsx +12 -77
  53. package/src/components/agent/ToolCallCard.tsx +94 -135
  54. package/src/components/agent/Transcript.tsx +103 -1288
  55. package/src/components/agent/TranscriptItemView.tsx +155 -0
  56. package/src/components/agent/TranscriptRows.tsx +418 -0
  57. package/src/components/agent/UsageDialog.tsx +7 -29
  58. package/src/components/agent/UsageMeters.tsx +18 -73
  59. package/src/components/agent/pulse.tsx +9 -32
  60. package/src/components/agent/scrubber-marks.ts +33 -103
  61. package/src/components/agent/status.ts +1 -5
  62. package/src/components/agent/tool-result-fetch.tsx +3 -25
  63. package/src/components/agent/tool-result-image.tsx +32 -111
  64. package/src/components/agent/transcript-rows.ts +41 -118
  65. package/src/components/agent/transcript-variant.tsx +3 -80
  66. package/src/components/agent/use-height-epoch.ts +10 -24
  67. package/src/components/agent/use-path-links.ts +45 -63
  68. package/src/components/agent/use-subagent-frame.ts +106 -0
  69. package/src/components/agent/use-transcript-jumps.ts +49 -107
  70. package/src/components/prompt-area/animated-placeholder.tsx +6 -5
  71. package/src/components/prompt-area/clipboard-helpers.ts +26 -21
  72. package/src/components/prompt-area/cursor-helpers.ts +79 -37
  73. package/src/components/prompt-area/dom-helpers.ts +97 -69
  74. package/src/components/prompt-area/file-strip.tsx +90 -80
  75. package/src/components/prompt-area/html-to-markdown.ts +67 -46
  76. package/src/components/prompt-area/image-strip.tsx +8 -18
  77. package/src/components/prompt-area/index.ts +2 -15
  78. package/src/components/prompt-area/prompt-area-engine.ts +100 -115
  79. package/src/components/prompt-area/prompt-area-list-ops.ts +66 -59
  80. package/src/components/prompt-area/prompt-area.tsx +31 -38
  81. package/src/components/prompt-area/remove-button.tsx +3 -9
  82. package/src/components/prompt-area/segment-helpers.ts +4 -12
  83. package/src/components/prompt-area/trigger-popover.tsx +15 -27
  84. package/src/components/prompt-area/trigger-presets.ts +0 -10
  85. package/src/components/prompt-area/types.ts +3 -8
  86. package/src/components/prompt-area/use-chip-editing.ts +305 -0
  87. package/src/components/prompt-area/use-markdown-mode.ts +7 -17
  88. package/src/components/prompt-area/use-prompt-area-events.ts +80 -86
  89. package/src/components/prompt-area/use-prompt-area-keydown.ts +598 -0
  90. package/src/components/prompt-area/use-prompt-area-state.ts +5 -23
  91. package/src/components/prompt-area/use-prompt-area.ts +170 -896
  92. package/src/components/prompt-area/use-trigger-search.ts +21 -19
  93. package/src/components/terminal/PermissionPrompt.tsx +56 -59
  94. package/src/components/terminal/QuestionPrompt.tsx +28 -79
  95. package/src/components/terminal/StatusLine.tsx +13 -63
  96. package/src/components/terminal/TerminalTranscript.tsx +44 -160
  97. package/src/components/terminal/affordances.tsx +68 -98
  98. package/src/components/terminal/blocks.ts +20 -156
  99. package/src/components/terminal/diff.tsx +19 -67
  100. package/src/components/terminal/height.ts +163 -313
  101. package/src/components/terminal/image-box.ts +0 -44
  102. package/src/components/terminal/items.tsx +150 -305
  103. package/src/components/terminal/markdown.tsx +36 -95
  104. package/src/components/terminal/press.tsx +26 -53
  105. package/src/components/terminal/prompt.tsx +40 -170
  106. package/src/components/terminal/result-preview.ts +8 -56
  107. package/src/components/terminal/row.tsx +11 -98
  108. package/src/components/terminal/scrubber.tsx +108 -401
  109. package/src/components/terminal/surface.tsx +6 -54
  110. package/src/components/terminal/todos.ts +66 -0
  111. package/src/components/terminal/tool-run.ts +21 -192
  112. package/src/components/ui/AlertDialog.tsx +8 -23
  113. package/src/components/ui/Badge.tsx +18 -29
  114. package/src/components/ui/Button.tsx +7 -15
  115. package/src/components/ui/Card.tsx +2 -13
  116. package/src/components/ui/CodeBlock.tsx +10 -37
  117. package/src/components/ui/CopyButton.tsx +10 -23
  118. package/src/components/ui/Dialog.tsx +23 -36
  119. package/src/components/ui/Empty.tsx +6 -29
  120. package/src/components/ui/Input.tsx +14 -16
  121. package/src/components/ui/Menu.tsx +6 -18
  122. package/src/components/ui/PortalScope.tsx +1 -21
  123. package/src/components/ui/ProgressRing.tsx +8 -19
  124. package/src/components/ui/Select.tsx +18 -31
  125. package/src/components/ui/Sonner.tsx +1 -2
  126. package/src/components/ui/Spinner.tsx +1 -1
  127. package/src/components/ui/Splitter.tsx +30 -64
  128. package/src/components/ui/Textarea.tsx +2 -5
  129. package/src/components/ui/Tooltip.tsx +3 -13
  130. package/src/format.ts +0 -9
  131. package/src/index.ts +16 -113
  132. package/src/lib/clipboard.ts +8 -28
  133. package/src/lib/css.ts +8 -0
  134. package/src/lib/format.ts +101 -86
  135. package/src/lib/plan-request.ts +16 -0
  136. package/src/lib/status.ts +45 -95
  137. package/src/lib/tool-icon.ts +39 -47
  138. package/src/lib/utils.ts +1 -3
  139. package/src/styles/terminal.css +81 -49
  140. package/src/styles/theme.css +96 -32
  141. package/src/workspace.ts +1 -24
  142. package/build/SessionPanel-BobynUo4.d.mts +0 -669
  143. package/build/SessionPanel-DUt2VzXG.mjs.map +0 -1
  144. package/build/format-ljc3lKpA.d.mts +0 -59
  145. package/build/status-BE-zg88x.mjs.map +0 -1
package/build/index.d.mts CHANGED
@@ -1,79 +1,52 @@
1
- import { a as formatDuration, c as formatRelativeTime, d as rateLimitWindowSeconds, f as toolInputPreview, i as formatCountdown, l as formatTokens, n as formatBytes, o as formatRateLimitWindow, r as formatCost, s as formatRateLimitWindowLong, t as formatAgoPrecise, u as friendlyModel } from "./format-ljc3lKpA.mjs";
2
- import { C as permissionModeChoices, S as PermissionModeSelectProps, _ as useAffordances, a as SessionVitals, b as PermissionModeMeta, c as TranscriptDensityProvider, d as TranscriptVariantProvider, f as useTranscriptDensity, g as WithActions, h as TerminalAffordances, i as SessionSurfacePanel, l as TranscriptFont, m as CopyAction, n as SessionPanel, o as TerminalMetrics, p as useTranscriptVariant, r as SessionPanelProps, s as TranscriptDensity, t as SessionControls, u as TranscriptVariant, v as PERMISSION_MODES, w as permissionModeMeta, x as PermissionModeSelect, y as PermissionModeChoice } from "./SessionPanel-BobynUo4.mjs";
3
- import * as _$react from "react";
1
+ import { a as formatDuration, c as formatRelativeTime, d as rateLimitWindowSeconds, f as toolInputPreview, i as formatCountdown, l as formatTokens, n as formatBytes, o as formatRateLimitWindow, r as formatCost, s as formatRateLimitWindowLong, t as formatAgoPrecise, u as friendlyModel } from "./format-C_lpFq0l.mjs";
2
+ import { C as permissionModeChoices, S as PermissionModeSelectProps, _ as useAffordances, a as SessionVitals, b as PermissionModeMeta, c as TranscriptDensityProvider, d as TranscriptVariantProvider, f as useTranscriptDensity, g as WithActions, h as TerminalAffordances, i as SessionSurfacePanel, l as TranscriptFont, m as CopyAction, n as SessionPanel, o as TerminalMetrics, p as useTranscriptVariant, r as SessionPanelProps, s as TranscriptDensity, t as SessionControls, u as TranscriptVariant, v as PERMISSION_MODES, w as permissionModeMeta, x as PermissionModeSelect, y as PermissionModeChoice } from "./SessionPanel-yNO60Tzw.mjs";
4
3
  import { ButtonHTMLAttributes, FunctionComponent, HTMLAttributes, InputHTMLAttributes, ReactElement, ReactNode, Ref, RefObject, TextareaHTMLAttributes } from "react";
5
4
  import { VariantProps } from "class-variance-authority";
6
5
  import { ClassValue } from "clsx";
7
- import * as _$_base_ui_react_select0 from "@base-ui/react/select";
8
6
  import { Select as Select$1 } from "@base-ui/react/select";
9
7
  import { LucideIcon } from "lucide-react";
10
- import * as _$_base_ui_react_alert_dialog0 from "@base-ui/react/alert-dialog";
11
8
  import { AlertDialog as AlertDialog$1 } from "@base-ui/react/alert-dialog";
12
9
  import { Menu as Menu$1 } from "@base-ui/react/menu";
13
- import * as _$_base_ui_react_dialog0 from "@base-ui/react/dialog";
14
10
  import { Dialog as Dialog$1 } from "@base-ui/react/dialog";
15
- import * as _$_base_ui_react_tooltip0 from "@base-ui/react/tooltip";
16
11
  import { Tooltip } from "@base-ui/react/tooltip";
17
12
  import { toast } from "sonner";
18
13
  import { ContextReading, ContextUsage, FilePatch, ModelOption, PermissionRequest, ProfileEngine, ProjectIcon as ProjectIcon$1, QuestionBehavior, RateLimitInfo, SessionInfo, SessionRow, SessionStatus, SkillInfo, SlashCommandInfo, UsageWindowRow, UserQuestion, ViewConfig, WorkspaceScope } from "@workerdeck/protocol";
19
14
  import { ConnectionState, TranscriptItem, TranscriptState, UseAttachmentsResult } from "@workerdeck/react";
20
- import * as _$class_variance_authority_types0 from "class-variance-authority/types";
21
15
  import { WorkerDeckClient } from "@workerdeck/client";
22
-
23
16
  //#region src/components/ui/Button.d.ts
24
17
  declare const buttonVariants: (props?: ({
25
18
  variant?: "default" | "outline" | "secondary" | "ghost" | "destructive" | "link" | null | undefined;
26
19
  size?: "default" | "xs" | "sm" | "lg" | "icon" | "icon-sm" | null | undefined;
27
- } & _$class_variance_authority_types0.ClassProp) | undefined) => string;
20
+ } & import("class-variance-authority/types").ClassProp) | undefined) => string;
28
21
  interface ButtonProps extends ButtonHTMLAttributes<HTMLButtonElement>, VariantProps<typeof buttonVariants> {}
29
- declare const Button: _$react.ForwardRefExoticComponent<ButtonProps & _$react.RefAttributes<HTMLButtonElement>>;
22
+ declare const Button: import("react").ForwardRefExoticComponent<ButtonProps & import("react").RefAttributes<HTMLButtonElement>>;
30
23
  //#endregion
31
24
  //#region src/components/ui/Badge.d.ts
32
25
  declare const badgeVariants: (props?: ({
33
26
  variant?: "neutral" | "accent" | "success" | "warning" | "danger" | "info" | null | undefined;
34
27
  mono?: boolean | null | undefined;
35
- } & _$class_variance_authority_types0.ClassProp) | undefined) => string;
28
+ } & import("class-variance-authority/types").ClassProp) | undefined) => string;
36
29
  interface BadgeProps extends HTMLAttributes<HTMLSpanElement>, VariantProps<typeof badgeVariants> {
37
- /** Render a leading status dot in the variant's color. */
38
30
  dot?: boolean;
39
31
  }
40
- declare function Badge({
41
- className,
42
- variant,
43
- mono,
44
- dot,
45
- children,
46
- ...props
47
- }: BadgeProps): _$react.JSX.Element;
32
+ declare function Badge({ className, variant, mono, dot, children, ...props }: BadgeProps): import("react").JSX.Element;
48
33
  //#endregion
49
34
  //#region src/components/ui/Card.d.ts
50
- declare function Card({
51
- className,
52
- ...props
53
- }: HTMLAttributes<HTMLDivElement>): _$react.JSX.Element;
54
- declare function CardHeader({
55
- className,
56
- ...props
57
- }: HTMLAttributes<HTMLDivElement>): _$react.JSX.Element;
58
- declare function CardTitle({
59
- className,
60
- ...props
61
- }: HTMLAttributes<HTMLHeadingElement>): _$react.JSX.Element;
62
- declare function CardContent({
63
- className,
64
- ...props
65
- }: HTMLAttributes<HTMLDivElement>): _$react.JSX.Element;
35
+ declare function Card({ className, ...props }: HTMLAttributes<HTMLDivElement>): import("react").JSX.Element;
36
+ declare function CardHeader({ className, ...props }: HTMLAttributes<HTMLDivElement>): import("react").JSX.Element;
37
+ declare function CardTitle({ className, ...props }: HTMLAttributes<HTMLHeadingElement>): import("react").JSX.Element;
38
+ declare function CardContent({ className, ...props }: HTMLAttributes<HTMLDivElement>): import("react").JSX.Element;
66
39
  //#endregion
67
40
  //#region src/components/ui/Input.d.ts
68
- declare const Input: _$react.ForwardRefExoticComponent<InputHTMLAttributes<HTMLInputElement> & _$react.RefAttributes<HTMLInputElement>>;
41
+ declare const Input: import("react").ForwardRefExoticComponent<InputHTMLAttributes<HTMLInputElement> & import("react").RefAttributes<HTMLInputElement>>;
69
42
  //#endregion
70
43
  //#region src/components/ui/Textarea.d.ts
71
- declare const Textarea: _$react.ForwardRefExoticComponent<TextareaHTMLAttributes<HTMLTextAreaElement> & _$react.RefAttributes<HTMLTextAreaElement>>;
44
+ declare const Textarea: import("react").ForwardRefExoticComponent<TextareaHTMLAttributes<HTMLTextAreaElement> & import("react").RefAttributes<HTMLTextAreaElement>>;
72
45
  //#endregion
73
46
  //#region src/components/ui/Select.d.ts
74
47
  declare const Select: typeof Select$1.Root;
75
- declare const SelectValue: _$react.ForwardRefExoticComponent<Omit<_$_base_ui_react_select0.SelectValueProps, "ref"> & _$react.RefAttributes<HTMLSpanElement>>;
76
- declare const SelectItemText: _$react.NamedExoticComponent<Omit<_$_base_ui_react_select0.SelectItemTextProps, "ref"> & _$react.RefAttributes<HTMLDivElement>>;
48
+ declare const SelectValue: import("react").ForwardRefExoticComponent<Omit<import("@base-ui/react/select").SelectValueProps, "ref"> & import("react").RefAttributes<HTMLSpanElement>>;
49
+ declare const SelectItemText: import("react").NamedExoticComponent<Omit<import("@base-ui/react/select").SelectItemTextProps, "ref"> & import("react").RefAttributes<HTMLDivElement>>;
77
50
  declare const SelectTrigger: FunctionComponent<Select$1.Trigger.Props>;
78
51
  declare const SelectContent: FunctionComponent<Select$1.Popup.Props & Pick<Select$1.Positioner.Props, 'align' | 'alignItemWithTrigger' | 'side' | 'sideOffset'>>;
79
52
  declare const SelectItem: FunctionComponent<Select$1.Item.Props>;
@@ -81,13 +54,13 @@ declare const SelectItem: FunctionComponent<Select$1.Item.Props>;
81
54
  //#region src/components/ui/AlertDialog.d.ts
82
55
  declare const AlertDialog: typeof AlertDialog$1.Root;
83
56
  declare const AlertDialogTrigger: AlertDialog$1.Trigger;
84
- declare const AlertDialogClose: _$react.ForwardRefExoticComponent<Omit<_$_base_ui_react_alert_dialog0.AlertDialogCloseProps, "ref"> & _$react.RefAttributes<HTMLButtonElement>>;
57
+ declare const AlertDialogClose: import("react").ForwardRefExoticComponent<Omit<import("@base-ui/react/alert-dialog").AlertDialogCloseProps, "ref"> & import("react").RefAttributes<HTMLButtonElement>>;
85
58
  declare const AlertDialogContent: FunctionComponent<AlertDialog$1.Popup.Props>;
86
59
  declare const AlertDialogTitle: FunctionComponent<AlertDialog$1.Title.Props>;
87
60
  declare const AlertDialogDescription: FunctionComponent<AlertDialog$1.Description.Props>;
88
61
  //#endregion
89
62
  //#region src/components/ui/Menu.d.ts
90
- declare const Menu: <Payload>(props: Menu$1.Root.Props<Payload>) => _$react.JSX.Element;
63
+ declare const Menu: <Payload>(props: Menu$1.Root.Props<Payload>) => import("react").JSX.Element;
91
64
  declare const MenuTrigger: Menu$1.Trigger;
92
65
  declare const MenuContent: FunctionComponent<Menu$1.Popup.Props & Pick<Menu$1.Positioner.Props, 'align' | 'side' | 'sideOffset'>>;
93
66
  declare const MenuItem: FunctionComponent<Menu$1.Item.Props & {
@@ -98,26 +71,16 @@ declare const MenuSeparator: FunctionComponent<Menu$1.Separator.Props>;
98
71
  //#region src/components/ui/Dialog.d.ts
99
72
  declare const Dialog: typeof Dialog$1.Root;
100
73
  declare const DialogTrigger: Dialog$1.Trigger;
101
- declare const DialogClose: _$react.ForwardRefExoticComponent<Omit<_$_base_ui_react_dialog0.DialogCloseProps, "ref"> & _$react.RefAttributes<HTMLButtonElement>>;
102
- /**
103
- * A dismissible panel, sized for reading rather than confirming — the web
104
- * counterpart of the iOS app's detail sheets (context, usage, session info, MCP).
105
- *
106
- * Taller than {@link AlertDialogContent} and scrollable inside, because these
107
- * carry lists whose length is the engine's business, not the layout's.
108
- */
74
+ declare const DialogClose: import("react").ForwardRefExoticComponent<Omit<import("@base-ui/react/dialog").DialogCloseProps, "ref"> & import("react").RefAttributes<HTMLButtonElement>>;
109
75
  declare const DialogContent: FunctionComponent<Dialog$1.Popup.Props & {
110
76
  size?: 'sm' | 'md' | 'lg';
111
77
  }>;
112
- /** Title row with the close button, pinned above the scrolling body. */
113
78
  declare const DialogHeader: FunctionComponent<{
114
79
  title: string;
115
- description?: string; /** Rendered between the title and the close button. */
80
+ description?: string;
116
81
  actions?: React.ReactNode;
117
82
  }>;
118
- /** The scrolling region under the header. */
119
83
  declare const DialogBody: FunctionComponent<React.HTMLAttributes<HTMLDivElement>>;
120
- /** A label/value row — the shape every one of these panels is mostly made of. */
121
84
  declare const DialogRow: FunctionComponent<{
122
85
  label: string;
123
86
  children: React.ReactNode;
@@ -125,196 +88,75 @@ declare const DialogRow: FunctionComponent<{
125
88
  }>;
126
89
  //#endregion
127
90
  //#region src/components/ui/Tooltip.d.ts
128
- declare const TooltipProvider: _$react.FC<_$_base_ui_react_tooltip0.TooltipProviderProps>;
91
+ declare const TooltipProvider: import("react").FC<import("@base-ui/react/tooltip").TooltipProviderProps>;
129
92
  declare const TooltipContent: FunctionComponent<Tooltip.Popup.Props & Pick<Tooltip.Positioner.Props, 'side' | 'sideOffset'>>;
130
- /**
131
- * Convenience wrapper: `<Tip content="..."><Button/></Tip>`.
132
- *
133
- * Pass `render` when the trigger must *be* an element you already have — a tab, a
134
- * row — rather than something wrapped in a span. The default span is fine beside
135
- * a button but would break any layout that styles its own children (a flex tab
136
- * strip gets an extra box between the container and its items).
137
- */
138
- declare function Tip({
139
- content,
140
- render,
141
- side,
142
- children
143
- }: {
93
+ declare function Tip({ content, render, side, children }: {
144
94
  content: ReactNode;
145
95
  render?: ReactElement;
146
96
  side?: 'top' | 'right' | 'bottom' | 'left';
147
97
  children?: ReactNode;
148
- }): _$react.JSX.Element;
98
+ }): import("react").JSX.Element;
149
99
  //#endregion
150
100
  //#region src/components/ui/Sonner.d.ts
151
- /** Token-themed toaster; relies on the [data-theme] swap, so no `theme` prop needed. */
152
- declare function Toaster(): _$react.JSX.Element;
101
+ declare function Toaster(): import("react").JSX.Element;
153
102
  //#endregion
154
103
  //#region src/components/ui/CopyButton.d.ts
155
104
  interface CopyButtonProps extends Omit<ButtonProps, 'onClick' | 'children'> {
156
105
  value: string;
157
- /** Draw the state as characters (`⧉` / `✓`) rather than line-art icons — for
158
- * terminal-styled surfaces, where an SVG reads as another app's button. */
159
106
  glyph?: boolean;
160
107
  }
161
- declare function CopyButton({
162
- value,
163
- glyph,
164
- className,
165
- variant,
166
- size,
167
- ...props
168
- }: CopyButtonProps): _$react.JSX.Element;
108
+ declare function CopyButton({ value, glyph, className, variant, size, ...props }: CopyButtonProps): import("react").JSX.Element;
169
109
  //#endregion
170
110
  //#region src/components/ui/Spinner.d.ts
171
- declare function Spinner({
172
- className
173
- }: {
111
+ declare function Spinner({ className }: {
174
112
  className?: string;
175
- }): _$react.JSX.Element;
113
+ }): import("react").JSX.Element;
176
114
  //#endregion
177
115
  //#region src/components/ui/CodeBlock.d.ts
178
116
  interface CodeBlockProps {
179
117
  code: string;
180
- /** Header label, e.g. a language or "Parameters". */
181
118
  label?: ReactNode;
182
119
  copyable?: boolean;
183
- /**
184
- * `'panel'` (default) is the framed card: border, header strip, rounded.
185
- * `'plain'` is the terminal treatment — the label is a dim line, the code a
186
- * flat band, and copy is a character. For surfaces where a box around every
187
- * payload is more chrome than content (the transcript's `lines` variant).
188
- *
189
- * A prop rather than a read of the transcript's variant context: this is a
190
- * `ui/` primitive and has no business knowing what a transcript is. The agent
191
- * component that renders it does.
192
- */
193
120
  variant?: 'panel' | 'plain';
194
121
  className?: string;
195
122
  }
196
- /** Plain (unhighlighted) code panel for structured data like tool inputs. Markdown code
197
- * inside assistant responses is highlighted by <Response> instead. */
198
- declare function CodeBlock({
199
- code,
200
- label,
201
- copyable,
202
- variant,
203
- className
204
- }: CodeBlockProps): _$react.JSX.Element;
123
+ declare function CodeBlock({ code, label, copyable, variant, className }: CodeBlockProps): import("react").JSX.Element;
205
124
  //#endregion
206
125
  //#region src/components/ui/Splitter.d.ts
207
126
  interface SplitterProps {
208
- /**
209
- * ARIA's sense of the word: a `vertical` splitter is a vertical bar between
210
- * two side-by-side panes, and it resizes a **width**. A `horizontal` one sits
211
- * between stacked panes and resizes a **height**.
212
- */
213
127
  orientation: 'vertical' | 'horizontal';
214
- /** Current size of the pane this splitter controls, in pixels. */
215
128
  value: number;
216
129
  onValueChange: (value: number) => void;
217
130
  min: number;
218
131
  max: number;
219
- /** Keyboard step. */
220
132
  step?: number;
221
- /**
222
- * Size to snap back to on a double-click — the convention every pane divider
223
- * that can be dragged is expected to honour. Omit and a double-click does
224
- * nothing, which is the honest behaviour when there is no default to mean.
225
- */
226
133
  defaultValue?: number;
227
- /** Set when dragging the splitter *away* from the origin should shrink the
228
- * controlled pane — i.e. the pane is on the right or the bottom. */
229
134
  inverted?: boolean;
230
- /** Required: "Resize" alone does not say which of two splitters this is. */
231
135
  'aria-label': string;
232
136
  className?: string;
233
137
  }
234
- /**
235
- * A draggable pane divider.
236
- *
237
- * Hand-rolled rather than depended on: `@base-ui/react` ships no splitter, the
238
- * behaviour is a hundred lines of pointer events, and this repo's instinct at
239
- * this layer is to own it (the composer is vendored for the same reason).
240
- *
241
- * Pointer capture is what makes it survive a fast drag — without it the pointer
242
- * leaves the 5px bar within a frame and the moves go to whatever is underneath,
243
- * which for this layout is an iframe-free but still selection-happy code pane.
244
- * The drag origin is captured on pointerdown and every move is measured against
245
- * it, so the pane cannot drift relative to the cursor over a long drag the way
246
- * per-move deltas do once clamping is involved.
247
- *
248
- * Keyboard-operable and announced as a separator, because a pane you can only
249
- * size by dragging is a pane some people cannot size.
250
- */
251
- declare function Splitter({
252
- orientation,
253
- value,
254
- onValueChange,
255
- min,
256
- max,
257
- step,
258
- defaultValue,
259
- inverted,
260
- 'aria-label': label,
261
- className
262
- }: SplitterProps): _$react.JSX.Element;
138
+ declare function Splitter({ orientation, value, onValueChange, min, max, step, defaultValue, inverted, 'aria-label': label, className }: SplitterProps): import("react").JSX.Element;
263
139
  //#endregion
264
140
  //#region src/components/ui/Empty.d.ts
265
- /**
266
- * A view with nothing in it: icon, title, description, and at most one action.
267
- *
268
- * Centered and given room, because an empty view is the first thing a new
269
- * install shows and a flush-left sentence in the top corner reads like a bug
270
- * report. It lives here rather than in one client because every panel that can
271
- * be empty should be empty the same way — the extension's views and the
272
- * dashboard's four sidebars are the same shape of thing.
273
- *
274
- * **At most one action, and never one the view header already offers.** Creating
275
- * a session and adding a gateway are the `+` in the native title bar, exclusively
276
- * — so those empty states point at it in words rather than growing a second
277
- * button that does the same thing two inches lower. A button here is for the way
278
- * out of a state the header has no answer to: clearing a filter, widening a
279
- * scope.
280
- */
281
- declare function Empty({
282
- icon,
283
- title,
284
- description,
285
- action,
286
- onAction
287
- }: {
141
+ declare function Empty({ icon, title, description, action, onAction }: {
288
142
  icon: ReactNode;
289
143
  title: string;
290
144
  description?: ReactNode;
291
145
  action?: string;
292
146
  onAction?: () => void;
293
- }): _$react.JSX.Element;
294
- /** A key or icon named inline in an empty state's description — "use the + above". */
295
- declare function EmptyKey({
296
- children
297
- }: {
147
+ }): import("react").JSX.Element;
148
+ declare function EmptyKey({ children }: {
298
149
  children: ReactNode;
299
- }): _$react.JSX.Element;
150
+ }): import("react").JSX.Element;
300
151
  //#endregion
301
152
  //#region src/components/ui/ProgressRing.d.ts
302
153
  interface ProgressRingProps {
303
- /** Filled share, 0–100 (clamped). */
304
154
  value: number;
305
- /** Outer diameter in px. */
306
155
  size?: number;
307
156
  strokeWidth?: number;
308
157
  className?: string;
309
158
  }
310
- /** Tiny SVG progress circle; stroke color comes from `currentColor` so callers set it
311
- * via text color classes (e.g. warning/danger past thresholds). */
312
- declare function ProgressRing({
313
- value,
314
- size,
315
- strokeWidth,
316
- className
317
- }: ProgressRingProps): _$react.JSX.Element;
159
+ declare function ProgressRing({ value, size, strokeWidth, className }: ProgressRingProps): import("react").JSX.Element;
318
160
  //#endregion
319
161
  //#region src/components/prompt-area/types.d.ts
320
162
  /**
@@ -325,20 +167,22 @@ declare function ProgressRing({
325
167
  * - Immutable chips for resolved mentions/commands
326
168
  * - Configurable trigger behavior (dropdown vs callback)
327
169
  * - Simple inline markdown rendering
328
- */
329
- /**
330
- * A segment of content within the editable text.
331
- * The document model is an ordered array of these segments.
170
+ *
171
+ * The document model is an ordered array of {@link TextSegment}/{@link ChipSegment}.
332
172
  */
333
173
  type TextSegment = {
334
174
  type: 'text';
335
175
  text: string;
336
176
  };
337
177
  type ChipSegment = {
338
- type: 'chip'; /** The trigger character that created this chip (e.g., '@', '#') */
339
- trigger: string; /** The resolved value/ID (e.g., user ID, file ID) */
340
- value: string; /** The display text shown in the chip */
341
- displayText: string; /** Optional data payload attached to the chip */
178
+ type: 'chip';
179
+ /** The trigger character that created this chip (e.g., '@', '#') */
180
+ trigger: string;
181
+ /** The resolved value/ID (e.g., user ID, file ID) */
182
+ value: string;
183
+ /** The display text shown in the chip */
184
+ displayText: string;
185
+ /** Optional data payload attached to the chip */
342
186
  data?: unknown;
343
187
  /**
344
188
  * True when this chip was auto-created by pressing space (resolveOnSpace).
@@ -372,18 +216,26 @@ type ChipStyle = 'pill' | 'inline';
372
216
  * A suggestion item shown in the trigger dropdown.
373
217
  */
374
218
  type TriggerSuggestion = {
375
- /** Unique value/ID for this suggestion */value: string; /** Display label shown in the dropdown */
376
- label: string; /** Optional description shown below the label */
377
- description?: string; /** Optional icon element rendered before the label */
378
- icon?: React.ReactNode; /** Optional arbitrary data passed through on selection */
219
+ /** Unique value/ID for this suggestion */
220
+ value: string;
221
+ /** Display label shown in the dropdown */
222
+ label: string;
223
+ /** Optional description shown below the label */
224
+ description?: string;
225
+ /** Optional icon element rendered before the label */
226
+ icon?: React.ReactNode;
227
+ /** Optional arbitrary data passed through on selection */
379
228
  data?: unknown;
380
229
  };
381
230
  /**
382
231
  * Configuration for a trigger character.
383
232
  */
384
233
  type TriggerConfig = {
385
- /** The trigger character (e.g., '/', '@', '#') */char: string; /** Where this trigger is valid */
386
- position: TriggerPosition; /** How this trigger behaves */
234
+ /** The trigger character (e.g., '/', '@', '#') */
235
+ char: string;
236
+ /** Where this trigger is valid */
237
+ position: TriggerPosition;
238
+ /** How this trigger behaves */
387
239
  mode: TriggerMode;
388
240
  /**
389
241
  * For 'dropdown' mode: called with the current query to fetch suggestions.
@@ -442,8 +294,10 @@ type TriggerConfig = {
442
294
  * - 'pill' (default): Button-like pill with background, padding, border-radius
443
295
  * - 'inline': Bold inline text without pill styling
444
296
  */
445
- chipStyle?: ChipStyle; /** CSS class name(s) applied to chips created by this trigger */
446
- chipClassName?: string; /** Label used for accessibility (e.g., "mention", "command") */
297
+ chipStyle?: ChipStyle;
298
+ /** CSS class name(s) applied to chips created by this trigger */
299
+ chipClassName?: string;
300
+ /** Label used for accessibility (e.g., "mention", "command") */
447
301
  accessibilityLabel?: string;
448
302
  /**
449
303
  * Debounce delay in milliseconds before calling `onSearch`.
@@ -466,8 +320,11 @@ type TriggerConfig = {
466
320
  * Context passed to callback-mode trigger handlers.
467
321
  */
468
322
  type TriggerActivateContext = {
469
- /** The full plain text content at the time of activation */text: string; /** The cursor offset position */
470
- cursorPosition: number; /** Function to insert a chip at the current cursor position */
323
+ /** The full plain text content at the time of activation */
324
+ text: string;
325
+ /** The cursor offset position */
326
+ cursorPosition: number;
327
+ /** Function to insert a chip at the current cursor position */
471
328
  insertChip: (chip: Omit<ChipSegment, 'type'>) => void;
472
329
  };
473
330
  /**
@@ -475,9 +332,13 @@ type TriggerActivateContext = {
475
332
  * State is managed externally by the parent component.
476
333
  */
477
334
  type PromptAreaImage = {
478
- /** Unique identifier for this image */id: string; /** URL to display (CDN URL or temporary blob URL for preview) */
479
- url: string; /** Optional alt text for accessibility */
480
- alt?: string; /** When true, shows a loading indicator over the thumbnail */
335
+ /** Unique identifier for this image */
336
+ id: string;
337
+ /** URL to display (CDN URL or temporary blob URL for preview) */
338
+ url: string;
339
+ /** Optional alt text for accessibility */
340
+ alt?: string;
341
+ /** When true, shows a loading indicator over the thumbnail */
481
342
  loading?: boolean;
482
343
  };
483
344
  /**
@@ -485,22 +346,34 @@ type PromptAreaImage = {
485
346
  * State is managed externally by the parent component.
486
347
  */
487
348
  type PromptAreaFile = {
488
- /** Unique identifier for this file */id: string; /** Display filename (e.g., "report.pdf") */
489
- name: string; /** File size in bytes */
490
- size?: number; /** MIME type (used for icon selection, e.g., "application/pdf") */
491
- type?: string; /** When true, shows a loading indicator over the file card */
349
+ /** Unique identifier for this file */
350
+ id: string;
351
+ /** Display filename (e.g., "report.pdf") */
352
+ name: string;
353
+ /** File size in bytes */
354
+ size?: number;
355
+ /** MIME type (used for icon selection, e.g., "application/pdf") */
356
+ type?: string;
357
+ /** When true, shows a loading indicator over the file card */
492
358
  loading?: boolean;
493
359
  };
494
360
  /**
495
361
  * Props for the PromptArea component.
496
362
  */
497
363
  type PromptAreaProps = {
498
- /** The document segments (controlled) */value: Segment[]; /** Called when the content changes */
499
- onChange: (segments: Segment[]) => void; /** Trigger configurations */
500
- triggers?: TriggerConfig[]; /** Placeholder text when empty. Pass an array of strings to animate between them. */
501
- placeholder?: string | string[]; /** Additional CSS class for the container */
502
- className?: string; /** Whether the input is disabled */
503
- disabled?: boolean; /** Whether to render simple inline markdown (bold, italic, URLs, lists) */
364
+ /** The document segments (controlled) */
365
+ value: Segment[];
366
+ /** Called when the content changes */
367
+ onChange: (segments: Segment[]) => void;
368
+ /** Trigger configurations */
369
+ triggers?: TriggerConfig[];
370
+ /** Placeholder text when empty. Pass an array of strings to animate between them. */
371
+ placeholder?: string | string[];
372
+ /** Additional CSS class for the container */
373
+ className?: string;
374
+ /** Whether the input is disabled */
375
+ disabled?: boolean;
376
+ /** Whether to render simple inline markdown (bold, italic, URLs, lists) */
504
377
  markdown?: boolean;
505
378
  /**
506
379
  * When markdown is on, the editor rewrites typed list markers (`- ` / `* `)
@@ -508,20 +381,31 @@ type PromptAreaProps = {
508
381
  * marker in the value/`onChange` text — needed when a host renders the output
509
382
  * as real markdown, where `•` is not a valid list marker. Default `true`.
510
383
  */
511
- normalizeBullets?: boolean; /** Called when Enter is pressed (without Shift) */
512
- onSubmit?: (segments: Segment[]) => void; /** Called when Escape is pressed */
513
- onEscape?: () => void; /** Called when a chip element is clicked. Receives the chip's segment data. */
514
- onChipClick?: (chip: ChipSegment) => void; /** Called when a new chip is added (dropdown selection, auto-resolve, paste, or imperative insert) */
515
- onChipAdd?: (chip: ChipSegment) => void; /** Called when a chip is deleted (backspace or forward delete) */
516
- onChipDelete?: (chip: ChipSegment) => void; /** Called when a URL link is clicked. Receives the URL string. */
517
- onLinkClick?: (url: string) => void; /** Called after content is pasted. Receives the resulting segments and the paste source. */
384
+ normalizeBullets?: boolean;
385
+ /** Called when Enter is pressed (without Shift) */
386
+ onSubmit?: (segments: Segment[]) => void;
387
+ /** Called when Escape is pressed */
388
+ onEscape?: () => void;
389
+ /** Called when a chip element is clicked. Receives the chip's segment data. */
390
+ onChipClick?: (chip: ChipSegment) => void;
391
+ /** Called when a new chip is added (dropdown selection, auto-resolve, paste, or imperative insert) */
392
+ onChipAdd?: (chip: ChipSegment) => void;
393
+ /** Called when a chip is deleted (backspace or forward delete) */
394
+ onChipDelete?: (chip: ChipSegment) => void;
395
+ /** Called when a URL link is clicked. Receives the URL string. */
396
+ onLinkClick?: (url: string) => void;
397
+ /** Called after content is pasted. Receives the resulting segments and the paste source. */
518
398
  onPaste?: (data: {
519
399
  segments: Segment[];
520
400
  source: 'internal' | 'external';
521
- }) => void; /** Called after an undo operation. Receives the restored segments. */
522
- onUndo?: (segments: Segment[]) => void; /** Called after a redo operation. Receives the restored segments. */
523
- onRedo?: (segments: Segment[]) => void; /** Minimum height in pixels */
524
- minHeight?: number; /** Maximum height in pixels */
401
+ }) => void;
402
+ /** Called after an undo operation. Receives the restored segments. */
403
+ onUndo?: (segments: Segment[]) => void;
404
+ /** Called after a redo operation. Receives the restored segments. */
405
+ onRedo?: (segments: Segment[]) => void;
406
+ /** Minimum height in pixels */
407
+ minHeight?: number;
408
+ /** Maximum height in pixels */
525
409
  maxHeight?: number;
526
410
  /**
527
411
  * Maximum number of plain-text characters allowed, enforced on typed input:
@@ -534,19 +418,32 @@ type PromptAreaProps = {
534
418
  * bypass it, so a programmatic write can exceed the cap until the next
535
419
  * keystroke truncates.
536
420
  */
537
- maxLength?: number; /** Auto-focus on mount */
538
- autoFocus?: boolean; /** When true, the area auto-grows to fit content on focus and shrinks on blur */
539
- autoGrow?: boolean; /** Accessible label for the input */
540
- 'aria-label'?: string; /** data-test-id for e2e testing */
541
- 'data-test-id'?: string; /** Array of image attachments to display */
542
- images?: PromptAreaImage[]; /** Where to render the image strip relative to the text area. Defaults to 'above'. */
543
- imagePosition?: 'above' | 'below'; /** Called when the user pastes an image from clipboard. Receives the File object. */
544
- onImagePaste?: (file: File) => void; /** Called when the user clicks the remove button on an image */
545
- onImageRemove?: (image: PromptAreaImage) => void; /** Called when the user clicks an image thumbnail */
546
- onImageClick?: (image: PromptAreaImage) => void; /** Array of file attachments to display */
547
- files?: PromptAreaFile[]; /** Where to render the file strip relative to the text area. Defaults to 'above'. */
548
- filePosition?: 'above' | 'below'; /** Called when the user clicks the remove button on a file */
549
- onFileRemove?: (file: PromptAreaFile) => void; /** Called when the user clicks a file attachment */
421
+ maxLength?: number;
422
+ /** Auto-focus on mount */
423
+ autoFocus?: boolean;
424
+ /** When true, the area auto-grows to fit content on focus and shrinks on blur */
425
+ autoGrow?: boolean;
426
+ /** Accessible label for the input */
427
+ 'aria-label'?: string;
428
+ /** data-test-id for e2e testing */
429
+ 'data-test-id'?: string;
430
+ /** Array of image attachments to display */
431
+ images?: PromptAreaImage[];
432
+ /** Where to render the image strip relative to the text area. Defaults to 'above'. */
433
+ imagePosition?: 'above' | 'below';
434
+ /** Called when the user pastes an image from clipboard. Receives the File object. */
435
+ onImagePaste?: (file: File) => void;
436
+ /** Called when the user clicks the remove button on an image */
437
+ onImageRemove?: (image: PromptAreaImage) => void;
438
+ /** Called when the user clicks an image thumbnail */
439
+ onImageClick?: (image: PromptAreaImage) => void;
440
+ /** Array of file attachments to display */
441
+ files?: PromptAreaFile[];
442
+ /** Where to render the file strip relative to the text area. Defaults to 'above'. */
443
+ filePosition?: 'above' | 'below';
444
+ /** Called when the user clicks the remove button on a file */
445
+ onFileRemove?: (file: PromptAreaFile) => void;
446
+ /** Called when the user clicks a file attachment */
550
447
  onFileClick?: (file: PromptAreaFile) => void;
551
448
  /**
552
449
  * Called on keydown before PromptArea's own handling. Call `preventDefault()`
@@ -571,18 +468,25 @@ type PromptAreaProps = {
571
468
  * to make Enter insert a newline instead (e.g. on touch devices where submit
572
469
  * is a dedicated button).
573
470
  */
574
- submitOnEnter?: boolean; /** Forwarded to the editable element. */
575
- spellCheck?: boolean; /** Forwarded to the editable element as `aria-describedby`. */
471
+ submitOnEnter?: boolean;
472
+ /** Forwarded to the editable element. */
473
+ spellCheck?: boolean;
474
+ /** Forwarded to the editable element as `aria-describedby`. */
576
475
  'aria-describedby'?: string;
577
476
  };
578
477
  /**
579
478
  * Ref handle exposed by PromptArea via useImperativeHandle.
580
479
  */
581
480
  type PromptAreaHandle = {
582
- /** Focus the editable area */focus: () => void; /** Blur the editable area */
583
- blur: () => void; /** Insert a chip at the current cursor position */
584
- insertChip: (chip: Omit<ChipSegment, 'type'>) => void; /** Get the current plain text (without chip markup) */
585
- getPlainText: () => string; /** Clear all content */
481
+ /** Focus the editable area */
482
+ focus: () => void;
483
+ /** Blur the editable area */
484
+ blur: () => void;
485
+ /** Insert a chip at the current cursor position */
486
+ insertChip: (chip: Omit<ChipSegment, 'type'>) => void;
487
+ /** Get the current plain text (without chip markup) */
488
+ getPlainText: () => string;
489
+ /** Clear all content */
586
490
  clear: () => void;
587
491
  /**
588
492
  * Replace all content with plain text (chips dropped), caret moved to the
@@ -593,14 +497,19 @@ type PromptAreaHandle = {
593
497
  * Append plain text at the end (existing chips preserved), caret moved to the
594
498
  * end. Not capped by `maxLength` (see its docs); undoable.
595
499
  */
596
- appendText: (text: string) => void; /** Caret offset in plain-text characters, or null when unavailable. */
597
- getCursorPosition: () => number | null; /** Move the caret to a plain-text offset. */
598
- setCursorPosition: (offset: number) => void; /** Move the caret to the end of the content. */
599
- setCursorToEnd: () => void; /** Current selection as plain-text offsets, or null when there is none. */
500
+ appendText: (text: string) => void;
501
+ /** Caret offset in plain-text characters, or null when unavailable. */
502
+ getCursorPosition: () => number | null;
503
+ /** Move the caret to a plain-text offset. */
504
+ setCursorPosition: (offset: number) => void;
505
+ /** Move the caret to the end of the content. */
506
+ setCursorToEnd: () => void;
507
+ /** Current selection as plain-text offsets, or null when there is none. */
600
508
  getSelection: () => {
601
509
  start: number;
602
510
  end: number;
603
- } | null; /** Set the selection between two plain-text offsets. */
511
+ } | null;
512
+ /** Set the selection between two plain-text offsets. */
604
513
  setSelection: (start: number, end: number) => void;
605
514
  };
606
515
  //#endregion
@@ -630,69 +539,41 @@ type PromptAreaHandle = {
630
539
  * />
631
540
  * ```
632
541
  */
633
- declare function PromptArea({
634
- value,
635
- onChange,
636
- triggers,
637
- placeholder,
638
- className,
639
- disabled,
640
- markdown,
641
- normalizeBullets,
642
- onSubmit,
643
- onEscape,
644
- onChipClick,
645
- onChipAdd,
646
- onChipDelete,
647
- onLinkClick,
648
- onPaste,
649
- onUndo,
650
- onRedo,
651
- minHeight,
652
- maxHeight,
653
- autoFocus,
654
- autoGrow,
655
- 'aria-label': ariaLabel,
656
- 'data-test-id': dataTestId,
657
- images,
658
- imagePosition,
659
- onImagePaste,
660
- onImageRemove,
661
- onImageClick,
662
- files,
663
- filePosition,
664
- onFileRemove,
665
- onFileClick,
666
- onKeyDown,
667
- onBlur,
668
- onRawPaste,
669
- submitOnEnter,
670
- spellCheck,
671
- maxLength,
672
- 'aria-describedby': ariaDescribedBy,
673
- ref
674
- }: PromptAreaProps & {
542
+ declare function PromptArea({ value, onChange, triggers, placeholder, className, disabled, markdown, normalizeBullets, onSubmit, onEscape, onChipClick, onChipAdd, onChipDelete, onLinkClick, onPaste, onUndo, onRedo, minHeight, maxHeight, autoFocus, autoGrow, 'aria-label': ariaLabel, 'data-test-id': dataTestId, images, imagePosition, onImagePaste, onImageRemove, onImageClick, files, filePosition, onFileRemove, onFileClick, onKeyDown, onBlur, onRawPaste, submitOnEnter, spellCheck, maxLength, 'aria-describedby': ariaDescribedBy, ref }: PromptAreaProps & {
675
543
  ref?: React.Ref<PromptAreaHandle>;
676
- }): _$react.JSX.Element;
544
+ }): import("react").JSX.Element;
677
545
  //#endregion
678
546
  //#region src/components/prompt-area/use-prompt-area-state.d.ts
679
547
  type UsePromptAreaStateOptions = {
680
- /** Initial segment value. Defaults to `[]`. */initialValue?: Segment[];
548
+ /** Initial segment value. Defaults to `[]`. */
549
+ initialValue?: Segment[];
681
550
  };
682
551
  type PromptAreaBind = {
683
- /** Ref to attach to PromptArea — gives access to imperative methods. */ref: React.RefObject<PromptAreaHandle | null>; /** Current segment array — pass as `value` prop. */
684
- value: Segment[]; /** Setter — pass as `onChange` prop. */
552
+ /** Ref to attach to PromptArea — gives access to imperative methods. */
553
+ ref: React.RefObject<PromptAreaHandle | null>;
554
+ /** Current segment array — pass as `value` prop. */
555
+ value: Segment[];
556
+ /** Setter — pass as `onChange` prop. */
685
557
  onChange: (segments: Segment[]) => void;
686
558
  };
687
559
  type PromptAreaState = {
688
- /** Props to spread directly onto `<PromptArea {...bind} />`. Contains ref, value, and onChange. */bind: PromptAreaBind; /** Derived plain text representation of the current value. */
689
- plainText: string; /** `true` when the value is empty or whitespace-only. */
690
- isEmpty: boolean; /** `true` when the value contains at least one chip. */
691
- hasChips: boolean; /** All chip segments in the current value. */
692
- chips: ChipSegment[]; /** Clear all content (both state and the editor DOM). */
693
- clear: () => void; /** Focus the editor. */
694
- focus: () => void; /** Blur the editor. */
695
- blur: () => void; /** Insert a chip at the current cursor position. */
560
+ /** Props to spread directly onto `<PromptArea {...bind} />`. Contains ref, value, and onChange. */
561
+ bind: PromptAreaBind;
562
+ /** Derived plain text representation of the current value. */
563
+ plainText: string;
564
+ /** `true` when the value is empty or whitespace-only. */
565
+ isEmpty: boolean;
566
+ /** `true` when the value contains at least one chip. */
567
+ hasChips: boolean;
568
+ /** All chip segments in the current value. */
569
+ chips: ChipSegment[];
570
+ /** Clear all content (both state and the editor DOM). */
571
+ clear: () => void;
572
+ /** Focus the editor. */
573
+ focus: () => void;
574
+ /** Blur the editor. */
575
+ blur: () => void;
576
+ /** Insert a chip at the current cursor position. */
696
577
  insertChip: (chip: Omit<ChipSegment, 'type'>) => void;
697
578
  };
698
579
  declare function usePromptAreaState(options?: UsePromptAreaStateOptions): PromptAreaState;
@@ -700,7 +581,8 @@ declare function usePromptAreaState(options?: UsePromptAreaStateOptions): Prompt
700
581
  //#region src/components/prompt-area/trigger-presets.d.ts
701
582
  type TriggerPresetOptions = Omit<Partial<TriggerConfig>, 'char' | 'position' | 'mode'>;
702
583
  type MentionTriggerOptions = TriggerPresetOptions & {
703
- /** Override the trigger character. Defaults to `'@'`. */char?: string;
584
+ /** Override the trigger character. Defaults to `'@'`. */
585
+ char?: string;
704
586
  };
705
587
  /**
706
588
  * Creates a **mention** trigger (`@`).
@@ -710,7 +592,8 @@ type MentionTriggerOptions = TriggerPresetOptions & {
710
592
  */
711
593
  declare function mentionTrigger(opts?: MentionTriggerOptions): TriggerConfig;
712
594
  type CommandTriggerOptions = TriggerPresetOptions & {
713
- /** Override the trigger character. Defaults to `'/'`. */char?: string;
595
+ /** Override the trigger character. Defaults to `'/'`. */
596
+ char?: string;
714
597
  /**
715
598
  * Where the command trigger is valid. Defaults to `'any'`, so commands fire
716
599
  * anywhere a `/` follows whitespace — not just at the start of a line.
@@ -730,7 +613,8 @@ type CommandTriggerOptions = TriggerPresetOptions & {
730
613
  */
731
614
  declare function commandTrigger(opts?: CommandTriggerOptions): TriggerConfig;
732
615
  type HashtagTriggerOptions = TriggerPresetOptions & {
733
- /** Override the trigger character. Defaults to `'#'`. */char?: string;
616
+ /** Override the trigger character. Defaults to `'#'`. */
617
+ char?: string;
734
618
  };
735
619
  /**
736
620
  * Creates a **hashtag / tag** trigger (`#`).
@@ -763,591 +647,172 @@ type ToolCallItem$1 = Extract<TranscriptItem, {
763
647
  kind: 'tool_call';
764
648
  }>;
765
649
  //#endregion
766
- //#region src/components/terminal/row.d.ts
767
- /**
768
- * The primitives every terminal row is built from.
769
- *
770
- * There are three, and that is the whole vocabulary: a {@link Row} (a gutter
771
- * cell and a body cell), a {@link Blank} (one empty line), and a {@link Band} (a
772
- * run of rows carrying a full-bleed background). Anything the theme draws — a
773
- * message, a tool call, a diff hunk, an approval prompt — is some arrangement of
774
- * those, which is what keeps the grid a property of the renderer rather than a
775
- * thing each component re-derives.
776
- *
777
- * Geometry is in `styles/terminal.css`. These components choose a class, a
778
- * marker and a tone; they never carry a measurement.
779
- */
780
- /** The palette, as a name. See the `[data-tone]` rules in `terminal.css`. */
781
- type Tone = 'fg' | 'bright' | 'dim' | 'faint' | 'mark' | 'blue' | 'green' | 'red' | 'yellow' | 'magenta';
782
- interface RowProps extends Omit<HTMLAttributes<HTMLDivElement>, 'children'> {
783
- /**
784
- * What sits in the gutter — `●`, `⎿`, `>`, a list bullet, or nothing. Kept to
785
- * the width of the gutter (`--term-cell`, two columns by default): a wider
786
- * marker would push its own body off the column every other row starts on.
787
- * Omitted, the gutter is still drawn as empty space, so an unmarked row's
788
- * text lines up with a marked one's.
789
- */
790
- glyph?: ReactNode;
791
- /** The marker's colour. Defaults to dim — the marker is structure, not content. */
792
- glyphTone?: Tone;
793
- /** The body's colour. */
794
- tone?: Tone;
795
- bold?: boolean;
796
- /** Indent levels, one character cell each. A child row's marker then sits
797
- * exactly under its parent row's first letter. */
798
- indent?: 0 | 1 | 2 | 3;
799
- /**
800
- * Gutter width in columns, when the marker needs other than two — an ordered
801
- * list's `10.` is four, a prompt's `❯ 1.` is five, and a framed payload wants
802
- * `0`. Changes only this row's split, so the body still starts on a whole
803
- * column.
804
- */
805
- columns?: number;
806
- children?: ReactNode;
807
- }
808
- declare function Row({
809
- glyph,
810
- glyphTone,
811
- tone,
812
- bold,
813
- indent,
814
- columns,
815
- className,
816
- children,
817
- style,
818
- ...props
819
- }: RowProps): _$react.JSX.Element;
820
- /**
821
- * One empty line — the theme's only vertical spacing.
822
- *
823
- * A terminal separates blocks with a blank line, not with padding, and saying it
824
- * that way has a practical payoff: spacing is part of the row list, so it can be
825
- * decided by whoever knows whether two blocks belong together (a tool call and
826
- * its output do not get one; two assistant turns do), instead of by a margin
827
- * rule that cannot tell them apart.
828
- */
829
- declare function Blank(): _$react.JSX.Element;
830
- /**
831
- * A run of rows under a background: a code block, a command's output, a diff
832
- * hunk. Full-bleed — the wash reaches the scroller's edges, because in a
833
- * terminal the line is the full width of the screen. See `--term-bleed` on
834
- * {@link TerminalSurface}.
835
- */
836
- declare function Band({
837
- className,
838
- ...props
839
- }: HTMLAttributes<HTMLDivElement>): _$react.JSX.Element;
840
- /** Inline colour/weight inside a row's body. */
841
- declare function Ink({
842
- tone,
843
- bold,
844
- className,
845
- ...props
846
- }: HTMLAttributes<HTMLSpanElement> & {
847
- tone?: Tone;
848
- bold?: boolean;
849
- }): _$react.JSX.Element;
850
- //#endregion
851
650
  //#region src/components/agent/Transcript.d.ts
852
651
  interface TranscriptProps {
853
652
  state: TranscriptState;
854
- /** Builds the download URL for a delivered file (see FileCard). Typically
855
- * `(path) => client.sessionFileUrl(sessionId, path)`. */
856
653
  fileUrl?: (path: string) => string;
857
- /** Builds the URL for an uploaded attachment. Typically
858
- * `(id) => client.attachmentUrl(sessionId, id)`. Same-origin and
859
- * cookie-authenticated, which is what lets an `<img src>` render one. */
860
654
  attachmentUrl?: (attachmentId: string) => string;
861
- /** Whether this gateway serves `@file` search here — the empty state must not
862
- * advertise an affordance the composer doesn't have. */
863
655
  canBrowseFiles?: boolean;
864
- /** Reads a host file as a data URL, for tool calls whose output is a picture
865
- * on the host (codex's `image_gen`). Omit and those cards name the path. */
866
656
  hostImage?: (path: string) => Promise<string | undefined>;
867
- /**
868
- * How a turn is drawn: `cards` (default, the chat convention) or `terminal`,
869
- * which is not a set of branches in these components but its own renderer.
870
- * See {@link TranscriptVariant}.
871
- */
872
657
  variant?: TranscriptVariant;
873
- /**
874
- * How much air each row gets: `comfortable` (default — a blank line between
875
- * messages, as the Claude Code CLI does) or `compact`. Independent of
876
- * {@link TranscriptVariant}. See {@link TranscriptDensity}.
877
- */
878
658
  density?: TranscriptDensity;
879
- /** Terminal theme only: the character cell, in whole pixels. See
880
- * {@link TerminalSurface}. */
881
659
  fontSize?: number;
882
660
  lineHeight?: number;
883
- /** Terminal theme only: the pointer affordances a real terminal cannot offer.
884
- * `false` for none. See {@link TerminalAffordances}. */
885
661
  affordances?: TerminalAffordances | boolean;
886
- /** Hold the prompt of the turn being read at the top of the scroller. Works
887
- * in both variants: the terminal clips to one line, cards shows a frosted
888
- * bar. The *real* row is pinned, not a copy — see `TranscriptRows`. */
889
662
  stickyPrompt?: boolean;
890
- /**
891
- * Mount the overview scrubber — a 12px rail of marks (your prompts, each
892
- * turn's response and result as one mark, errors, the pending approval, the
893
- * catch-up boundary) over the scroller's right edge. Two rails behind one
894
- * prop: under `terminal` it is the pixel-exact ruler that replaces the
895
- * native scrollbar (positions ride the height calculator; drag scrubs), and
896
- * under `cards` it is the **proportional annotation rail** — positioned by
897
- * `itemIndex / items.length`, because proportional text gives the
898
- * calculator no claim there — where the native scrollbar stays and the rail
899
- * only peeks and jumps. With `affordances={false}` either rail degrades to
900
- * passive paint — no drag, peek or click.
901
- */
902
663
  scrubber?: boolean;
903
- /**
904
- * Bookmarked item indices, painted as full-width marks on the rail. Paint
905
- * only, deliberately: the store — and the affordance that writes it — is
906
- * the client's, the way the unread watermarks are, not the panel's.
907
- */
908
- scrubberMarks?: readonly number[];
909
- /**
910
- * The attach replay is still landing (`useClaudeSession().replaying`): rows
911
- * render, measure and pin exactly as normal but nothing paints, and a loading
912
- * line shows in their place; when it flips false the settled tail appears in
913
- * one frame. Hiding is by *visibility*, never by not mounting — see the
914
- * comment at the render site. Optional: an embedder that never passes it
915
- * gets today's behaviour, and a short or empty session holds for no visible
916
- * time at all (the frame between attach and replay-complete).
917
- */
664
+ bookmarks?: readonly string[];
918
665
  replaying?: boolean;
919
- /**
920
- * Catch-up: `from` is how many items had been seen last time, `since` when
921
- * that was. A recap row is drawn at that boundary and everything above it is
922
- * dimmed. Omit (or pass a boundary at/after the end) and the transcript
923
- * renders exactly as before.
924
- */
925
666
  catchUp?: {
926
667
  from: number;
927
668
  since?: number;
928
669
  };
929
- /**
930
- * Filled with a closure that scrolls the recap row into view — the seam the
931
- * panel's catch-up strip presses. A ref rather than a DOM query because the
932
- * rows are virtualized: when the recap row isn't mounted, only the
933
- * virtualizer knows where it would be. Optional; embedders without a
934
- * catch-up strip never touch it. `null` while no transcript is mounted.
935
- */
936
670
  jumpToRecapRef?: RefObject<(() => void) | null>;
937
- /**
938
- * Filled with a closure that re-pins the transcript to the bottom, so a host
939
- * can resume following after the reader has scrolled away. The panel presses
940
- * it on send: choosing to say something is choosing to watch what happens
941
- * next, and a transcript left parked where you were reading makes a sent
942
- * message look like it did nothing at all.
943
- */
944
671
  repinRef?: RefObject<(() => void) | null>;
945
- /**
946
- * Scroll a tool call into view — bump `nonce` to ask again for the same one.
947
- *
948
- * The seam a *list* needs: sub-agent work is nested inside the `Task` call
949
- * that spawned it, so "open that sub-agent" can only ever mean "take me to its
950
- * row". A `parentToolUseId` works here as well as the Task's own id, since the
951
- * lookup resolves an absorbed child to the row that folded it.
952
- *
953
- * A prop rather than a ref (the shape `jumpToRecapRef` uses) because the asker
954
- * is outside this webview entirely and the request travels as data; a ref
955
- * would need a live closure at the other end of a postMessage bridge.
956
- */
957
672
  reveal?: {
958
673
  toolUseId: string;
959
674
  nonce: number;
960
675
  };
961
- /**
962
- * Render **only** the work one sub-agent did, rather than the conversation —
963
- * the sub-agent takeover's frame.
964
- *
965
- * Membership is `subagentItems` (`terminal/blocks.ts`), which is also the rule
966
- * iOS will mirror: everything the agent produced, and not the spawning `Task`
967
- * call itself, which *is* the frame rather than a row in it.
968
- *
969
- * Features are switched off internally whenever it is set, and the gate lives
970
- * here rather than at the call site on purpose: each is keyed to a
971
- * **full-transcript item index**, so a host that passed a frame and a catch-up
972
- * boundary together would not be making a strange choice, it would be making
973
- * an incoherent one. Those are the catch-up boundary and its recap row, the
974
- * sticky prompt, `reveal`, and the scrubber's **bookmarks** (host indices in
975
- * full-transcript space).
976
- *
977
- * The **scrubber itself stays**, and the distinction is the point: the rail
978
- * derives every one of its inputs from the rows it is given, and inside a
979
- * frame those are the sub-agent's own — so it marks that agent's prompts,
980
- * answers and failures at that agent's offsets. It was originally gated with
981
- * the marks, on the reasonable-looking argument that they are one feature;
982
- * they are two, and a fifty-tool agent run is exactly where a rail earns its
983
- * keep. What stays besides is everything that makes a long stream readable —
984
- * virtualization, the height epoch, the follow spring, the replay hold.
985
- */
986
676
  frame?: {
987
677
  parentToolUseId: string;
988
678
  };
989
- /**
990
- * Raise the takeover from a `Task` row. Absent draws no affordance, which is
991
- * what the plain renderer and the cards variant get: cards folds nothing, so
992
- * it has no task blocks to hang this on, and reaches the takeover from the
993
- * sessions list instead.
994
- */
995
679
  onOpenSubagent?: (toolUseId: string) => void;
996
- /**
997
- * Replaces the default empty state when the transcript has no items. Pass a
998
- * `ReactNode` to show your product's own onboarding instead of WorkerDeck's
999
- * generic "`>_` Tell the agent what to do." placeholder.
1000
- */
1001
680
  emptyState?: ReactNode;
1002
681
  className?: string;
1003
682
  }
1004
- declare function Transcript({
1005
- state,
1006
- fileUrl,
1007
- attachmentUrl,
1008
- canBrowseFiles,
1009
- hostImage,
1010
- variant,
1011
- density,
1012
- fontSize,
1013
- lineHeight,
1014
- affordances,
1015
- stickyPrompt,
1016
- scrubber,
1017
- scrubberMarks,
1018
- replaying,
1019
- catchUp,
1020
- jumpToRecapRef,
1021
- repinRef,
1022
- reveal,
1023
- frame,
1024
- onOpenSubagent,
1025
- emptyState,
1026
- className
1027
- }: TranscriptProps): _$react.JSX.Element;
683
+ declare function Transcript({ state, fileUrl, attachmentUrl, canBrowseFiles, hostImage, variant, density, fontSize, lineHeight, affordances, stickyPrompt, scrubber, bookmarks, replaying, catchUp, jumpToRecapRef, repinRef, reveal, frame, onOpenSubagent, emptyState, className }: TranscriptProps): import("react").JSX.Element;
1028
684
  //#endregion
1029
685
  //#region src/components/terminal/surface.d.ts
1030
- /**
1031
- * The root of the terminal theme: the element that establishes the character
1032
- * cell every row inside it lands on.
1033
- *
1034
- * It exists as a component rather than a class because the cell has to be *set*
1035
- * somewhere — the font, the size and the line height together are what make
1036
- * `1ch` mean one column and `--term-line` mean one row — and because that is the
1037
- * one place a host is allowed to change the metrics. Everything below this
1038
- * element measures itself in those two units and never in pixels.
1039
- *
1040
- * The geometry and the palette live in `styles/terminal.css`; this only names
1041
- * the element and hands down the two numbers.
1042
- */
1043
686
  interface TerminalSurfaceProps extends HTMLAttributes<HTMLDivElement> {
1044
- /**
1045
- * Cell size in **whole pixels**. Fractional values put every other row on a
1046
- * half-pixel: text softens and the diff bands show a seam, which is exactly
1047
- * what a grid renderer must not do. Defaults (13/18) are the CLI's own.
1048
- */
1049
687
  fontSize?: number;
1050
688
  lineHeight?: number;
1051
- /**
1052
- * How far a full-bleed band reaches past the content edge — normally the
1053
- * scroller's own horizontal padding. A band cancels it with matched negative
1054
- * margin and padding, so a diff hunk's wash runs to the viewport edge the way
1055
- * a terminal's line does, instead of stopping at a gutter.
1056
- */
1057
689
  bleed?: string;
1058
- /**
1059
- * The things a real terminal cannot do — the pointer hover fill, the
1060
- * hover-revealed copy actions. `false` turns them all off, an object picks.
1061
- * Default: all on. See {@link TerminalAffordances}; none of them costs layout,
1062
- * so switching them off changes no glyph's position.
1063
- */
1064
690
  affordances?: TerminalAffordances | boolean;
1065
691
  }
1066
- declare function TerminalSurface({
1067
- fontSize,
1068
- lineHeight,
1069
- bleed,
1070
- affordances,
1071
- className,
1072
- style,
1073
- children,
1074
- ...props
1075
- }: TerminalSurfaceProps): _$react.JSX.Element;
692
+ declare function TerminalSurface({ fontSize, lineHeight, bleed, affordances, className, style, children, ...props }: TerminalSurfaceProps): import("react").JSX.Element;
1076
693
  //#endregion
1077
694
  //#region src/components/terminal/TerminalTranscript.d.ts
1078
- /**
1079
- * The transcript, drawn as a terminal.
1080
- *
1081
- * The whole of the layout is here and it is four lines long, which is the point:
1082
- * items become row blocks, a blank line goes between blocks that do not belong
1083
- * together, and the working line is one more row at the end. There is no gap
1084
- * scale, no density knob and no variant branch — a terminal has one line height
1085
- * and one type size, and everything the theme can express is expressed in which
1086
- * rows exist and what marker each carries.
1087
- *
1088
- * Not virtualized yet: the row blocks are the part that has to be right first,
1089
- * and the existing `Transcript` already owns a hard-won virtualizer plus the
1090
- * scroll-regime rules it needs. This renders into that shell when the rows are
1091
- * settled, rather than growing a second copy of that logic.
1092
- */
1093
695
  interface TerminalTranscriptProps {
1094
696
  state: TranscriptState;
1095
- /** Builds the download URL for a delivered file. */
1096
697
  fileUrl?: (path: string) => string;
1097
- /** Cell metrics, in whole pixels. See {@link TerminalSurface}. */
1098
698
  fontSize?: number;
1099
699
  lineHeight?: number;
1100
- /** The pointer affordances a real terminal has no way to offer — hover fill,
1101
- * hover-revealed copy. `false` for none. See {@link TerminalAffordances}. */
1102
700
  affordances?: TerminalAffordances | boolean;
1103
701
  className?: string;
1104
702
  }
1105
- /**
1106
- * One transcript item as terminal rows. Exported because the virtualized shell
1107
- * in `agent/Transcript.tsx` renders rows through it: the theme owns how a row
1108
- * looks, that component owns which rows are mounted, and neither needs a copy
1109
- * of the other.
1110
- */
1111
- declare function TerminalItemView({
1112
- item,
1113
- fileUrl
1114
- }: {
703
+ declare function TerminalItemView({ item, fileUrl }: {
1115
704
  item: TranscriptItem;
1116
705
  fileUrl?: (path: string) => string;
1117
- }): _$react.JSX.Element | null;
1118
- declare function TerminalTranscript({
1119
- state,
1120
- fileUrl,
1121
- fontSize,
1122
- lineHeight,
1123
- affordances,
1124
- className
1125
- }: TerminalTranscriptProps): _$react.JSX.Element;
706
+ }): import("react").JSX.Element | null;
707
+ declare function TerminalTranscript({ state, fileUrl, fontSize, lineHeight, affordances, className }: TerminalTranscriptProps): import("react").JSX.Element;
1126
708
  //#endregion
1127
709
  //#region src/components/terminal/StatusLine.d.ts
1128
710
  interface TerminalStatusLineProps {
1129
711
  className?: string;
1130
712
  state: TranscriptState;
1131
- /** Plan windows to read from, when they should not be the session's own — the
1132
- * gateway's per-profile state merged over this transcript's. See
1133
- * {@link StatusBarProps.rateLimits}. Absent = `state.rateLimits`. */
1134
713
  rateLimits?: Record<string, RateLimitInfo>;
1135
- /** How the client is doing at reaching the gateway. Wins the status slot when
1136
- * the socket is down — see above. */
1137
714
  connection?: ConnectionState;
1138
- /** Opens the panel that answers each reading's own question. Omit and the
1139
- * reading is text rather than something to press. */
1140
715
  onOpenStatus?: () => void;
1141
716
  onOpenContext?: () => void;
1142
717
  onOpenUsage?: () => void;
1143
718
  }
1144
- declare function TerminalStatusLine({
1145
- className,
1146
- state,
1147
- rateLimits,
1148
- connection,
1149
- onOpenStatus,
1150
- onOpenContext,
1151
- onOpenUsage
1152
- }: TerminalStatusLineProps): _$react.JSX.Element;
719
+ declare function TerminalStatusLine({ className, state, rateLimits, connection, onOpenStatus, onOpenContext, onOpenUsage }: TerminalStatusLineProps): import("react").JSX.Element;
1153
720
  //#endregion
1154
721
  //#region src/components/terminal/PermissionPrompt.d.ts
1155
- /**
1156
- * The approval, as the CLI draws it: a rule, what is being asked and about what,
1157
- * the change itself, a dashed rule, the question, numbered answers, and the keys.
1158
- *
1159
- * Two things it does that the card version does not, both taken from the CLI:
1160
- *
1161
- * - **It shows the change, not the payload.** For a file edit, `old_string` and
1162
- * `new_string` are a diff — so it renders one, rather than the JSON input a
1163
- * reader would have to diff in their head. Without line numbers, necessarily:
1164
- * the edit has not happened and this client has never read the file (see
1165
- * {@link previewPatch}). Everything else falls back to the input.
1166
- * - **The heading is the engine's own sentence.** `displayName` ("Edit file")
1167
- * over `title`, never "wants to use {tool}" composed here — for codex an
1168
- * approval is an *escalation after a sandbox refusal*, and the runner has
1169
- * already written the sentence that says so.
1170
- */
1171
722
  interface TerminalPermissionPromptProps {
1172
723
  request: PermissionRequest;
1173
724
  onApprove: (requestId: string) => void;
1174
- /** `message` is fed back to the agent, which can then try something else;
1175
- * `interrupt` also stops the turn. */
1176
725
  onDeny: (requestId: string, message?: string, interrupt?: boolean) => void;
1177
726
  className?: string;
1178
727
  }
1179
- declare function TerminalPermissionPrompt({
1180
- request,
1181
- onApprove,
1182
- onDeny,
1183
- className
1184
- }: TerminalPermissionPromptProps): _$react.JSX.Element;
728
+ declare function TerminalPermissionPrompt({ request, onApprove, onDeny, className }: TerminalPermissionPromptProps): import("react").JSX.Element;
1185
729
  //#endregion
1186
730
  //#region src/components/terminal/QuestionPrompt.d.ts
1187
731
  interface TerminalQuestionPromptProps {
1188
- /** A pending permission whose toolName is 'AskUserQuestion'. */
1189
732
  request: PermissionRequest;
1190
- /** Allow the tool with `updatedInput` (the original input plus `answers`). */
1191
733
  onAnswer: (requestId: string, updatedInput: Record<string, unknown>) => void;
1192
- /** Deny the tool — the model proceeds without an answer. */
1193
734
  onDismiss: (requestId: string, message?: string) => void;
1194
735
  className?: string;
1195
736
  }
1196
- declare function TerminalQuestionPrompt({
1197
- request,
1198
- onAnswer,
1199
- onDismiss,
1200
- className
1201
- }: TerminalQuestionPromptProps): _$react.JSX.Element;
737
+ declare function TerminalQuestionPrompt({ request, onAnswer, onDismiss, className }: TerminalQuestionPromptProps): import("react").JSX.Element;
1202
738
  //#endregion
1203
739
  //#region src/components/terminal/diff.d.ts
1204
- /**
1205
- * A patch for a change that has **not happened yet** — an approval prompt's
1206
- * `Edit`, where the input names the old and new text but no line numbers exist
1207
- * because the edit has not been applied and this client has never read the file.
1208
- *
1209
- * `newStart: 0` is how it says so, and {@link TerminalDiff} reads that back: a
1210
- * diff whose hunks all start at zero renders without a number column rather than
1211
- * printing a column of zeroes or inventing an offset.
1212
- */
1213
740
  declare function previewPatch(input: unknown): FilePatch | undefined;
1214
- declare function TerminalDiff({
1215
- patch
1216
- }: {
741
+ declare function TerminalDiff({ patch }: {
1217
742
  patch: FilePatch;
1218
- }): _$react.JSX.Element;
743
+ }): import("react").JSX.Element;
1219
744
  //#endregion
1220
745
  //#region src/components/terminal/markdown.d.ts
1221
746
  interface TerminalMarkdownProps {
1222
747
  children: string;
1223
- /** Streaming text: tolerate half-written markdown (unclosed fences, half links). */
1224
748
  streaming?: boolean;
1225
749
  className?: string;
1226
750
  }
1227
- declare const TerminalMarkdown: _$react.MemoExoticComponent<({
1228
- children,
1229
- streaming,
1230
- className
1231
- }: TerminalMarkdownProps) => _$react.JSX.Element>;
751
+ declare const TerminalMarkdown: import("react").MemoExoticComponent<({ children, streaming, className }: TerminalMarkdownProps) => import("react").JSX.Element>;
752
+ //#endregion
753
+ //#region src/components/terminal/row.d.ts
754
+ type Tone = 'fg' | 'bright' | 'dim' | 'faint' | 'mark' | 'blue' | 'green' | 'red' | 'yellow' | 'magenta';
755
+ interface RowProps extends Omit<HTMLAttributes<HTMLDivElement>, 'children'> {
756
+ glyph?: ReactNode;
757
+ glyphTone?: Tone;
758
+ tone?: Tone;
759
+ bold?: boolean;
760
+ indent?: 0 | 1 | 2 | 3;
761
+ columns?: number;
762
+ children?: ReactNode;
763
+ }
764
+ declare function Row({ glyph, glyphTone, tone, bold, indent, columns, className, children, style, ...props }: RowProps): import("react").JSX.Element;
765
+ declare function Blank(): import("react").JSX.Element;
766
+ declare function Band({ className, ...props }: HTMLAttributes<HTMLDivElement>): import("react").JSX.Element;
767
+ declare function Ink({ tone, bold, className, ...props }: HTMLAttributes<HTMLSpanElement> & {
768
+ tone?: Tone;
769
+ bold?: boolean;
770
+ }): import("react").JSX.Element;
1232
771
  //#endregion
1233
772
  //#region src/components/agent/Conversation.d.ts
1234
773
  interface ConversationProps extends Omit<HTMLAttributes<HTMLDivElement>, 'children'> {
1235
774
  children: ReactNode;
1236
775
  }
1237
- /** Scroll container that stays pinned to the bottom while streaming, unless the user
1238
- * scrolls up plus a floating scroll-to-bottom button.
1239
- *
1240
- * **Nothing here animates its scroll position.** `initial` and `resize` are both
1241
- * `'instant'` and are no longer configurable: the follow spring's job is to
1242
- * *stay* at the bottom, not to travel there, and every travel a reader has ever
1243
- * complained about on this surface was an animation we asked for. The `resize`
1244
- * prop used to exist so a caller could pick, which required the caller to know
1245
- * whether the transcript was streaming or replaying — a latch's worth of
1246
- * machinery to decide something that has one right answer. */
1247
- declare function Conversation({
1248
- className,
1249
- children,
1250
- ...props
1251
- }: ConversationProps): _$react.JSX.Element;
1252
- declare function ConversationContent({
1253
- className,
1254
- children,
1255
- ...props
1256
- }: HTMLAttributes<HTMLDivElement> & {
776
+ declare function Conversation({ className, children, ...props }: ConversationProps): import("react").JSX.Element;
777
+ declare function ConversationContent({ className, children, ...props }: HTMLAttributes<HTMLDivElement> & {
1257
778
  children: ReactNode;
1258
- }): _$react.JSX.Element;
1259
- declare function ConversationScrollButton({
1260
- className
1261
- }: {
779
+ }): import("react").JSX.Element;
780
+ declare function ConversationScrollButton({ className }: {
1262
781
  className?: string;
1263
- }): _$react.JSX.Element | null;
782
+ }): import("react").JSX.Element | null;
1264
783
  //#endregion
1265
784
  //#region src/components/agent/Message.d.ts
1266
785
  interface MessageProps extends HTMLAttributes<HTMLDivElement> {
1267
786
  from: 'user' | 'assistant';
1268
787
  }
1269
- /**
1270
- * One chat turn row.
1271
- *
1272
- * `cards`: user messages sit in a bubble, assistant content is flat and
1273
- * full-width. Both are **left-aligned**: the transcript is a log read top to
1274
- * bottom, and an editor-shaped host (a full-width session view beside a sessions
1275
- * rail) has no right edge to anchor to — a bubble drifting right in a 1600px
1276
- * column separates a prompt from the reply it produced. The bubble alone is
1277
- * enough to say who spoke.
1278
- *
1279
- * The terminal theme draws none of this: it is its own renderer
1280
- * (`components/terminal/`) and mounts instead of these rows.
1281
- */
1282
- declare function Message({
1283
- from,
1284
- className,
1285
- children,
1286
- ...props
1287
- }: MessageProps): _$react.JSX.Element;
1288
- declare function MessageContent({
1289
- className,
1290
- ...props
1291
- }: HTMLAttributes<HTMLDivElement>): _$react.JSX.Element;
788
+ declare function Message({ from, className, children, ...props }: MessageProps): import("react").JSX.Element;
789
+ declare function MessageContent({ className, ...props }: HTMLAttributes<HTMLDivElement>): import("react").JSX.Element;
1292
790
  //#endregion
1293
791
  //#region src/components/agent/Response.d.ts
1294
792
  interface ResponseProps {
1295
793
  children: string;
1296
- /** Streaming text: tolerate incomplete markdown (unclosed fences, half links). */
1297
794
  streaming?: boolean;
1298
795
  className?: string;
1299
796
  }
1300
- /** Markdown renderer for assistant output streaming-safe via streamdown, code
1301
- * highlighted with shiki (dual theme follows [data-theme] through the dark: variant). */
1302
- declare const Response: _$react.MemoExoticComponent<({
1303
- children,
1304
- streaming,
1305
- className
1306
- }: ResponseProps) => _$react.JSX.Element>;
797
+ declare const Response: import("react").MemoExoticComponent<({ children, streaming, className }: ResponseProps) => import("react").JSX.Element>;
1307
798
  //#endregion
1308
799
  //#region src/components/agent/Reasoning.d.ts
1309
800
  interface ReasoningProps {
1310
801
  children: string;
1311
- /** Auto-opens while true, auto-closes shortly after it flips false. */
1312
802
  isStreaming?: boolean;
1313
803
  defaultOpen?: boolean;
1314
804
  className?: string;
1315
805
  }
1316
- /** Collapsible extended-thinking block: open while the model is thinking, tucks itself
1317
- * away once the thought is finished (unless the user toggled it manually). */
1318
- declare function Reasoning({
1319
- children,
1320
- isStreaming,
1321
- defaultOpen,
1322
- className
1323
- }: ReasoningProps): _$react.JSX.Element | null;
806
+ declare function Reasoning({ children, isStreaming, defaultOpen, className }: ReasoningProps): import("react").JSX.Element | null;
1324
807
  //#endregion
1325
808
  //#region src/components/agent/Loader.d.ts
1326
809
  interface LoaderProps {
1327
- /** Overrides the cycling verb — for a state that has one true name
1328
- * ("Starting session…"). */
1329
810
  label?: string;
1330
- /** When the current run began, for the elapsed clock. Absent = no clock.
1331
- * Unused by the card treatment; kept so the `cards` and `terminal` loaders
1332
- * take the same call site in `Transcript`. */
1333
811
  startedAt?: number;
1334
- /** Context tokens in play. Same story as `startedAt`. */
1335
812
  tokens?: number;
1336
813
  className?: string;
1337
814
  }
1338
- /**
1339
- * "The agent is working and hasn't produced output yet."
1340
- *
1341
- * Three dots pulsing in CSS — the chat convention, for the `cards` variant. The
1342
- * terminal theme has its own working line (`terminal/items.tsx`'s `WorkingRow`,
1343
- * with the mark's pulse in the gutter and the run's readings beside the verb),
1344
- * because there it is a *row of the transcript* rather than a spinner floating
1345
- * over one.
1346
- */
1347
- declare function Loader({
1348
- label,
1349
- className
1350
- }: LoaderProps): _$react.JSX.Element;
815
+ declare function Loader({ label, className }: LoaderProps): import("react").JSX.Element;
1351
816
  //#endregion
1352
817
  //#region src/components/agent/ToolCallCard.d.ts
1353
818
  type ToolCallItem = Extract<TranscriptItem, {
@@ -1355,21 +820,10 @@ type ToolCallItem = Extract<TranscriptItem, {
1355
820
  }>;
1356
821
  interface ToolCallCardProps {
1357
822
  item: ToolCallItem;
1358
- /**
1359
- * Reads a host file as a data URL, for tools whose output is a picture on the
1360
- * host. Resolves `undefined` when the gateway won't serve that path — a
1361
- * generated image saved outside the allowed roots (codex's default
1362
- * `$CODEX_HOME/generated_images/`) is one, and the card then names the path
1363
- * instead of showing it.
1364
- */
1365
823
  hostImage?: (path: string) => Promise<string | undefined>;
1366
824
  className?: string;
1367
825
  }
1368
- declare function ToolCallCard({
1369
- item,
1370
- hostImage,
1371
- className
1372
- }: ToolCallCardProps): _$react.JSX.Element;
826
+ declare function ToolCallCard({ item, hostImage, className }: ToolCallCardProps): import("react").JSX.Element;
1373
827
  //#endregion
1374
828
  //#region src/components/agent/FileCard.d.ts
1375
829
  type FileDeliveredItem = Extract<TranscriptItem, {
@@ -1377,47 +831,19 @@ type FileDeliveredItem = Extract<TranscriptItem, {
1377
831
  }>;
1378
832
  interface FileCardProps {
1379
833
  item: FileDeliveredItem;
1380
- /** Download URL for the delivered path (the server's session file route).
1381
- * Without it the card renders informational only. */
1382
834
  href?: string;
1383
835
  className?: string;
1384
836
  }
1385
- /** A file the agent handed over (`file_delivered`): name, size, download link.
1386
- * The file lives in the session's in-memory VFS — the link works while the
1387
- * session lives. */
1388
- declare function FileCard({
1389
- item,
1390
- href,
1391
- className
1392
- }: FileCardProps): _$react.JSX.Element;
837
+ declare function FileCard({ item, href, className }: FileCardProps): import("react").JSX.Element;
1393
838
  //#endregion
1394
839
  //#region src/components/agent/PermissionPrompt.d.ts
1395
840
  interface PermissionPromptProps {
1396
841
  request: PermissionRequest;
1397
842
  onApprove: (requestId: string) => void;
1398
- /** `message` is fed back to the agent, which can then try something else;
1399
- * `interrupt` also stops the turn. */
1400
843
  onDeny: (requestId: string, message?: string, interrupt?: boolean) => void;
1401
844
  className?: string;
1402
845
  }
1403
- /**
1404
- * Generic allow/deny prompt for a pending permission request.
1405
- *
1406
- * Three outcomes, not two: denying usually means "not that, try something else",
1407
- * so plain Deny lets the turn continue (with an optional reason the agent reads)
1408
- * while "Deny & stop" also interrupts.
1409
- *
1410
- * The heading is whatever the engine authored — `title`, else `displayName`.
1411
- * Composing "wants to use {tool}" instead would be wrong for codex, where an
1412
- * approval is usually an *escalation after a sandbox refusal* and the runner has
1413
- * already written the sentence that says so.
1414
- */
1415
- declare function PermissionPrompt({
1416
- request,
1417
- onApprove,
1418
- onDeny,
1419
- className
1420
- }: PermissionPromptProps): _$react.JSX.Element;
846
+ declare function PermissionPrompt({ request, onApprove, onDeny, className }: PermissionPromptProps): import("react").JSX.Element;
1421
847
  //#endregion
1422
848
  //#region src/components/agent/QuestionPrompt.d.ts
1423
849
  type QuestionBehaviorMeta = {
@@ -1425,233 +851,84 @@ type QuestionBehaviorMeta = {
1425
851
  label: string;
1426
852
  description: string;
1427
853
  };
1428
- /** The AskUserQuestion policies surfaced on job/session creation forms. */
1429
854
  declare const QUESTION_BEHAVIORS: QuestionBehaviorMeta[];
1430
- /** Extract well-formed questions from an AskUserQuestion permission request's input. */
1431
855
  declare function parseUserQuestions(input: Record<string, unknown>): UserQuestion[];
1432
856
  interface QuestionPromptProps {
1433
- /** A pending permission whose toolName is 'AskUserQuestion'. */
1434
857
  request: PermissionRequest;
1435
- /** Allow the tool with `updatedInput` (the original input plus `answers`). */
1436
858
  onAnswer: (requestId: string, updatedInput: Record<string, unknown>) => void;
1437
- /** Deny the tool — the model proceeds without an answer. */
1438
859
  onDismiss: (requestId: string, message?: string) => void;
1439
860
  className?: string;
1440
861
  }
1441
- /** Interactive form for the AskUserQuestion tool: option buttons per question
1442
- * (multi-select where the question allows it), a free-text "Other" escape hatch,
1443
- * and the focused option's preview. Falls back to nothing renderable → the caller
1444
- * should show a generic PermissionPrompt if `parseUserQuestions` finds no questions. */
1445
- declare function QuestionPrompt({
1446
- request,
1447
- onAnswer,
1448
- onDismiss,
1449
- className
1450
- }: QuestionPromptProps): _$react.JSX.Element;
862
+ declare function QuestionPrompt({ request, onAnswer, onDismiss, className }: QuestionPromptProps): import("react").JSX.Element;
1451
863
  //#endregion
1452
864
  //#region src/components/agent/Composer.d.ts
1453
- /** Files matching an `@` query, for the composer's file trigger. Structural so
1454
- * the ui package doesn't have to reach for the protocol's `HostFileMatch`. */
1455
865
  type ComposerFileMatch = {
1456
866
  path: string;
1457
867
  relative: string;
1458
868
  };
1459
- /** Imperative surface for panels that draft a message the user then finishes —
1460
- * the skills dialog's "Use this skill". Nothing here sends. */
1461
869
  type ComposerHandle = {
1462
- /** Append plain text at the caret's end and focus, separating it from
1463
- * whatever is already there. */
1464
- insertText: (text: string) => void; /** Put the caret in the field, changing nothing. */
870
+ insertText: (text: string) => void;
1465
871
  focus: () => void;
1466
872
  };
1467
873
  interface ComposerProps {
1468
- /** `attachmentIds` are the staged uploads, in the order they were picked. */
1469
874
  onSend: (text: string, attachmentIds: string[]) => void;
1470
875
  onInterrupt: () => void;
1471
876
  busy: boolean;
1472
- /** Disable input entirely (session failed/closed). */
1473
877
  disabled?: boolean;
1474
878
  placeholder?: string;
1475
- /** Slash commands offered as autocomplete; picked ones render as chips. */
1476
879
  commands?: SlashCommandInfo[];
1477
- /**
1478
- * Skills offered under a **`$`** popover of their own — codex's sigil, kept
1479
- * separate from `/` because the two behave differently. A skill is a typing
1480
- * aid, not a command: picking one inserts editable text (the skill's own
1481
- * `defaultPrompt` where it has one, else `$name`) and nothing is sent. No
1482
- * engine parses `$skillname` as syntax, which is exactly why these can never
1483
- * resolve to a chip the way `commands` do.
1484
- */
1485
880
  skills?: SkillInfo[];
1486
- /** Host-file search behind the `@` trigger. Omit to leave `@` inert — a
1487
- * gateway without host files has nothing to complete. */
1488
881
  onSearchFiles?: (query: string, options: {
1489
882
  signal: AbortSignal;
1490
883
  }) => Promise<ComposerFileMatch[]>;
1491
- /** Attachment staging (see `useAttachments`). Omit for a text-only composer. */
1492
884
  attachments?: UseAttachmentsResult;
1493
- /** Left side of the toolbar row (mode selects, …). */
1494
885
  toolbar?: ReactNode;
1495
- /**
1496
- * `'stacked'` (default) gives the buttons a row of their own under the field —
1497
- * right where a toolbar belongs. `'inline'` puts the field and the buttons on
1498
- * ONE line, growing from a single row as the message does: for a host whose
1499
- * session controls live in its own chrome (VS Code's status bar), where the
1500
- * empty composer would otherwise spend two rows saying nothing.
1501
- */
1502
886
  layout?: 'stacked' | 'inline';
1503
- /**
1504
- * Terminal theme only: the cell the composer draws on. Passed straight
1505
- * through to its own {@link TerminalSurface}, and it has to be passed — the
1506
- * composer sits outside the transcript's scroller, so it establishes a second
1507
- * surface, and a surface handed no metrics falls back to the 13/18 default. A
1508
- * host running the transcript at its editor's size and the composer at the
1509
- * default would have the caret land on a different column from the text above
1510
- * it, which is the one thing this theme exists to prevent.
1511
- */
1512
887
  fontSize?: number;
1513
888
  lineHeight?: number;
1514
- /** Terminal theme only; see {@link TerminalAffordances}. */
1515
889
  affordances?: TerminalAffordances | boolean;
890
+ /**
891
+ * Where unsent text is remembered between mounts. The composer is remounted on every session switch, so without
892
+ * this a half-written prompt dies with the switch. Omit to keep the composer stateless across mounts.
893
+ */
894
+ draft?: {
895
+ initialText: string;
896
+ save: (text: string) => void;
897
+ clear: () => void;
898
+ };
1516
899
  className?: string;
1517
900
  ref?: Ref<ComposerHandle>;
1518
901
  }
1519
- /**
1520
- * What a picked skill types into the composer.
1521
- *
1522
- * The engine's own `defaultPrompt` when it declared one — it knows what its
1523
- * skill wants to be asked — and otherwise `$name`, which is codex's native way
1524
- * of referring to a skill in prompt text: its `skill-creator` documents the form
1525
- * (`Use $skill-x at /path/to/skill-x to solve problem y`) and its own bundled
1526
- * prompts are written that way ("Use $pdf to …"). Spelling it the way the engine
1527
- * spells it beats paraphrasing into "Use the X skill to".
1528
- *
1529
- * Either way it ends in a space so the caret lands ready for the rest of the
1530
- * sentence, and either way it is ordinary text: nothing here is submitted, and
1531
- * nothing is parsed back out.
1532
- */
1533
902
  declare function skillPrompt(skill: SkillInfo): string;
1534
- /**
1535
- * Framed prompt input built on prompt-area's contentEditable.
1536
- *
1537
- * Three completions ride the same field and behave nothing alike. `/` is the
1538
- * CLI's command list and `$` is the engine's skill list — both local, so they
1539
- * filter completely and instantly; `@` is a search against the host filesystem,
1540
- * debounced and abortable so a fast typist makes one request rather than eight.
1541
- *
1542
- * `/` and `$` are separate keys rather than one merged menu, and that mirrors
1543
- * the engines themselves: codex completes skills on `$` and reserves `/` for
1544
- * commands. The behaviours differ too — a command resolves to a **chip**,
1545
- * because the CLI really does parse `/name` out of the message, while a skill
1546
- * resolves to plain editable **text**, because no engine parses `$name` as
1547
- * syntax; it is prose the model reads. Rendering them alike would promise
1548
- * something that does not happen.
1549
- *
1550
- * Files can arrive three ways — the paperclip, a drop, or a paste — because on a
1551
- * desktop all three are things people already do, and the upload starts the
1552
- * moment one lands rather than at send time.
1553
- */
1554
- declare function Composer({
1555
- onSend,
1556
- onInterrupt,
1557
- busy,
1558
- disabled,
1559
- placeholder,
1560
- commands,
1561
- skills,
1562
- onSearchFiles,
1563
- attachments,
1564
- toolbar,
1565
- layout,
1566
- fontSize,
1567
- lineHeight,
1568
- affordances,
1569
- className,
1570
- ref
1571
- }: ComposerProps): _$react.JSX.Element;
903
+ declare function Composer({ onSend, onInterrupt, busy, disabled, placeholder, commands, skills, onSearchFiles, attachments, toolbar, layout, fontSize, lineHeight, affordances, draft, className, ref }: ComposerProps): import("react").JSX.Element;
1572
904
  //#endregion
1573
905
  //#region src/components/agent/ModelSelect.d.ts
1574
906
  interface ModelSelectProps {
1575
- /** Models the session can switch to (TranscriptState.models). */
1576
907
  models: ModelOption[];
1577
- /** The session's current model id (TranscriptState.model), possibly decorated
1578
- * (e.g. "claude-fable-5[1m]") — matched leniently against the options.
1579
- * `undefined` selects the list's default row, if it has one. */
1580
908
  model?: string;
1581
- /** `undefined` = back to the CLI's default model. */
1582
909
  onModelChange: (model?: string) => void;
1583
- /** 'toolbar' (default) is the composer's compact borderless trigger;
1584
- * 'form' is a standard field-sized Select for create/settings forms. */
1585
910
  variant?: 'toolbar' | 'form';
1586
911
  disabled?: boolean;
1587
912
  className?: string;
1588
913
  }
1589
- /** Compact model switcher for the composer toolbar; fed by the `capabilities` event.
1590
- * Rows render CLI-style: bold display name with the model's description beneath. */
1591
- declare function ModelSelect({
1592
- models,
1593
- model,
1594
- onModelChange,
1595
- variant,
1596
- disabled,
1597
- className
1598
- }: ModelSelectProps): _$react.JSX.Element;
914
+ declare function ModelSelect({ models, model, onModelChange, variant, disabled, className }: ModelSelectProps): import("react").JSX.Element;
1599
915
  //#endregion
1600
916
  //#region src/components/agent/StatusBar.d.ts
1601
917
  interface StatusBarProps {
1602
918
  state: TranscriptState;
1603
- /**
1604
- * Plan windows to draw, when they should not be the session's own. The panel
1605
- * hands over the gateway's per-profile state merged over this transcript's
1606
- * reading (`mergeUsage`): a session's own `rate_limit` readings arrive only at
1607
- * a turn's edges, so one idle since yesterday would otherwise render
1608
- * yesterday's number as current. Absent = `state.rateLimits`, which is what a
1609
- * bar composed by hand outside the panel gets.
1610
- */
1611
919
  rateLimits?: Record<string, RateLimitInfo>;
1612
- /** @deprecated Pass {@link StatusBarProps.connection}; kept so an embedder
1613
- * still handing over a boolean keeps working. */
920
+ /** @deprecated Pass {@link StatusBarProps.connection}. */
1614
921
  connected?: boolean;
1615
- /** How the client is doing at reaching the gateway. A dropped socket wins the
1616
- * status slot: the session status held over a dead socket is a stale reading,
1617
- * and presenting it as a live one is the thing worth avoiding. */
1618
922
  connection?: ConnectionState;
1619
- /**
1620
- * Where the gauges lead. Each one opens the panel that answers *its* question
1621
- * — the two meters measure different things, so sending both to one "details"
1622
- * list would be a detour every time. Omit a handler and that gauge stays a
1623
- * read-only tooltip.
1624
- */
1625
923
  onOpenStatus?: () => void;
1626
924
  onOpenContext?: () => void;
1627
925
  onOpenUsage?: () => void;
1628
- /**
1629
- * The session's own controls (model, permission mode), for
1630
- * `controlsSurface: 'status'`. They sit at the end of the readings cluster —
1631
- * status, context, usage, then what you can *change* — rather than out by the
1632
- * actions menu, because they belong with the session facts they act on.
1633
- */
1634
926
  controls?: ReactNode;
1635
- /** Trailing slot — the session-actions menu, at the bar's trailing edge. */
1636
927
  actions?: ReactNode;
1637
- /** Which edge the bar sits on, so its separating rule goes on the other side.
1638
- * Placement is the panel's decision; this only styles it. */
1639
928
  placement?: 'top' | 'bottom';
1640
929
  className?: string;
1641
930
  }
1642
- declare function StatusBar({
1643
- state,
1644
- rateLimits,
1645
- connected,
1646
- connection,
1647
- onOpenStatus,
1648
- onOpenContext,
1649
- onOpenUsage,
1650
- controls,
1651
- actions,
1652
- placement,
1653
- className
1654
- }: StatusBarProps): _$react.JSX.Element;
931
+ declare function StatusBar({ state, rateLimits, connected, connection, onOpenStatus, onOpenContext, onOpenUsage, controls, actions, placement, className }: StatusBarProps): import("react").JSX.Element;
1655
932
  //#endregion
1656
933
  //#region src/components/agent/ContextDialog.d.ts
1657
934
  interface ContextDialogProps {
@@ -1660,97 +937,28 @@ interface ContextDialogProps {
1660
937
  onOpenChange: (open: boolean) => void;
1661
938
  className?: string;
1662
939
  }
1663
- /**
1664
- * What is in the model's context window right now, category by category.
1665
- *
1666
- * One of the three panels the status bar opens. Context, usage and session info
1667
- * are different questions asked at different moments, so they are different
1668
- * screens rather than one "details" list you scroll past two answers to reach.
1669
- */
1670
- declare function ContextDialog({
1671
- usage,
1672
- open,
1673
- onOpenChange,
1674
- className
1675
- }: ContextDialogProps): _$react.JSX.Element;
940
+ declare function ContextDialog({ usage, open, onOpenChange, className }: ContextDialogProps): import("react").JSX.Element;
1676
941
  //#endregion
1677
942
  //#region src/components/agent/UsageDialog.d.ts
1678
943
  interface UsageDialogProps {
1679
- /**
1680
- * Windows in reading order — session, weekly, then per-model weeklies.
1681
- *
1682
- * `updatedAt`/`inferredReset` ride each window because the readings no longer
1683
- * share one clock: the panel merges the gateway's per-profile state over this
1684
- * session's, so a `five_hour` learned from a sibling session two minutes ago
1685
- * can sit beside a `seven_day` this session last heard about yesterday.
1686
- * `inferredReset` marks the ones the *gateway* zeroed because their own reset
1687
- * time passed with nothing newer — a floor, not a report.
1688
- */
1689
944
  rateLimits: UsageWindowRow[];
1690
- /** claude.ai plan behind the windows ('max', 'pro', …), when there is one. */
1691
945
  subscriptionType?: string;
1692
946
  engine: ProfileEngine;
1693
947
  totalCostUsd: number;
1694
- /** When the *freshest* of the windows was read, for the footer line. Readings
1695
- * arrive one per turn at best (and for an idle session, not at all), so a
1696
- * stale one is normal and worth saying out loud. */
1697
948
  updatedAt?: number;
1698
949
  open: boolean;
1699
950
  onOpenChange: (open: boolean) => void;
1700
951
  className?: string;
1701
952
  }
1702
- /**
1703
- * The session's view of the plan: every window as a meter (see
1704
- * {@link UsageMeters}), the plan tier, and what this session itself has cost.
1705
- */
1706
- declare function UsageDialog({
1707
- rateLimits,
1708
- subscriptionType,
1709
- engine,
1710
- totalCostUsd,
1711
- updatedAt,
1712
- open,
1713
- onOpenChange,
1714
- className
1715
- }: UsageDialogProps): _$react.JSX.Element;
953
+ declare function UsageDialog({ rateLimits, subscriptionType, engine, totalCostUsd, updatedAt, open, onOpenChange, className }: UsageDialogProps): import("react").JSX.Element;
1716
954
  //#endregion
1717
955
  //#region src/components/agent/UsageMeters.d.ts
1718
- /**
1719
- * Ticking clock — the countdowns and the pace markers both move with it, and a
1720
- * minute is the finest resolution either of them prints.
1721
- *
1722
- * `active` is what a dialog passes its `open`: a closed panel's clock is a timer
1723
- * re-rendering something nobody can see.
1724
- */
1725
956
  declare function useMinuteClock(active?: boolean): number;
1726
- /**
1727
- * The plan's rate-limit windows, spelled out: how much of each is used, how that
1728
- * compares to the pace that would spend the window exactly, and when it resets.
1729
- *
1730
- * The pace marker is the point. A bar alone says "17% used", which is only
1731
- * alarming or reassuring once you know how far into the week you are — so every
1732
- * window draws a tick at the elapsed share of its duration. Left of the tick is
1733
- * under budget, right of it is ahead of it. The duration comes from the window
1734
- * key (5h, 7d) because the engine reports a reset time and a percentage and
1735
- * never a duration; a window whose key doesn't say gets no marker rather than a
1736
- * guessed one.
1737
- *
1738
- * Its own component rather than the Usage dialog's private helper because two
1739
- * surfaces draw these now — the session panel's Usage panel, from the session's
1740
- * readings merged with the gateway's, and the dashboard's profile page, straight
1741
- * off `ProfileInfo.usage` with no session in sight. Same account, same bars.
1742
- */
1743
- declare function UsageMeters({
1744
- windows,
1745
- now,
1746
- className
1747
- }: {
1748
- /** In reading order — protocol's `orderUsageWindows`. */windows: UsageWindowRow[];
1749
- /** A shared clock, when the caller already ticks one. Omitted, this ticks its
1750
- * own for as long as it is mounted. */
957
+ declare function UsageMeters({ windows, now, className }: {
958
+ windows: UsageWindowRow[];
1751
959
  now?: number;
1752
960
  className?: string;
1753
- }): _$react.JSX.Element;
961
+ }): import("react").JSX.Element;
1754
962
  //#endregion
1755
963
  //#region src/components/agent/SessionInfoDialog.d.ts
1756
964
  interface SessionInfoDialogProps {
@@ -1760,21 +968,7 @@ interface SessionInfoDialogProps {
1760
968
  open: boolean;
1761
969
  onOpenChange: (open: boolean) => void;
1762
970
  }
1763
- /**
1764
- * What this session *is*: engine, profile, model, mode, where it runs, which
1765
- * credentials it found, and the files it has handed over.
1766
- *
1767
- * The identity half of the session's facts. Context and usage have their own
1768
- * panels — they change every turn and are consulted mid-run, while everything
1769
- * here is fixed at creation and looked up once.
1770
- */
1771
- declare function SessionInfoDialog({
1772
- state,
1773
- client,
1774
- sessionId,
1775
- open,
1776
- onOpenChange
1777
- }: SessionInfoDialogProps): _$react.JSX.Element;
971
+ declare function SessionInfoDialog({ state, client, sessionId, open, onOpenChange }: SessionInfoDialogProps): import("react").JSX.Element;
1778
972
  //#endregion
1779
973
  //#region src/components/agent/McpDialog.d.ts
1780
974
  interface McpDialogProps {
@@ -1782,90 +976,29 @@ interface McpDialogProps {
1782
976
  sessionId: string | undefined;
1783
977
  open: boolean;
1784
978
  onOpenChange: (open: boolean) => void;
1785
- /**
1786
- * Whether this engine can reconnect/enable/disable a server
1787
- * (`EngineCapabilities.mcpServerActions`). False renders the panel read-only:
1788
- * codex reports rich status but exposes no per-server action, and buttons
1789
- * that 501 are worse than buttons that aren't there.
1790
- */
1791
979
  canManageServers?: boolean;
1792
980
  className?: string;
1793
981
  }
1794
- /**
1795
- * The session's MCP servers, at the CLI's own `/mcp` depth: servers → one server
1796
- * → its tools → one tool, with Reconnect / Enable / Disable where they apply.
1797
- *
1798
- * Two things vary by engine rather than being fixed here. **The actions** exist
1799
- * only where the engine has them (`canManageServers`): codex reports rich status
1800
- * but has no per-server reconnect or toggle, so its panel is read-only. And
1801
- * **tool parameters** appear only where the engine reports a schema — codex
1802
- * returns each tool's full JSON Schema, the Agent SDK returns none at all, so
1803
- * the tool view either renders it or says why it can't, rather than leaving a
1804
- * silent gap or claiming the absence is universal.
1805
- */
1806
- declare function McpDialog({
1807
- client,
1808
- sessionId,
1809
- open,
1810
- onOpenChange,
1811
- canManageServers,
1812
- className
1813
- }: McpDialogProps): _$react.JSX.Element;
982
+ declare function McpDialog({ client, sessionId, open, onOpenChange, canManageServers, className }: McpDialogProps): import("react").JSX.Element;
1814
983
  //#endregion
1815
984
  //#region src/components/agent/SkillsDialog.d.ts
1816
985
  interface SkillsDialogProps {
1817
986
  skills: SkillInfo[] | undefined;
1818
987
  open: boolean;
1819
988
  onOpenChange: (open: boolean) => void;
1820
- /** Insert a skill's opening message into the composer, if the host offers
1821
- * that. Omit and the dialog is read-only. */
1822
989
  onUse?: (skill: SkillInfo) => void;
1823
990
  className?: string;
1824
991
  }
1825
- /**
1826
- * What this session's engine can do beyond its own tools: the skills it found,
1827
- * grouped by where they came from, with one drilled-down view each.
1828
- *
1829
- * The framing matters more here than in most panels. A skill is **not** a
1830
- * command — the model decides to use one by reading its description, and there
1831
- * is no wire syntax that invokes it. So this screen is a *discovery* surface,
1832
- * and the one action it offers ("Use this skill") is honest about being a
1833
- * drafting aid: it types a message for the operator to edit and send.
1834
- *
1835
- * Fed from the session's `skills` event rather than a REST route, because that
1836
- * is the channel the engine refreshes on its own when a skill changes on disk.
1837
- */
1838
- declare function SkillsDialog({
1839
- skills,
1840
- open,
1841
- onOpenChange,
1842
- onUse,
1843
- className
1844
- }: SkillsDialogProps): _$react.JSX.Element;
992
+ declare function SkillsDialog({ skills, open, onOpenChange, onUse, className }: SkillsDialogProps): import("react").JSX.Element;
1845
993
  //#endregion
1846
994
  //#region src/components/agent/HostFilesDialog.d.ts
1847
995
  interface HostFilesDialogProps {
1848
996
  client: WorkerDeckClient;
1849
- /** The session's working directory — the browser is rooted here. */
1850
997
  cwd: string | undefined;
1851
998
  open: boolean;
1852
999
  onOpenChange: (open: boolean) => void;
1853
1000
  }
1854
- /**
1855
- * Browse the project the session is working in.
1856
- *
1857
- * Deliberately rooted at the session's cwd rather than at the server's
1858
- * `hostFiles.roots`: the roots are the *security* boundary (the server enforces
1859
- * them on every request), but what someone wants while watching an agent is this
1860
- * project's tree. Read-only — writing is a separate server opt-in and not
1861
- * something a session viewer should be doing behind the agent's back.
1862
- */
1863
- declare function HostFilesDialog({
1864
- client,
1865
- cwd,
1866
- open,
1867
- onOpenChange
1868
- }: HostFilesDialogProps): _$react.JSX.Element;
1001
+ declare function HostFilesDialog({ client, cwd, open, onOpenChange }: HostFilesDialogProps): import("react").JSX.Element;
1869
1002
  //#endregion
1870
1003
  //#region src/components/agent/SessionList.d.ts
1871
1004
  interface SessionListItemProps {
@@ -1875,13 +1008,7 @@ interface SessionListItemProps {
1875
1008
  onDelete?: (id: string) => void;
1876
1009
  className?: string;
1877
1010
  }
1878
- declare function SessionListItem({
1879
- session,
1880
- active,
1881
- onSelect,
1882
- onDelete,
1883
- className
1884
- }: SessionListItemProps): _$react.JSX.Element;
1011
+ declare function SessionListItem({ session, active, onSelect, onDelete, className }: SessionListItemProps): import("react").JSX.Element;
1885
1012
  interface SessionListProps {
1886
1013
  sessions: SessionInfo[];
1887
1014
  activeId?: string;
@@ -1890,606 +1017,128 @@ interface SessionListProps {
1890
1017
  emptyText?: string;
1891
1018
  className?: string;
1892
1019
  }
1893
- declare function SessionList({
1894
- sessions,
1895
- activeId,
1896
- onSelect,
1897
- onDelete,
1898
- emptyText,
1899
- className
1900
- }: SessionListProps): _$react.JSX.Element;
1020
+ declare function SessionList({ sessions, activeId, onSelect, onDelete, emptyText, className }: SessionListProps): import("react").JSX.Element;
1901
1021
  //#endregion
1902
1022
  //#region src/components/agent/SessionStatusIcon.d.ts
1903
- /**
1904
- * State as one glyph — a ringing bell when it wants a human, a spinner while it
1905
- * works, a moon when it is only sleeping. Replaces the text badge: in a sidebar
1906
- * the word costs more room than it earns, and the states that matter are the two
1907
- * you can recognise without reading.
1908
- *
1909
- * **It reads `row.state`, not `info.status`, and that distinction is the whole
1910
- * point of the row model.** `sessionState` already folds in the arm this glyph
1911
- * cannot see for itself: a *background* sub-agent outlives its turn by design,
1912
- * so the turn ends, `status` comes to rest at `idle`, and the agent keeps
1913
- * working. Reading the raw status drew a **moon on a row filed under the
1914
- * "Working" header** — the list contradicting itself on one line, which is
1915
- * exactly what a derived view model exists to prevent. The value was in scope
1916
- * and unread.
1917
- *
1918
- * The terminal statuses still come off `info.status`, because `ended` collapses
1919
- * `failed` and `closed` into one bucket and those are worth telling apart here.
1920
- *
1921
- * It lives in its own file rather than inside the dashboard's browser because
1922
- * the extension's cards draw it too, and a second copy there is how the two
1923
- * lists last disagreed about what a parked session looks like.
1924
- */
1925
- declare function SessionStatusIcon({
1926
- row,
1927
- className
1928
- }: {
1023
+ declare function SessionStatusIcon({ row, className }: {
1929
1024
  row: SessionRow;
1930
1025
  className?: string;
1931
- }): _$react.JSX.Element;
1026
+ }): import("react").JSX.Element;
1932
1027
  //#endregion
1933
1028
  //#region src/components/agent/SessionBrowser.d.ts
1934
- /**
1935
- * A sessions list with the affordances a list of thirty needs: search, facets,
1936
- * grouping, sorting, unread counts, and one honest line about what is hidden.
1937
- *
1938
- * The *rules* are `@workerdeck/protocol`'s (`filterRows`/`groupRows`/
1939
- * `subsetSummary`), not this component's — the VS Code sidebar renders the same
1940
- * model with workbench chrome, its activity-bar badge counts the same rows this
1941
- * would show, and iOS mirrors them in Swift. What lives here is the styled
1942
- * rendering of that model, so a host that wants the dashboard's look gets it
1943
- * without reimplementing the model behind it.
1944
- *
1945
- * `SessionList` remains beside this for the plain case (a fixed set of rows, no
1946
- * controls); this is what you reach for when the list is the screen.
1947
- */
1948
1029
  interface SessionBrowserProps {
1949
1030
  rows: SessionRow[];
1950
1031
  config: ViewConfig;
1951
1032
  onConfigChange: (config: ViewConfig) => void;
1952
- /** The host's own folders, if it has such a notion. Absent — a dashboard, a
1953
- * phone — makes the scope filter genuinely inert rather than empty. */
1954
1033
  scope?: WorkspaceScope;
1955
1034
  activeId?: string;
1956
- /**
1957
- * Which sub-agent the host currently has open, by tool-use id — the *finer*
1958
- * of the two selections. The card holding it drops to the secondary grey and
1959
- * that step takes the blue; see `SessionItem`. A host with no sub-agent
1960
- * surface leaves it undefined and nothing changes.
1961
- */
1962
1035
  activeSubagentId?: string;
1963
1036
  onSelect?: (row: SessionRow) => void;
1964
1037
  onDelete?: (row: SessionRow) => void;
1965
- /**
1966
- * Rename, from the row's pencil. Empty string restores the derived title. A
1967
- * gateway edit (`PATCH /sessions/:id`), never a local override — every client
1968
- * should see the same name. Omit to make titles read-only.
1969
- *
1970
- * A hover affordance rather than the extension's double-click-the-title,
1971
- * because here a single click on the row navigates: the *first* click of a
1972
- * double-click would have already left the page.
1973
- */
1974
1038
  onRename?: (row: SessionRow, title: string) => void;
1975
- /**
1976
- * Clear the conversation in place, from the row's eraser. Same session, empty
1977
- * context — **not** a delete: the engine keeps the old conversation and it
1978
- * stays resumable, which is why the row's copy never says "deleted".
1979
- *
1980
- * Rendered only where the session's own capability record allows it
1981
- * (`capabilities.clearContext`, absent = false), so a row that cannot be
1982
- * cleared has no eraser rather than one that errors. Omit the prop to have
1983
- * none at all — a host with no way to send a session command has nothing to
1984
- * hang it on (this is a WS command, not a REST route).
1985
- */
1986
1039
  onClearContext?: (row: SessionRow) => void;
1987
- /** Open a session *at* one of its sub-agents, when the host can scroll a
1988
- * transcript to a `Task` row. Absent, the sub-agent list still expands and a
1989
- * step just opens its session — see `SessionRowItemProps`. */
1990
1040
  onSelectSubagent?: (row: SessionRow, toolUseId: string) => void;
1991
- /** Open a session and travel to one of its **tasks** — see
1992
- * `SessionItem.onRevealStep`. A task has no agent behind it, so it is a place
1993
- * to go rather than a thing to open, and framing it as an agent drew an empty
1994
- * view. */
1995
1041
  onRevealStep?: (row: SessionRow, toolUseId: string) => void;
1996
- /** Rendered when nothing at all exists (as opposed to nothing matching). */
1997
1042
  emptyState?: React.ReactNode;
1998
- /**
1999
- * Whether the search + facet bar is shown. Defaults to `true` — a list that
2000
- * *is* the screen shows its controls.
2001
- *
2002
- * A host with somewhere better to put the toggle (a view title bar) passes
2003
- * `false` and owns the boolean itself, the way the VS Code extension does: the
2004
- * key lives where the commands do. Two rules come with it, and they are why
2005
- * this hides only the bar and nothing else — **closing the bar never clears
2006
- * the filters**, and the subset line below it renders either way, so a list
2007
- * filtered by a control you can't currently see still says so.
2008
- */
2009
1043
  showControls?: boolean;
2010
- /**
2011
- * Resolved project-icon bytes by content hash — `useProjectIcons`' output.
2012
- *
2013
- * Passed in rather than fetched here for the reason `ProjectIcon` states: the
2014
- * wire carries an *address*, and who can fetch it differs per client. Absent,
2015
- * or a hash not in it yet, simply draws no picture; the project's name is
2016
- * already there.
2017
- */
2018
1044
  projectIcons?: Record<string, string>;
2019
1045
  className?: string;
2020
1046
  }
2021
- /**
2022
- * How a list row is drawn, in one place, so `SidebarRow` in `web` matches this
2023
- * exactly rather than approximating it — the dashboard's other three sidebars
2024
- * are that component, and a sessions list that hovered differently from the
2025
- * gateways list beside it would read as a different product.
2026
- *
2027
- * Two rules are load-bearing:
2028
- *
2029
- * - **Fill means hover, and only hover.** It stays on the row whether or not
2030
- * the row is selected, because a selected row still has to answer the
2031
- * pointer. Selection gets the gutter instead.
2032
- * - **`ml-0` on the selected row is not cosmetic.** It hands the accent border
2033
- * the 4px the margin was holding, so the text does not shift sideways as a
2034
- * row becomes the selected one. The squared left corners are what let the bar
2035
- * sit flush against the sidebar edge.
2036
- */
2037
1047
  declare function rowShapeClass(active: boolean): string;
2038
- declare function SessionBrowser({
2039
- rows,
2040
- config,
2041
- onConfigChange,
2042
- scope,
2043
- activeId,
2044
- activeSubagentId,
2045
- onSelect,
2046
- onDelete,
2047
- onRename,
2048
- onClearContext,
2049
- onSelectSubagent,
2050
- onRevealStep,
2051
- emptyState,
2052
- showControls,
2053
- projectIcons,
2054
- className
2055
- }: SessionBrowserProps): _$react.JSX.Element;
1048
+ declare function SessionBrowser({ rows, config, onConfigChange, scope, activeId, activeSubagentId, onSelect, onDelete, onRename, onClearContext, onSelectSubagent, onRevealStep, emptyState, showControls, projectIcons, className }: SessionBrowserProps): import("react").JSX.Element;
2056
1049
  //#endregion
2057
1050
  //#region src/components/agent/SessionItem.d.ts
2058
- /**
2059
- * One session in a list — the **card**, and the only drawing of it in the
2060
- * product.
2061
- *
2062
- * The dashboard's `SessionBrowser` and the VS Code sidebar both render this;
2063
- * before it existed they rendered two hand-kept copies that agreed on the model
2064
- * and disagreed on every measurement, and the two lists read as two products.
2065
- * iOS mirrors this file's geometry rather than either copy.
2066
- *
2067
- * ## The shape
2068
- *
2069
- * A 4px-padded, 4px-rounded card whose whole surface is the hit target, holding
2070
- * two 20px lines and, when it is open, the work under them.
2071
- *
2072
- * **Line one is state and identity**: the status glyph leads, the title takes
2073
- * the rest, and the line closes with the unread badge and the context ring. The
2074
- * glyph leads because a sessions list is scanned for *state* first — which of
2075
- * these is working, which is waiting on me — and the title is what you read once
2076
- * the glyph has told you which row to read. The two readings that close the line
2077
- * are the two that change while you are looking at them.
2078
- *
2079
- * **Line two is identity and cost**: the engine's mark and its model in the
2080
- * vendor's own colour, then the project, then everything else the host wants
2081
- * said, then the age — a `·`-joined run that ends in the one part of it that
2082
- * keeps moving. The line's right edge belongs to the disclosure (which doubles
2083
- * as the count of the work below, so the card says how much there is without
2084
- * being opened) and to the host's own actions.
2085
- *
2086
- * **The gutter is one 16px cell, shared by both lines.** The two glyphs are
2087
- * different sizes and laying them out as plain flex children starts the two
2088
- * text columns at different x — two pixels, invisible as a measurement and
2089
- * obvious as a misalignment. Centring inside a fixed cell fixes the text edges
2090
- * and the ink centres at once. It is the terminal gutter's argument at card
2091
- * scale.
2092
- *
2093
- * ## Selection
2094
- *
2095
- * **Selection is the card's own fill**, not a gutter bar: the card is an inset
2096
- * shape with air around it, so filling it is unambiguous in a way a fill on a
2097
- * full-bleed row is not, and it leaves the left edge to the state glyph.
2098
- *
2099
- * There are **two selections at two grains**, and the card and its steps split
2100
- * them:
2101
- *
2102
- * | what is on screen | card | the step |
2103
- * | --- | --- | --- |
2104
- * | nothing | transparent, hovers | transparent, hovers |
2105
- * | this session | `--row-selected` (blue) | transparent, hovers |
2106
- * | one of its sub-agents | `--row-selected-weak` (grey) | `--row-selected` (blue) |
2107
- *
2108
- * **The blue always marks the finest thing selected.** Opening a sub-agent
2109
- * selects its session too, so both claims are true at once and the blue can only
2110
- * carry one; it goes to the agent, and the card steps back to grey — present,
2111
- * holding what you are looking at, not itself the thing you are looking at.
2112
- * Reversing that (blue card, blue row inside it) says nothing, which is what a
2113
- * blue-on-blue card looked like.
2114
- *
2115
- * A filled card does **not** also answer hover: the fill is already spent, and a
2116
- * selected row that lightened under the pointer read as a third state nobody
2117
- * could name. Its steps still do, on `--row-active`, which is a tint and so
2118
- * works on all three grounds.
2119
- *
2120
- * A **task** never takes the blue. It is a reference to a place inside a
2121
- * session, so pressing one selects the session and travels to its marker — see
2122
- * `StepRow`.
2123
- */
2124
1051
  interface SessionItemProps {
2125
1052
  row: SessionRow;
2126
- /** This session is the one the host is showing. */
2127
1053
  active?: boolean;
2128
- /**
2129
- * Which sub-agent is open, by `Step.key` — the *finer* of the two selections.
2130
- * When it names one of this card's agents, that step takes the blue and the
2131
- * card drops to the secondary grey. A key belonging to some other card's
2132
- * agent, or to a task, changes nothing here.
2133
- */
2134
1054
  activeStepKey?: string;
2135
- /** Shown when the list is not already grouped by gateway. */
2136
1055
  showGateway?: boolean;
2137
- /**
2138
- * False when the list is already grouped by project — the header above has
2139
- * said the name, so the card must not spend its metadata line repeating it.
2140
- * What takes the slot is the *sub-path inside the project*
2141
- * (`projectSubpath`): `packages/ui`, `packages/server` — the one thing the
2142
- * header cannot say and the only thing that tells two sessions in one repo
2143
- * apart. A session at the project root has nothing to add and the slot
2144
- * disappears entirely. Exactly the rule `showGateway` follows one facet over.
2145
- */
2146
1056
  showProject?: boolean;
2147
- /** Resolved project-icon bytes by content hash. A hash this map has not got
2148
- * yet simply draws no icon. */
2149
1057
  projectIcons?: Record<string, string>;
2150
- /** Uncontrolled by default — pass both to drive expansion from the host. */
2151
1058
  expanded?: boolean;
2152
1059
  onExpandedChange?: (expanded: boolean) => void;
2153
1060
  onSelect?: () => void;
2154
- /** Open the session *at* one of its sub-agents — hand the panel body over to
2155
- * that agent's own work. Only ever called for an **agent** step. Absent is not
2156
- * a missing feature: without it a step just opens the session, which is all a
2157
- * host with no sub-agent surface can offer. */
2158
1061
  onSelectSubagent?: (toolUseId: string) => void;
2159
- /**
2160
- * Open the session and travel to a **task**'s row in the transcript — where
2161
- * the work was started, and where it finished.
2162
- *
2163
- * A separate seam from `onSelectSubagent` because the destinations are
2164
- * different, and conflating them is not a styling detail: a task has no agent
2165
- * behind it, so framing its tool-use id selects **no items at all** and the
2166
- * panel draws an empty agent view. That was the bug. A task is a reference,
2167
- * and the only honest thing to do with a reference is follow it.
2168
- */
2169
1062
  onRevealStep?: (toolUseId: string) => void;
2170
- /** Enables in-place rename. The trigger is the host's — see `renameOn`. */
2171
1063
  onRename?: (title: string) => void;
2172
- /**
2173
- * How a rename starts. `doubleClick` is the editor feel (a rename is a thing
2174
- * you do to the word you are looking at); `external` means the host opens it
2175
- * from its own affordance — a menu entry, a pencil in `actions` — and drives
2176
- * it through `editing`/`onEditingChange`.
2177
- */
2178
1064
  renameOn?: 'doubleClick' | 'external';
2179
1065
  editing?: boolean;
2180
1066
  onEditingChange?: (editing: boolean) => void;
2181
- /** The card's trailing controls, at the end of line two. A single overflow
2182
- * glyph is what the design draws; a host with three always-on actions can put
2183
- * them here instead. */
2184
1067
  actions?: ReactNode;
2185
1068
  className?: string;
2186
1069
  }
2187
- declare function SessionItem({
2188
- row,
2189
- active,
2190
- activeStepKey,
2191
- showGateway,
2192
- showProject,
2193
- projectIcons,
2194
- expanded,
2195
- onExpandedChange,
2196
- onSelect,
2197
- onSelectSubagent,
2198
- onRevealStep,
2199
- onRename,
2200
- renameOn,
2201
- editing,
2202
- onEditingChange,
2203
- actions,
2204
- className
2205
- }: SessionItemProps): _$react.JSX.Element;
1070
+ declare function SessionItem({ row, active, activeStepKey, showGateway, showProject, projectIcons, expanded, onExpandedChange, onSelect, onSelectSubagent, onRevealStep, onRename, renameOn, editing, onEditingChange, actions, className }: SessionItemProps): import("react").JSX.Element;
2206
1071
  //#endregion
2207
1072
  //#region src/components/agent/EngineIcon.d.ts
2208
- /**
2209
- * Which mark a session wears.
2210
- *
2211
- * The two first-party engines are named directly. A `provider` session is
2212
- * whatever the host wired up, so its *model* is the only thing that says whose
2213
- * it is — sniffed loosely on purpose (`gemini-2.5-pro`, `deepseek-chat`,
2214
- * `kimi-k2`), and falling through to no mark rather than guessing wrong.
2215
- */
2216
1073
  declare function engineMark(engine: string, model?: string): string | undefined;
2217
- /** The colour a session's engine mark wears. Pass it to `EngineIcon`'s
2218
- * `className` rather than to a parent: the svg carries its own `text-fg-3`,
2219
- * and only a class on the element itself is merged over it. */
2220
1074
  declare function vendorMarkClass(engine: string, model?: string): string;
2221
- /** The colour the model *name* wears beside that mark — muted unless the vendor
2222
- * is one whose accent survives at label size. See `VENDOR_TEXT`.
2223
- *
2224
- * The fallback is `text-fg-3` rather than the metadata line's own `text-fg-4`,
2225
- * so an unbranded model still sits one step above the project and gateway
2226
- * beside it — the order the spec lists them in, held without a colour. */
2227
1075
  declare function vendorTextClass(engine: string, model?: string): string;
2228
- declare function EngineIcon({
2229
- engine,
2230
- model,
2231
- className
2232
- }: {
1076
+ declare function EngineIcon({ engine, model, className }: {
2233
1077
  engine: string;
2234
1078
  model?: string;
2235
1079
  className?: string;
2236
- }): _$react.JSX.Element;
1080
+ }): import("react").JSX.Element;
2237
1081
  //#endregion
2238
1082
  //#region src/components/agent/SessionSteps.d.ts
2239
- /**
2240
- * The work *under* a session row, and the one row shape every client renders it
2241
- * through.
2242
- *
2243
- * This lived inside the VS Code webview first, which is exactly why the
2244
- * dashboard had none of it. Nothing in here is extension-specific: a session's
2245
- * sub-agents are a protocol fact, and a disclosure over them is a list
2246
- * affordance. It sits in `packages/ui` so the sidebar, the dashboard and (in its
2247
- * own idiom) the phone are annotating rows the same way rather than three ways.
2248
- *
2249
- * Today the only source is `SessionInfo.subagents`. The other — the CLI's own
2250
- * **task checklist**, the to-do list it keeps for the current turn — is what the
2251
- * design was drawn from, and it is not built: nothing on the wire carries it yet
2252
- * (see `_docs/features/sub-agent-handling.md`, second thread, which opens with
2253
- * "check a capture" rather than "design a surface"). When it arrives it is a
2254
- * *source*, not a second row component: checklist when the session has one, its
2255
- * sub-agents otherwise.
2256
- *
2257
- * That is also why `state` has a `pending` arm no sub-agent can produce. A
2258
- * sub-agent record exists only once dispatched, so it is never queued; a to-do
2259
- * is queued for most of its life, and dropping the state would mean widening the
2260
- * union later — the shape is cheaper to state now than to retrofit.
2261
- */
2262
1083
  type Step = {
2263
1084
  key: string;
2264
- label: string; /** What one of these is called, for the disclosure's count. */
1085
+ label: string;
2265
1086
  noun: string;
2266
- /**
2267
- * Both kinds press. The kind decides **where the press goes**, which is the
2268
- * whole of the distinction.
2269
- *
2270
- * An **agent** has an identity and work of its own, so it wears the sub-agent
2271
- * colour and opens that agent's own frame. A **task** is something the model
2272
- * described with no agent behind it (`isAgentRecord`), so there is no frame:
2273
- * framing its id selects no items and draws an empty screen. What it has
2274
- * instead is a *place* — the spawning call's row in the transcript — so it is
2275
- * muted, never selected, and travels there. See `StepRow` for why an inert
2276
- * row was the worse answer.
2277
- *
2278
- * Two values and not a boolean because the checklist source this shape was
2279
- * drawn for (see above) produces the second kind natively — a to-do is a task
2280
- * in exactly this sense, and it will slot in here rather than widening
2281
- * anything.
2282
- */
2283
1087
  kind: 'agent' | 'task';
2284
- state: 'done' | 'running' | 'pending' | 'failed'; /** A trailing reading — a sub-agent's tool count. Absent draws nothing. */
1088
+ state: 'done' | 'running' | 'pending' | 'failed';
2285
1089
  detail?: string;
2286
1090
  title: string;
2287
1091
  onSelect: () => void;
2288
1092
  };
2289
- /**
2290
- * The steps under one session, **agents first**.
2291
- *
2292
- * The two kinds do different things when pressed and are worth different
2293
- * amounts of attention: an agent has work of its own to go and read, a task is a
2294
- * marker in a transcript. Interleaved in dispatch order they read as one
2295
- * undifferentiated list, and the rows you can actually open are scattered
2296
- * through it. Grouped, the openable ones are a block at the top and the markers
2297
- * are a tail you can skip.
2298
- *
2299
- * Stable **within** each group, deliberately: dispatch order is the only order
2300
- * these records have that means anything (it is the order the work was started
2301
- * in), so the sort partitions and never reorders inside a partition.
2302
- *
2303
- * `onSelect` is handed the **kind** as well as the id, because the two kinds go
2304
- * to different places — see `SessionItem`, which is what routes them. Passing
2305
- * only the id is what let a task be opened as if it were an agent, and a framed
2306
- * task id matches no items, so the panel drew an **empty agent view**.
2307
- */
2308
1093
  declare function sessionSteps(info: SessionInfo, onSelect: (toolUseId: string, kind: Step['kind']) => void): Step[];
2309
- /** How many of these are still going — the live half of the disclosure's count. */
2310
1094
  declare function runningSteps(steps: readonly Step[]): number;
2311
- /**
2312
- * The disclosure, which is also the reading: `3 agents` — or `2 of 3 agents`
2313
- * while some have settled, because "how many are still going" is the live
2314
- * question and a bare total answers it wrong the moment one finishes.
2315
- *
2316
- * Sub-agents are an annotation on a working row rather than a state of their own
2317
- * (see `runningSubagents` in protocol's `session-list.ts`), so this never
2318
- * competes with the row's status glyph: that still says what the *session* is
2319
- * doing.
2320
- */
2321
- declare function StepToggle({
2322
- expanded,
2323
- running,
2324
- total,
2325
- noun,
2326
- onToggle
2327
- }: {
1095
+ declare function StepToggle({ expanded, running, total, noun, onToggle }: {
2328
1096
  expanded: boolean;
2329
1097
  running: number;
2330
1098
  total: number;
2331
1099
  noun: string;
2332
1100
  onToggle: () => void;
2333
- }): _$react.JSX.Element;
2334
- /**
2335
- * One step under its session — **pressable, all of them**, and what a press
2336
- * means is what tells the two kinds apart.
2337
- *
2338
- * Pressing an **agent** hands the panel over to that agent's own work
2339
- * (`SessionPanel.openSubagent`): it is not a session and never becomes one, but
2340
- * it has a surface, so it can be the selected thing. Pressing a **task** selects
2341
- * the *session* and travels to that task's marker inside it — a task is a
2342
- * reference to a place in a transcript, not a thing with a screen, so it can be
2343
- * followed but never held.
2344
- *
2345
- * That is a reversal, and a deliberate one. A task used to be inert markup on
2346
- * the argument that "a disabled-looking button still announces itself as one" —
2347
- * correct about the markup, wrong about the premise, because there *was* always
2348
- * somewhere to go and the row simply swallowed the click on its way there. A row
2349
- * that looks like a list item, sits in a list, and does nothing when pressed is
2350
- * the worse lie. So every step answers the pointer and every step answers a
2351
- * press; only what the press does differs.
2352
- *
2353
- * Divided from the card's header by **indentation and its own hit shape**, not
2354
- * by a rule. The rules came first, on the argument that at 11px an indent is not
2355
- * enough to say "list inside a row" — and they were right about the reading and
2356
- * wrong about the cost: a stack of hairlines across every open card turned the
2357
- * list into a ledger, and a rule cannot answer a pointer. A step that lights up
2358
- * under the cursor and fills when it is the one on screen says *list* far more
2359
- * plainly than a line between two of them, and it says it while doing the job
2360
- * the rule could not.
2361
- *
2362
- * **Only an agent can wear the selection**, and `active` is guarded on that here
2363
- * rather than trusted from the caller: a host that hands back a task's key is
2364
- * describing where it navigated, not what it selected, and the row must not
2365
- * paint itself blue for it.
2366
- *
2367
- * The hover is `--row-active` — **alpha, not a flat fill** — because this row
2368
- * has to answer the pointer on three different grounds: a transparent card, a
2369
- * blue one (its session is selected), and a grey one (a sibling agent is). A
2370
- * flat value tuned for any of those is wrong on the other two; a tint darkens or
2371
- * lifts whatever it lands on. It is the one place in the list where the alpha
2372
- * token earns its keep.
2373
- */
2374
- declare function StepRow({
2375
- step,
2376
- active,
2377
- onSelect
2378
- }: {
1101
+ }): import("react").JSX.Element;
1102
+ declare function StepRow({ step, active, onSelect }: {
2379
1103
  step: Step;
2380
- /** The panel is showing this step's own work. Ignored for tasks, which cannot
2381
- * be the selected thing — see above. */
2382
1104
  active?: boolean;
2383
1105
  onSelect: () => void;
2384
- }): _$react.JSX.Element;
1106
+ }): import("react").JSX.Element;
2385
1107
  //#endregion
2386
1108
  //#region src/components/agent/SubagentStrip.d.ts
2387
- /**
2388
- * The one line above a sub-agent takeover: who this is, how it is doing, and the
2389
- * way back.
2390
- *
2391
- * **It claims exactly what the `TaskRow` it was opened from claims** — the same
2392
- * `taskBusy` / `taskFailed` / tool count over the same items — and deliberately
2393
- * *not* `SubagentInfo.status`. Protocol documents those two as divergent on
2394
- * purpose (`index.ts:1476-1487`), but that divergence is transcript-versus-*list*
2395
- * and this surface **is** the transcript. The disagreement that must not exist
2396
- * here is between a header and the rows directly beneath it.
2397
- *
2398
- * The rollup is still allowed one job — naming an agent whose `Task` call is not
2399
- * in the transcript — because a label is not content, and `SessionInfo.subagents`
2400
- * keeps only eight settled records (`SUBAGENT_HISTORY`), so it can never be the
2401
- * source of what a frame *shows*.
2402
- *
2403
- * Both variants, because the panel has two and a strip that only existed in one
2404
- * would make the takeover a terminal-theme feature rather than a session feature.
2405
- */
2406
- declare function SubagentStrip({
2407
- task,
2408
- items,
2409
- label,
2410
- onBack,
2411
- terminal,
2412
- fontSize,
2413
- lineHeight
2414
- }: {
2415
- /** The spawning call. Absent when the transcript does not have it — the strip
2416
- * still draws, because the way back must exist even when the content cannot. */
2417
- task: ToolCallItem$1 | undefined; /** The frame's items, for the busy reading and the tool count. */
2418
- items: readonly TranscriptItem[]; /** Fallback name when there is no task item. */
1109
+ declare function SubagentStrip({ task, items, label, onBack, terminal, fontSize, lineHeight }: {
1110
+ task: ToolCallItem$1 | undefined;
1111
+ items: readonly TranscriptItem[];
2419
1112
  label: string;
2420
1113
  onBack: () => void;
2421
1114
  terminal: boolean;
2422
1115
  fontSize?: number;
2423
1116
  lineHeight?: number;
2424
- }): _$react.JSX.Element;
1117
+ }): import("react").JSX.Element;
2425
1118
  //#endregion
2426
1119
  //#region src/components/agent/ProjectIcon.d.ts
2427
- declare function ProjectIcon({
2428
- icon,
2429
- src,
2430
- name,
2431
- className
2432
- }: {
1120
+ declare function ProjectIcon({ icon, src, name, className }: {
2433
1121
  icon: ProjectIcon$1 | undefined;
2434
- /** Resolved bytes for the `image` arm — an object URL or a data URL. The
2435
- * caller fetches (see the note above); absent draws nothing. */
2436
- src?: string; /** The project's name, for the alt text. */
1122
+ src?: string;
2437
1123
  name?: string;
2438
1124
  className?: string;
2439
- }): _$react.JSX.Element | null;
1125
+ }): import("react").JSX.Element | null;
2440
1126
  //#endregion
2441
1127
  //#region src/components/agent/SessionEmptyState.d.ts
2442
1128
  interface SessionEmptyStateProps {
2443
1129
  cwd?: string;
2444
- /** Whether `/command` completion is live yet — the CLI reports its commands a
2445
- * beat after the session starts, and promising a feature that isn't wired up
2446
- * yet is worse than not mentioning it. */
2447
1130
  hasCommands?: boolean;
2448
- /** Whether the engine has reported skills the `/` popover can offer. Its own
2449
- * flag, not a variant of `hasCommands`: what `/` does differs — a command is
2450
- * submitted, a skill is typed for you to edit — and an engine can have one
2451
- * without the other. */
2452
1131
  hasSkills?: boolean;
2453
- /** Whether this gateway serves `@file` search for the session's directory. */
2454
1132
  canBrowseFiles?: boolean;
2455
1133
  className?: string;
2456
1134
  }
2457
- /**
2458
- * What a session shows before it has said anything: where the agent is sitting,
2459
- * and what the composer accepts beyond prose.
2460
- *
2461
- * Every hint is conditional on the affordance actually existing — an engine
2462
- * without slash commands, or a gateway without host files, is not told about
2463
- * them. Deliberately no project name (the header already carries it) and no
2464
- * brand mark (its geometry is inlined in several places already and they are
2465
- * meant to stay identical).
2466
- */
2467
- declare function SessionEmptyState({
2468
- cwd,
2469
- hasCommands,
2470
- hasSkills,
2471
- canBrowseFiles,
2472
- className
2473
- }: SessionEmptyStateProps): _$react.JSX.Element;
1135
+ declare function SessionEmptyState({ cwd, hasCommands, hasSkills, canBrowseFiles, className }: SessionEmptyStateProps): import("react").JSX.Element;
2474
1136
  //#endregion
2475
1137
  //#region src/components/agent/PromptTokenText.d.ts
2476
- /**
2477
- * A sent message, with its `@file` and `/command` tokens styled the way the CLI
2478
- * writes them: monospace and tinted, no background — the bubble already has one,
2479
- * and a second fill inside it reads as a button.
2480
- *
2481
- * Literal text, never markdown: what was typed is what was sent. The one pass
2482
- * over it is this, so a message reads the same after sending as it did in the
2483
- * composer. Two tokens, two meanings — a file is a reference, a command is an
2484
- * action — so they are told apart by hue rather than by shape alone.
2485
- */
2486
- declare function PromptTokenText({
2487
- text,
2488
- className
2489
- }: {
1138
+ declare function PromptTokenText({ text, className }: {
2490
1139
  text: string;
2491
1140
  className?: string;
2492
- }): _$react.JSX.Element;
1141
+ }): import("react").JSX.Element;
2493
1142
  //#endregion
2494
1143
  //#region src/components/agent/status.d.ts
2495
1144
  declare const STATUS_META: Record<SessionStatus, {
@@ -2499,73 +1148,20 @@ declare const STATUS_META: Record<SessionStatus, {
2499
1148
  }>;
2500
1149
  //#endregion
2501
1150
  //#region src/components/agent/ContextRing.d.ts
2502
- /**
2503
- * How full a session's context window is, sized for a **list row**.
2504
- *
2505
- * The reading the session screen has always drawn, moved somewhere it answers a
2506
- * question the session screen cannot: *which* of these thirty sessions is
2507
- * bloating. That is also why it is a ring and not a number — across a list, a
2508
- * ring is read at a glance and `71%` has to be read one row at a time.
2509
- *
2510
- * **Absent draws nothing, and absent is not zero.** A promptless session, a
2511
- * parked one from before the field existed, or an engine that reports no window
2512
- * has no reading; an empty ring would claim its context is empty rather than
2513
- * unknown. The title carries the exact numbers for anyone who wants them.
2514
- *
2515
- * Shared rather than spelled per client: the dashboard's row and the VS Code
2516
- * sidebar's card both draw it, and two copies would be two sets of thresholds
2517
- * the day one of them is nudged.
2518
- */
2519
- declare function ContextRing({
2520
- usage,
2521
- size,
2522
- className
2523
- }: {
1151
+ declare function ContextRing({ usage, size, className }: {
2524
1152
  usage: ContextReading | undefined;
2525
1153
  size?: number;
2526
1154
  className?: string;
2527
- }): _$react.JSX.Element | null;
1155
+ }): import("react").JSX.Element | null;
2528
1156
  //#endregion
2529
1157
  //#region src/lib/utils.d.ts
2530
1158
  declare function cn(...inputs: ClassValue[]): string;
2531
1159
  //#endregion
2532
1160
  //#region src/lib/clipboard.d.ts
2533
- /**
2534
- * Copy text to the clipboard, on origins where the modern API does not exist.
2535
- *
2536
- * `navigator.clipboard` is gated on a **secure context**: HTTPS, or localhost.
2537
- * A WorkerDeck dashboard reached the way it is meant to be reached — plain HTTP
2538
- * on a LAN address, from a laptop or a phone — is neither, so `navigator.clipboard`
2539
- * is `undefined` there and touching `.writeText` throws outright. That is the
2540
- * normal deployment, not an edge case, which is why this falls back rather than
2541
- * feature-detecting into a disabled button.
2542
- *
2543
- * The fallback is `document.execCommand('copy')` over an off-screen textarea.
2544
- * It is deprecated and it is also the only thing that works here; every browser
2545
- * still implements it. Returns whether the text actually landed, so a caller can
2546
- * avoid claiming success it did not have.
2547
- */
2548
1161
  declare function copyText(value: string): Promise<boolean>;
2549
1162
  //#endregion
2550
1163
  //#region src/lib/tool-icon.d.ts
2551
- /**
2552
- * An icon per tool, so a transcript can be skimmed by shape rather than read.
2553
- *
2554
- * The same mapping the iOS app makes, in lucide's vocabulary rather than SF
2555
- * Symbols — the two clients should be recognisably showing the same thing. An
2556
- * unknown tool falls back to a wrench, and an MCP tool (`mcp__server__name`) to
2557
- * the puzzle piece the MCP screens use, because "which server is this from" is
2558
- * the useful thing to see at a glance.
2559
- */
2560
1164
  declare function toolIcon(toolName: string): LucideIcon;
2561
- /**
2562
- * Does this tool *change* the workspace?
2563
- *
2564
- * Worth its own colour in a transcript: skimming a run, "what did it edit" is a
2565
- * different question from "what did it look at", and a write is the one you
2566
- * might need to undo. Names from both first-party engines; an MCP tool is
2567
- * unknowable from its name, so it reads as neutral rather than guessed.
2568
- */
2569
1165
  declare function isMutatingTool(toolName: string): boolean;
2570
1166
  //#endregion
2571
1167
  export { AlertDialog, AlertDialogClose, AlertDialogContent, AlertDialogDescription, AlertDialogTitle, AlertDialogTrigger, Badge, type BadgeProps, Band, Blank, Button, type ButtonProps, Card, CardContent, CardHeader, CardTitle, type ChipSegment, CodeBlock, type CodeBlockProps, Composer, type ComposerFileMatch, type ComposerHandle, type ComposerProps, ContextDialog, type ContextDialogProps, ContextRing, Conversation, ConversationContent, type ConversationProps, ConversationScrollButton, CopyAction, CopyButton, type CopyButtonProps, Dialog, DialogBody, DialogClose, DialogContent, DialogHeader, DialogRow, DialogTrigger, Empty, EmptyKey, EngineIcon, FileCard, type FileCardProps, type FileDeliveredItem, HostFilesDialog, type HostFilesDialogProps, Ink, Input, Loader, McpDialog, type McpDialogProps, Menu, MenuContent, MenuItem, MenuSeparator, MenuTrigger, Message, MessageContent, type MessageProps, ModelSelect, type ModelSelectProps, PERMISSION_MODES, type PermissionModeChoice, type PermissionModeMeta, PermissionModeSelect, type PermissionModeSelectProps, PermissionPrompt, type PermissionPromptProps, ProgressRing, type ProgressRingProps, ProjectIcon, PromptArea, type PromptAreaHandle, type PromptAreaProps, PromptTokenText, QUESTION_BEHAVIORS, type QuestionBehaviorMeta, QuestionPrompt, type QuestionPromptProps, Reasoning, type ReasoningProps, Response, type ResponseProps, Row, type RowProps, STATUS_META, type Segment, Select, SelectContent, SelectItem, SelectItemText, SelectTrigger, SelectValue, SessionBrowser, type SessionBrowserProps, type SessionControls, SessionEmptyState, type SessionEmptyStateProps, SessionInfoDialog, type SessionInfoDialogProps, SessionItem, type SessionItemProps, SessionList, SessionListItem, type SessionListItemProps, type SessionListProps, SessionPanel, type SessionPanelProps, SessionStatusIcon, type SessionSurfacePanel, type SessionVitals, SkillsDialog, type SkillsDialogProps, Spinner, Splitter, type SplitterProps, StatusBar, type StatusBarProps, type Step, StepRow, StepToggle, SubagentStrip, type TerminalAffordances, TerminalDiff, TerminalItemView, TerminalMarkdown, type TerminalMarkdownProps, type TerminalMetrics, TerminalPermissionPrompt, type TerminalPermissionPromptProps, TerminalQuestionPrompt, type TerminalQuestionPromptProps, TerminalStatusLine, type TerminalStatusLineProps, TerminalSurface, type TerminalSurfaceProps, TerminalTranscript, type TerminalTranscriptProps, type TextSegment, Textarea, Tip, Toaster, type Tone, ToolCallCard, type ToolCallCardProps, type ToolCallItem, TooltipContent, TooltipProvider, Transcript, type TranscriptDensity, TranscriptDensityProvider, type TranscriptFont, type TranscriptProps, type TranscriptVariant, TranscriptVariantProvider, type TriggerConfig, type TriggerSuggestion, UsageDialog, type UsageDialogProps, UsageMeters, WithActions, badgeVariants, buttonVariants, cn, commandTrigger, copyText, engineMark, formatAgoPrecise, formatBytes, formatCost, formatCountdown, formatDuration, formatRateLimitWindow, formatRateLimitWindowLong, formatRelativeTime, formatTokens, friendlyModel, getChipsByTrigger, hashtagTrigger, isMutatingTool, isSegmentsEmpty, mentionTrigger, parseUserQuestions, permissionModeChoices, permissionModeMeta, plainTextToSegments, previewPatch, rateLimitWindowSeconds, rowShapeClass, runningSteps, segmentsToPlainText, sessionSteps, skillPrompt, toast, toolIcon, toolInputPreview, useAffordances, useMinuteClock, usePromptAreaState, useTranscriptDensity, useTranscriptVariant, vendorMarkClass, vendorTextClass };