@mcp-b/react-components 0.10.0 → 0.12.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/{AgentChat-B9LD_WF1.d.ts → AgentChat-CRmsKg9B.d.ts} +10 -6
- package/dist/{BrowserLiveView-ZktFZiMD.d.ts → BrowserLiveView-BV5qgFgI.d.ts} +11 -10
- package/dist/{BrowserReplay-6G-mnwcn.d.ts → BrowserReplay-xWvRjRAC.d.ts} +2 -1
- package/dist/{Menu-B5vDqZe_.d.ts → Menu-BLhnNnRK.d.ts} +3 -0
- package/dist/{ModelSelector-DXtpcRmT.js → ModelSelector-BB-xB-Es.js} +16 -13
- package/dist/{PromptInput-D6-G24p7.d.ts → PromptInput-IyM6ZETj.d.ts} +13 -45
- package/dist/ThinkChat-B3wYahor.js +190 -0
- package/dist/{ThinkChatActivity-B2UD95My.d.ts → ThinkChatActivity-F4KFPcJA.d.ts} +4 -4
- package/dist/ThinkChatContext-C3Eb1Xpi.d.ts +16 -0
- package/dist/{ThinkChatToolParts-DnUiZgCC.d.ts → ThinkChatToolParts-Cv4o7j6F.d.ts} +13 -5
- package/dist/components/AgentChat.d.ts +1 -1
- package/dist/components/AgentChat.js +57 -23
- package/dist/components/AgentConnection.d.ts +3 -14
- package/dist/components/AgentConnection.js +7 -111
- package/dist/components/Badge.js +1 -15
- package/dist/components/BrowserLiveView.d.ts +1 -1
- package/dist/components/BrowserLiveView.js +14 -10
- package/dist/components/BrowserReplay.d.ts +1 -1
- package/dist/components/BrowserRunPanel.d.ts +46 -0
- package/dist/components/BrowserRunPanel.js +159 -0
- package/dist/components/ChatGptSignInScreen.js +1 -1
- package/dist/components/CodexModelSelector.d.ts +63 -0
- package/dist/components/CodexModelSelector.js +148 -0
- package/dist/components/Commit.d.ts +2 -2
- package/dist/components/Commit.js +10 -22
- package/dist/components/Conversation.d.ts +2 -6
- package/dist/components/Conversation.js +2 -3
- package/dist/components/EnvironmentVariables.d.ts +2 -7
- package/dist/components/EnvironmentVariables.js +10 -33
- package/dist/components/Marker.js +1 -15
- package/dist/components/McpServerPicker.d.ts +31 -6
- package/dist/components/McpServerPicker.js +129 -67
- package/dist/components/Menu.d.ts +1 -1
- package/dist/components/Menu.js +2 -2
- package/dist/components/Message.d.ts +3 -2
- package/dist/components/Message.js +10 -3
- package/dist/components/ModelSelector.d.ts +11 -8
- package/dist/components/ModelSelector.js +1 -1
- package/dist/components/PromptInput.d.ts +2 -2
- package/dist/components/PromptInput.js +49 -98
- package/dist/components/Queue.d.ts +1 -12
- package/dist/components/Reasoning.js +2 -15
- package/dist/components/Stepper.js +1 -7
- package/dist/components/ThinkChat.d.ts +30 -30
- package/dist/components/ThinkChat.js +1 -152
- package/dist/components/ThinkChatActivity.d.ts +2 -2
- package/dist/components/ThinkChatActivity.js +3 -10
- package/dist/components/ThinkChatContext.d.ts +2 -2
- package/dist/components/ThinkChatContext.js +9 -2
- package/dist/components/ThinkChatToolPanels.d.ts +1 -1
- package/dist/components/ThinkChatToolPanels.js +19 -7
- package/dist/components/ThinkChatToolParts.d.ts +1 -1
- package/dist/components/ThinkExecutionWorkbench.d.ts +10 -7
- package/dist/components/ThinkExecutionWorkbench.js +382 -359
- package/dist/components/ThinkFullApp.d.ts +16 -13
- package/dist/components/ThinkFullApp.js +28 -18
- package/dist/components/ThinkThreadPicker.d.ts +1 -31
- package/dist/components/ThinkThreadPicker.js +32 -171
- package/dist/components/ThinkThreadShell.d.ts +35 -0
- package/dist/components/ThinkThreadShell.js +146 -0
- package/dist/components/WorkspaceExplorer.js +3 -1
- package/dist/merge-refs-DF_7w2x_.js +18 -0
- package/dist/styles/agent-chat.css +4 -1
- package/dist/styles/agent-connection.css +0 -166
- package/dist/styles/browser-run-panel.css +125 -0
- package/dist/styles/codex-model-selector.css +197 -0
- package/dist/styles/index.css +5 -0
- package/dist/styles/mcp-server-picker.css +62 -15
- package/dist/styles/message.css +1 -1
- package/dist/styles/model-selector.css +20 -8
- package/dist/styles/prompt-input.css +5 -0
- package/dist/styles/streamdown.css +2 -48
- package/dist/styles/think-execution-workbench.css +337 -0
- package/dist/styles/think-full-app.css +15 -390
- package/dist/styles/think-resize-handle.css +33 -0
- package/dist/styles/think-thread-picker.css +0 -238
- package/dist/styles/think-thread-shell.css +219 -0
- package/dist/styles/workspace-explorer.css +8 -2
- package/dist/summarize-tool-input-BUJsENSn.js +12 -0
- package/dist/utils/mcp-server-catalog.d.ts +2 -3
- package/package.json +2 -2
- package/dist/ThinkChatContext-BLAAb8J5.d.ts +0 -28
- package/dist/components/useStickToBottom.d.ts +0 -33
- package/dist/components/useStickToBottom.js +0 -107
|
@@ -0,0 +1,159 @@
|
|
|
1
|
+
import { t as cx } from "../class-names-9UtZwb0J.js";
|
|
2
|
+
import { L as XIcon, M as SpinnerIcon } from "../icons-D2Q5n5C1.js";
|
|
3
|
+
import { Button } from "./Button.js";
|
|
4
|
+
import { BrowserLiveView } from "./BrowserLiveView.js";
|
|
5
|
+
import { WebPreview, WebPreviewNavigation, WebPreviewNavigationButton, WebPreviewUrl } from "./WebPreview.js";
|
|
6
|
+
import * as React from "react";
|
|
7
|
+
import { jsx, jsxs } from "react/jsx-runtime";
|
|
8
|
+
//#region src/components/BrowserRunPanel.tsx
|
|
9
|
+
function isInspectablePage(target) {
|
|
10
|
+
const pageUrl = target.pageUrl;
|
|
11
|
+
return Boolean(pageUrl && !pageUrl.startsWith("about:") && !pageUrl.startsWith("chrome:") && !pageUrl.startsWith("devtools:"));
|
|
12
|
+
}
|
|
13
|
+
function targetLabel(target) {
|
|
14
|
+
return target.title || target.pageUrl || target.targetId;
|
|
15
|
+
}
|
|
16
|
+
function targetGlyph(target) {
|
|
17
|
+
return (target.title || target.pageUrl || target.targetId).trim().charAt(0).toUpperCase() || "•";
|
|
18
|
+
}
|
|
19
|
+
function pickTarget(targets, targetId) {
|
|
20
|
+
return (targetId ? targets.find((target) => target.targetId === targetId) : void 0) ?? targets.find(isInspectablePage) ?? targets[0];
|
|
21
|
+
}
|
|
22
|
+
function BrowserRunPanelState({ children, role, tone = "neutral" }) {
|
|
23
|
+
return /* @__PURE__ */ jsx("div", {
|
|
24
|
+
className: "web-preview__body--empty browser-run-panel__state",
|
|
25
|
+
"data-tone": tone,
|
|
26
|
+
role: role ?? (tone === "danger" ? "alert" : void 0),
|
|
27
|
+
children
|
|
28
|
+
});
|
|
29
|
+
}
|
|
30
|
+
/**
|
|
31
|
+
* Right-side Browser Run panel for `ThinkFullApp.workbenchPanels`.
|
|
32
|
+
*
|
|
33
|
+
* The app owns `createBrowserRuntime()`, `connector.liveView()`, polling, and
|
|
34
|
+
* session cleanup. This component only renders upstream `BrowserLiveView`
|
|
35
|
+
* data and calls app-provided refresh/close callbacks.
|
|
36
|
+
*/
|
|
37
|
+
function BrowserRunPanel({ liveView, onRefresh, onCloseSession, loading, error, label = "Browser", empty = "No live browser session", fallback, className, ref, ...props }) {
|
|
38
|
+
const [selectedTargetId, setSelectedTargetId] = React.useState();
|
|
39
|
+
const [receivedAt, setReceivedAt] = React.useState(() => Date.now());
|
|
40
|
+
const tabRefs = React.useRef(/* @__PURE__ */ new Map());
|
|
41
|
+
const tabListId = React.useId();
|
|
42
|
+
React.useEffect(() => {
|
|
43
|
+
if (liveView) setReceivedAt(Date.now());
|
|
44
|
+
}, [liveView]);
|
|
45
|
+
const targets = liveView?.targets ?? [];
|
|
46
|
+
const target = pickTarget(targets, selectedTargetId);
|
|
47
|
+
const pageUrl = target?.pageUrl ?? "";
|
|
48
|
+
const selectTarget = React.useCallback((nextTarget) => {
|
|
49
|
+
setSelectedTargetId(nextTarget.targetId);
|
|
50
|
+
}, []);
|
|
51
|
+
const handleTabListKeyDown = (event) => {
|
|
52
|
+
const currentIndex = targets.findIndex((candidate) => candidate.targetId === target?.targetId);
|
|
53
|
+
if (currentIndex < 0) return;
|
|
54
|
+
let nextIndex;
|
|
55
|
+
if (event.key === "ArrowRight") nextIndex = (currentIndex + 1) % targets.length;
|
|
56
|
+
if (event.key === "ArrowLeft") nextIndex = (currentIndex - 1 + targets.length) % targets.length;
|
|
57
|
+
if (event.key === "Home") nextIndex = 0;
|
|
58
|
+
if (event.key === "End") nextIndex = targets.length - 1;
|
|
59
|
+
if (nextIndex === void 0) return;
|
|
60
|
+
event.preventDefault();
|
|
61
|
+
const nextTarget = targets[nextIndex];
|
|
62
|
+
if (!nextTarget) return;
|
|
63
|
+
selectTarget(nextTarget);
|
|
64
|
+
tabRefs.current.get(nextTarget.targetId)?.focus();
|
|
65
|
+
};
|
|
66
|
+
return /* @__PURE__ */ jsxs(WebPreview, {
|
|
67
|
+
ref,
|
|
68
|
+
className: cx("browser-run-panel", className),
|
|
69
|
+
url: pageUrl,
|
|
70
|
+
role: "region",
|
|
71
|
+
"aria-label": typeof label === "string" ? label : "Browser",
|
|
72
|
+
...props,
|
|
73
|
+
children: [
|
|
74
|
+
targets.length > 1 ? /* @__PURE__ */ jsx(WebPreviewNavigation, { children: /* @__PURE__ */ jsx("div", {
|
|
75
|
+
id: tabListId,
|
|
76
|
+
className: "browser-run-panel__tabs",
|
|
77
|
+
role: "tablist",
|
|
78
|
+
"aria-label": "Open browser pages",
|
|
79
|
+
onKeyDown: handleTabListKeyDown,
|
|
80
|
+
children: targets.map((candidate) => {
|
|
81
|
+
const selected = candidate.targetId === target?.targetId;
|
|
82
|
+
return /* @__PURE__ */ jsxs(Button, {
|
|
83
|
+
ref: (node) => {
|
|
84
|
+
if (node) tabRefs.current.set(candidate.targetId, node);
|
|
85
|
+
else tabRefs.current.delete(candidate.targetId);
|
|
86
|
+
},
|
|
87
|
+
type: "button",
|
|
88
|
+
variant: "ghost",
|
|
89
|
+
color: "neutral",
|
|
90
|
+
size: "sm",
|
|
91
|
+
className: "browser-run-panel__tab",
|
|
92
|
+
role: "tab",
|
|
93
|
+
id: `${tabListId}-${candidate.targetId}`,
|
|
94
|
+
"aria-selected": selected,
|
|
95
|
+
"aria-controls": `${tabListId}-panel`,
|
|
96
|
+
tabIndex: selected ? 0 : -1,
|
|
97
|
+
onClick: () => selectTarget(candidate),
|
|
98
|
+
children: [/* @__PURE__ */ jsx("span", {
|
|
99
|
+
className: "browser-run-panel__tab-glyph",
|
|
100
|
+
"aria-hidden": "true",
|
|
101
|
+
children: targetGlyph(candidate)
|
|
102
|
+
}), /* @__PURE__ */ jsx("span", {
|
|
103
|
+
className: "browser-run-panel__tab-title",
|
|
104
|
+
children: targetLabel(candidate)
|
|
105
|
+
})]
|
|
106
|
+
}, candidate.targetId);
|
|
107
|
+
})
|
|
108
|
+
}) }) : null,
|
|
109
|
+
/* @__PURE__ */ jsxs(WebPreviewNavigation, {
|
|
110
|
+
className: "browser-run-panel__address-bar",
|
|
111
|
+
children: [
|
|
112
|
+
/* @__PURE__ */ jsx(WebPreviewUrl, {
|
|
113
|
+
"aria-label": "Browser page URL",
|
|
114
|
+
placeholder: "Waiting for browser session",
|
|
115
|
+
readOnly: true
|
|
116
|
+
}),
|
|
117
|
+
onRefresh ? /* @__PURE__ */ jsx(WebPreviewNavigationButton, {
|
|
118
|
+
action: "reload",
|
|
119
|
+
label: "Refresh browser view",
|
|
120
|
+
disabled: loading,
|
|
121
|
+
onClick: () => void onRefresh()
|
|
122
|
+
}) : null,
|
|
123
|
+
onCloseSession ? /* @__PURE__ */ jsx(WebPreviewNavigationButton, {
|
|
124
|
+
label: "Close browser session",
|
|
125
|
+
onClick: () => void onCloseSession(),
|
|
126
|
+
children: /* @__PURE__ */ jsx(XIcon, {})
|
|
127
|
+
}) : null
|
|
128
|
+
]
|
|
129
|
+
}),
|
|
130
|
+
error ? /* @__PURE__ */ jsx(BrowserRunPanelState, {
|
|
131
|
+
tone: "danger",
|
|
132
|
+
children: error
|
|
133
|
+
}) : null,
|
|
134
|
+
/* @__PURE__ */ jsx("div", {
|
|
135
|
+
id: `${tabListId}-panel`,
|
|
136
|
+
className: "web-preview__body browser-run-panel__body",
|
|
137
|
+
role: targets.length > 1 ? "tabpanel" : void 0,
|
|
138
|
+
"aria-labelledby": targets.length > 1 && target ? `${tabListId}-${target.targetId}` : void 0,
|
|
139
|
+
"aria-busy": loading || void 0,
|
|
140
|
+
children: target && liveView ? /* @__PURE__ */ jsx(BrowserLiveView, {
|
|
141
|
+
source: {
|
|
142
|
+
url: target.url,
|
|
143
|
+
targetId: target.targetId,
|
|
144
|
+
expiresInMs: liveView.expiresInMs
|
|
145
|
+
},
|
|
146
|
+
receivedAt,
|
|
147
|
+
pageTitle: target.title ?? target.pageUrl,
|
|
148
|
+
fallback,
|
|
149
|
+
className: "browser-run-panel__live-view"
|
|
150
|
+
}) : loading ? /* @__PURE__ */ jsxs(BrowserRunPanelState, {
|
|
151
|
+
role: "status",
|
|
152
|
+
children: [/* @__PURE__ */ jsx(SpinnerIcon, { className: "browser-run-panel__spinner" }), "Loading browser session"]
|
|
153
|
+
}) : /* @__PURE__ */ jsx(BrowserRunPanelState, { children: empty })
|
|
154
|
+
})
|
|
155
|
+
]
|
|
156
|
+
});
|
|
157
|
+
}
|
|
158
|
+
//#endregion
|
|
159
|
+
export { BrowserRunPanel };
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { t as cx } from "../class-names-9UtZwb0J.js";
|
|
2
2
|
import { M as SpinnerIcon } from "../icons-D2Q5n5C1.js";
|
|
3
3
|
import { Button } from "./Button.js";
|
|
4
|
-
import { u as ModelSelectorLogo } from "../ModelSelector-
|
|
4
|
+
import { u as ModelSelectorLogo } from "../ModelSelector-BB-xB-Es.js";
|
|
5
5
|
import "react";
|
|
6
6
|
import { jsx, jsxs } from "react/jsx-runtime";
|
|
7
7
|
//#region src/components/ChatGptSignInScreen.tsx
|
|
@@ -0,0 +1,63 @@
|
|
|
1
|
+
import * as React from "react";
|
|
2
|
+
|
|
3
|
+
//#region src/components/CodexModelSelector.d.ts
|
|
4
|
+
/** One server-supported value for a Codex response setting. */
|
|
5
|
+
interface CodexModelSelectorSetting {
|
|
6
|
+
readonly id: string;
|
|
7
|
+
readonly label: string;
|
|
8
|
+
/** Optional explanation shown below the option, such as its usage impact. */
|
|
9
|
+
readonly description?: string;
|
|
10
|
+
}
|
|
11
|
+
interface CodexModelSelectorProps {
|
|
12
|
+
/** Model options allowed by the consuming app. Keep authentication and entitlement checks server-side. */
|
|
13
|
+
readonly models: readonly CodexModelSelectorSetting[];
|
|
14
|
+
/** Current model id used by the consuming app's AI SDK provider. */
|
|
15
|
+
readonly selectedModelId?: string | null;
|
|
16
|
+
/** Called only with an id from the app-provided catalog. */
|
|
17
|
+
readonly onSelectModel: (modelId: string) => void;
|
|
18
|
+
/** Server-supported reasoning effort values for the selected model. */
|
|
19
|
+
readonly effortOptions?: readonly CodexModelSelectorSetting[];
|
|
20
|
+
readonly selectedEffortId?: string | null;
|
|
21
|
+
readonly onSelectEffort?: (effortId: string) => void;
|
|
22
|
+
/** Server-supported response-speed values for the selected model. */
|
|
23
|
+
readonly speedOptions?: readonly CodexModelSelectorSetting[];
|
|
24
|
+
readonly selectedSpeedId?: string | null;
|
|
25
|
+
readonly onSelectSpeed?: (speedId: string) => void;
|
|
26
|
+
/** Restores all values to the consuming app's preferred defaults. */
|
|
27
|
+
readonly onReset?: () => void;
|
|
28
|
+
readonly disabled?: boolean;
|
|
29
|
+
readonly className?: string;
|
|
30
|
+
/** Controlled menu open state. */
|
|
31
|
+
readonly open?: boolean;
|
|
32
|
+
/** Initial menu state for uncontrolled usage. */
|
|
33
|
+
readonly defaultOpen?: boolean;
|
|
34
|
+
readonly onOpenChange?: (open: boolean) => void;
|
|
35
|
+
readonly "aria-label"?: string;
|
|
36
|
+
}
|
|
37
|
+
/**
|
|
38
|
+
* A compact Codex-style response settings picker: model, reasoning effort,
|
|
39
|
+
* response speed, and reset are kept in one cascading menu.
|
|
40
|
+
*
|
|
41
|
+
* The consuming app supplies every selectable value. This component only
|
|
42
|
+
* renders those values and never guesses model ids or account entitlements.
|
|
43
|
+
*/
|
|
44
|
+
declare function CodexModelSelector({
|
|
45
|
+
models,
|
|
46
|
+
selectedModelId,
|
|
47
|
+
onSelectModel,
|
|
48
|
+
effortOptions,
|
|
49
|
+
selectedEffortId,
|
|
50
|
+
onSelectEffort,
|
|
51
|
+
speedOptions,
|
|
52
|
+
selectedSpeedId,
|
|
53
|
+
onSelectSpeed,
|
|
54
|
+
onReset,
|
|
55
|
+
disabled,
|
|
56
|
+
className,
|
|
57
|
+
open,
|
|
58
|
+
defaultOpen,
|
|
59
|
+
onOpenChange,
|
|
60
|
+
"aria-label": ariaLabel
|
|
61
|
+
}: CodexModelSelectorProps): React.JSX.Element;
|
|
62
|
+
//#endregion
|
|
63
|
+
export { CodexModelSelector, CodexModelSelectorProps, CodexModelSelectorSetting };
|
|
@@ -0,0 +1,148 @@
|
|
|
1
|
+
import { t as cx } from "../class-names-9UtZwb0J.js";
|
|
2
|
+
import { a as CheckIcon, c as ChevronRightIcon, k as RefreshIcon, o as ChevronDownIcon } from "../icons-D2Q5n5C1.js";
|
|
3
|
+
import { MenuContent, MenuGroup, MenuGroupLabel, MenuItem, MenuRadioGroup, MenuRadioItem, MenuRadioItemIndicator, MenuRoot, MenuSeparator, MenuSub, MenuSubContent, MenuSubmenuTrigger, MenuTrigger } from "./Menu.js";
|
|
4
|
+
import * as React from "react";
|
|
5
|
+
import { Fragment, jsx, jsxs } from "react/jsx-runtime";
|
|
6
|
+
//#region src/components/CodexModelSelector.tsx
|
|
7
|
+
/**
|
|
8
|
+
* A compact Codex-style response settings picker: model, reasoning effort,
|
|
9
|
+
* response speed, and reset are kept in one cascading menu.
|
|
10
|
+
*
|
|
11
|
+
* The consuming app supplies every selectable value. This component only
|
|
12
|
+
* renders those values and never guesses model ids or account entitlements.
|
|
13
|
+
*/
|
|
14
|
+
function CodexModelSelector({ models, selectedModelId = null, onSelectModel, effortOptions = [], selectedEffortId = null, onSelectEffort, speedOptions = [], selectedSpeedId = null, onSelectSpeed, onReset, disabled = false, className, open, defaultOpen, onOpenChange, "aria-label": ariaLabel = "Codex response settings" }) {
|
|
15
|
+
const [internalOpen, setInternalOpen] = React.useState(defaultOpen);
|
|
16
|
+
const selectedModel = models.find((model) => model.id === selectedModelId);
|
|
17
|
+
const selectedEffort = effortOptions.find((option) => option.id === selectedEffortId);
|
|
18
|
+
const selectedSpeed = speedOptions.find((option) => option.id === selectedSpeedId);
|
|
19
|
+
const currentOpen = open ?? internalOpen;
|
|
20
|
+
const handleOpenChange = React.useCallback((nextOpen) => {
|
|
21
|
+
if (open === void 0) setInternalOpen(nextOpen);
|
|
22
|
+
onOpenChange?.(nextOpen);
|
|
23
|
+
}, [onOpenChange, open]);
|
|
24
|
+
const handleSelectModel = React.useCallback((modelId) => {
|
|
25
|
+
onSelectModel(modelId);
|
|
26
|
+
handleOpenChange(false);
|
|
27
|
+
}, [handleOpenChange, onSelectModel]);
|
|
28
|
+
const handleSelectEffort = React.useCallback((effortId) => {
|
|
29
|
+
onSelectEffort?.(effortId);
|
|
30
|
+
handleOpenChange(false);
|
|
31
|
+
}, [handleOpenChange, onSelectEffort]);
|
|
32
|
+
const handleSelectSpeed = React.useCallback((speedId) => {
|
|
33
|
+
onSelectSpeed?.(speedId);
|
|
34
|
+
handleOpenChange(false);
|
|
35
|
+
}, [handleOpenChange, onSelectSpeed]);
|
|
36
|
+
const handleReset = React.useCallback(() => {
|
|
37
|
+
onReset?.();
|
|
38
|
+
handleOpenChange(false);
|
|
39
|
+
}, [handleOpenChange, onReset]);
|
|
40
|
+
return /* @__PURE__ */ jsxs(MenuRoot, {
|
|
41
|
+
open: currentOpen,
|
|
42
|
+
onOpenChange: handleOpenChange,
|
|
43
|
+
children: [/* @__PURE__ */ jsxs(MenuTrigger, {
|
|
44
|
+
unstyled: true,
|
|
45
|
+
className: cx("codex-model-selector__trigger", className),
|
|
46
|
+
disabled,
|
|
47
|
+
"aria-label": ariaLabel,
|
|
48
|
+
children: [/* @__PURE__ */ jsxs("span", {
|
|
49
|
+
className: "codex-model-selector__summary",
|
|
50
|
+
children: [/* @__PURE__ */ jsx("span", { children: selectedModel?.label ?? "Select model" }), selectedEffort ? /* @__PURE__ */ jsx("span", {
|
|
51
|
+
className: cx("codex-model-selector__summary-effort", selectedEffort.id === "ultra" && "codex-model-selector__summary-effort--ultra"),
|
|
52
|
+
children: selectedEffort.label
|
|
53
|
+
}) : null]
|
|
54
|
+
}), /* @__PURE__ */ jsx(ChevronDownIcon, { className: "codex-model-selector__trigger-icon" })]
|
|
55
|
+
}), /* @__PURE__ */ jsxs(MenuContent, {
|
|
56
|
+
className: "codex-model-selector__menu",
|
|
57
|
+
side: "top",
|
|
58
|
+
align: "end",
|
|
59
|
+
children: [
|
|
60
|
+
/* @__PURE__ */ jsx(CodexModelSelectorSubmenu, {
|
|
61
|
+
label: "Model",
|
|
62
|
+
value: selectedModel?.label ?? "Select",
|
|
63
|
+
disabled: models.length === 0,
|
|
64
|
+
children: /* @__PURE__ */ jsx(MenuRadioGroup, {
|
|
65
|
+
value: selectedModelId ?? void 0,
|
|
66
|
+
onValueChange: handleSelectModel,
|
|
67
|
+
children: models.map((model) => /* @__PURE__ */ jsx(CodexModelSelectorRadioItem, {
|
|
68
|
+
value: model.id,
|
|
69
|
+
description: model.description,
|
|
70
|
+
children: model.label
|
|
71
|
+
}, model.id))
|
|
72
|
+
})
|
|
73
|
+
}),
|
|
74
|
+
effortOptions.length > 0 && onSelectEffort ? /* @__PURE__ */ jsx(CodexModelSelectorSubmenu, {
|
|
75
|
+
label: "Effort",
|
|
76
|
+
value: selectedEffort?.label ?? "Select",
|
|
77
|
+
children: /* @__PURE__ */ jsx(MenuRadioGroup, {
|
|
78
|
+
value: selectedEffortId ?? void 0,
|
|
79
|
+
onValueChange: handleSelectEffort,
|
|
80
|
+
children: effortOptions.map((option) => /* @__PURE__ */ jsx(CodexModelSelectorRadioItem, {
|
|
81
|
+
value: option.id,
|
|
82
|
+
description: option.description,
|
|
83
|
+
children: option.label
|
|
84
|
+
}, option.id))
|
|
85
|
+
})
|
|
86
|
+
}) : null,
|
|
87
|
+
speedOptions.length > 0 && onSelectSpeed ? /* @__PURE__ */ jsx(CodexModelSelectorSubmenu, {
|
|
88
|
+
label: "Speed",
|
|
89
|
+
value: selectedSpeed?.label ?? "Select",
|
|
90
|
+
children: /* @__PURE__ */ jsx(MenuRadioGroup, {
|
|
91
|
+
value: selectedSpeedId ?? void 0,
|
|
92
|
+
onValueChange: handleSelectSpeed,
|
|
93
|
+
children: speedOptions.map((option) => /* @__PURE__ */ jsx(CodexModelSelectorRadioItem, {
|
|
94
|
+
value: option.id,
|
|
95
|
+
description: option.description,
|
|
96
|
+
children: option.label
|
|
97
|
+
}, option.id))
|
|
98
|
+
})
|
|
99
|
+
}) : null,
|
|
100
|
+
onReset ? /* @__PURE__ */ jsxs(Fragment, { children: [/* @__PURE__ */ jsx(MenuSeparator, {}), /* @__PURE__ */ jsxs(MenuItem, {
|
|
101
|
+
className: "codex-model-selector__reset",
|
|
102
|
+
onClick: handleReset,
|
|
103
|
+
children: ["Reset to default", /* @__PURE__ */ jsx(RefreshIcon, { className: "codex-model-selector__reset-icon" })]
|
|
104
|
+
})] }) : null
|
|
105
|
+
]
|
|
106
|
+
})]
|
|
107
|
+
});
|
|
108
|
+
}
|
|
109
|
+
function CodexModelSelectorSubmenu({ label, value, disabled = false, children }) {
|
|
110
|
+
return /* @__PURE__ */ jsxs(MenuSub, { children: [/* @__PURE__ */ jsxs(MenuSubmenuTrigger, {
|
|
111
|
+
className: "codex-model-selector__submenu-trigger",
|
|
112
|
+
disabled,
|
|
113
|
+
children: [
|
|
114
|
+
/* @__PURE__ */ jsx("span", { children: label }),
|
|
115
|
+
/* @__PURE__ */ jsx("span", {
|
|
116
|
+
className: "codex-model-selector__submenu-value",
|
|
117
|
+
children: value
|
|
118
|
+
}),
|
|
119
|
+
/* @__PURE__ */ jsx(ChevronRightIcon, { className: "codex-model-selector__submenu-icon" })
|
|
120
|
+
]
|
|
121
|
+
}), /* @__PURE__ */ jsx(MenuSubContent, {
|
|
122
|
+
className: cx("codex-model-selector__submenu", `codex-model-selector__submenu--${label.toLowerCase()}`),
|
|
123
|
+
side: "right",
|
|
124
|
+
align: "start",
|
|
125
|
+
children: /* @__PURE__ */ jsxs(MenuGroup, { children: [/* @__PURE__ */ jsx(MenuGroupLabel, {
|
|
126
|
+
className: "codex-model-selector__submenu-title",
|
|
127
|
+
children: label
|
|
128
|
+
}), children] })
|
|
129
|
+
})] });
|
|
130
|
+
}
|
|
131
|
+
function CodexModelSelectorRadioItem({ children, description, ...props }) {
|
|
132
|
+
return /* @__PURE__ */ jsxs(MenuRadioItem, {
|
|
133
|
+
className: "codex-model-selector__option",
|
|
134
|
+
...props,
|
|
135
|
+
children: [/* @__PURE__ */ jsxs("span", { children: [/* @__PURE__ */ jsx("span", {
|
|
136
|
+
className: "codex-model-selector__option-label",
|
|
137
|
+
children
|
|
138
|
+
}), description ? /* @__PURE__ */ jsx("span", {
|
|
139
|
+
className: "codex-model-selector__option-description",
|
|
140
|
+
children: description
|
|
141
|
+
}) : null] }), /* @__PURE__ */ jsx(MenuRadioItemIndicator, {
|
|
142
|
+
className: "codex-model-selector__option-indicator",
|
|
143
|
+
children: /* @__PURE__ */ jsx(CheckIcon, {})
|
|
144
|
+
})]
|
|
145
|
+
});
|
|
146
|
+
}
|
|
147
|
+
//#endregion
|
|
148
|
+
export { CodexModelSelector };
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { CollapsiblePanelProps, CollapsibleRootProps, CollapsibleTriggerProps } from "./Collapsible.js";
|
|
2
|
-
import {
|
|
2
|
+
import { t as CopyButtonProps } from "../copy-button-BKXqGiNm.js";
|
|
3
3
|
import * as React from "react";
|
|
4
4
|
|
|
5
5
|
//#region src/components/Commit.d.ts
|
|
@@ -133,7 +133,7 @@ declare function CommitHash({
|
|
|
133
133
|
}: CommitHashProps & {
|
|
134
134
|
ref?: React.Ref<HTMLSpanElement>;
|
|
135
135
|
}): React.JSX.Element;
|
|
136
|
-
interface CommitCopyButtonProps extends Omit<
|
|
136
|
+
interface CommitCopyButtonProps extends Omit<CopyButtonProps, "label" | "stopPropagation" | "text"> {
|
|
137
137
|
hash: string;
|
|
138
138
|
label?: string;
|
|
139
139
|
className?: string;
|
|
@@ -1,11 +1,10 @@
|
|
|
1
1
|
import { CollapsiblePanel, CollapsibleRoot, CollapsibleTrigger } from "./Collapsible.js";
|
|
2
2
|
import { t as cx } from "../class-names-9UtZwb0J.js";
|
|
3
|
-
import {
|
|
4
|
-
import {
|
|
5
|
-
import { Tooltip, TooltipPopup, TooltipPortal, TooltipPositioner, TooltipTrigger } from "./Tooltip.js";
|
|
3
|
+
import { c as ChevronRightIcon, h as FileIcon } from "../icons-D2Q5n5C1.js";
|
|
4
|
+
import { t as CopyButton } from "../copy-button-C6JSKtFE.js";
|
|
6
5
|
import { Avatar } from "./Avatar.js";
|
|
7
6
|
import { Badge } from "./Badge.js";
|
|
8
|
-
import
|
|
7
|
+
import "react";
|
|
9
8
|
import { jsx, jsxs } from "react/jsx-runtime";
|
|
10
9
|
//#region src/components/Commit.tsx
|
|
11
10
|
const FILE_STATUS_COLOR = {
|
|
@@ -141,25 +140,14 @@ function CommitHash({ className, children, hash, ref, ...props }) {
|
|
|
141
140
|
});
|
|
142
141
|
}
|
|
143
142
|
function CommitCopyButton({ className, hash, label = "Copy hash", onClick, ...props }) {
|
|
144
|
-
|
|
145
|
-
const handleClick = React.useCallback(async (e) => {
|
|
146
|
-
e.stopPropagation();
|
|
147
|
-
try {
|
|
148
|
-
await navigator.clipboard.writeText(hash);
|
|
149
|
-
setCopied(true);
|
|
150
|
-
window.setTimeout(() => setCopied(false), 1500);
|
|
151
|
-
} catch {}
|
|
152
|
-
onClick?.(e);
|
|
153
|
-
}, [hash, onClick]);
|
|
154
|
-
return /* @__PURE__ */ jsxs(Tooltip, { children: [/* @__PURE__ */ jsx(TooltipTrigger, { render: /* @__PURE__ */ jsx(Button, {
|
|
155
|
-
variant: "ghost",
|
|
156
|
-
size: "icon",
|
|
157
|
-
"aria-label": label,
|
|
158
|
-
className: cx("commit__copy", className),
|
|
143
|
+
return /* @__PURE__ */ jsx(CopyButton, {
|
|
159
144
|
...props,
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
145
|
+
text: hash,
|
|
146
|
+
label,
|
|
147
|
+
stopPropagation: true,
|
|
148
|
+
className: cx("commit__copy", className),
|
|
149
|
+
onClick
|
|
150
|
+
});
|
|
163
151
|
}
|
|
164
152
|
function CommitTimestamp({ className, children, date, ref, ...props }) {
|
|
165
153
|
return /* @__PURE__ */ jsx("time", {
|
|
@@ -4,12 +4,8 @@ import * as React from "react";
|
|
|
4
4
|
import { UIMessage } from "ai";
|
|
5
5
|
|
|
6
6
|
//#region src/components/Conversation.d.ts
|
|
7
|
-
/** AI SDK
|
|
8
|
-
type ConversationMessage = UIMessage
|
|
9
|
-
id?: string;
|
|
10
|
-
role: string;
|
|
11
|
-
content?: string;
|
|
12
|
-
};
|
|
7
|
+
/** Whole AI SDK message accepted by transcript export helpers. */
|
|
8
|
+
type ConversationMessage = UIMessage;
|
|
13
9
|
interface ConversationProps extends Omit<React.HTMLAttributes<HTMLDivElement>, "children"> {
|
|
14
10
|
/** Additional class names for layout only; do not override scroll behavior from apps. */
|
|
15
11
|
className?: string;
|
|
@@ -133,11 +133,10 @@ function ConversationScrollButton({ className, variant = "outline", color = "neu
|
|
|
133
133
|
const ROLE_HEADING = {
|
|
134
134
|
user: "### User",
|
|
135
135
|
assistant: "### Assistant",
|
|
136
|
-
system: "### System"
|
|
137
|
-
tool: "### Tool"
|
|
136
|
+
system: "### System"
|
|
138
137
|
};
|
|
139
138
|
function defaultFormatMessage(message) {
|
|
140
|
-
return `${ROLE_HEADING[message.role]
|
|
139
|
+
return `${ROLE_HEADING[message.role]}\n\n${message.parts.filter((part) => isTextUIPart(part) || isReasoningUIPart(part)).map((part) => part.text).join("").trim()}`;
|
|
141
140
|
}
|
|
142
141
|
/**
|
|
143
142
|
* Converts a conversation to a Markdown document with a heading per message.
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { t as CopyButtonProps } from "../copy-button-BKXqGiNm.js";
|
|
2
2
|
import * as React from "react";
|
|
3
3
|
|
|
4
4
|
//#region src/components/EnvironmentVariables.d.ts
|
|
@@ -142,15 +142,10 @@ declare function EnvironmentVariableValue({
|
|
|
142
142
|
ref?: React.Ref<HTMLSpanElement>;
|
|
143
143
|
}): React.JSX.Element;
|
|
144
144
|
type EnvironmentVariableCopyFormat = "name" | "value" | "export";
|
|
145
|
-
interface EnvironmentVariableCopyButtonProps extends Omit<
|
|
145
|
+
interface EnvironmentVariableCopyButtonProps extends Omit<CopyButtonProps, "label" | "stopPropagation" | "text"> {
|
|
146
146
|
format?: EnvironmentVariableCopyFormat;
|
|
147
147
|
copyFormat?: EnvironmentVariableCopyFormat;
|
|
148
148
|
label?: string;
|
|
149
|
-
className?: string;
|
|
150
|
-
onClick?: React.MouseEventHandler<HTMLButtonElement>;
|
|
151
|
-
onCopy?: () => void;
|
|
152
|
-
onError?: (error: Error) => void;
|
|
153
|
-
timeout?: number;
|
|
154
149
|
}
|
|
155
150
|
declare function EnvironmentVariableCopyButton({
|
|
156
151
|
className,
|
|
@@ -1,7 +1,6 @@
|
|
|
1
1
|
import { t as cx } from "../class-names-9UtZwb0J.js";
|
|
2
|
-
import {
|
|
3
|
-
import {
|
|
4
|
-
import { Tooltip, TooltipPopup, TooltipPortal, TooltipPositioner, TooltipTrigger } from "./Tooltip.js";
|
|
2
|
+
import { m as EyeOffIcon, p as EyeIcon } from "../icons-D2Q5n5C1.js";
|
|
3
|
+
import { t as CopyButton } from "../copy-button-C6JSKtFE.js";
|
|
5
4
|
import { Badge } from "./Badge.js";
|
|
6
5
|
import { Switch, SwitchThumb } from "./Switch.js";
|
|
7
6
|
import * as React from "react";
|
|
@@ -171,41 +170,19 @@ function EnvironmentVariableValue({ className, children, ref, ...props }) {
|
|
|
171
170
|
}
|
|
172
171
|
function EnvironmentVariableCopyButton({ className, format = "value", copyFormat, label, onClick, onCopy, onError, timeout = 1500, ...props }) {
|
|
173
172
|
const { name, value } = useVariableContext();
|
|
174
|
-
const [copied, setCopied] = React.useState(false);
|
|
175
|
-
const timeoutRef = React.useRef(null);
|
|
176
173
|
const resolvedFormat = copyFormat ?? format;
|
|
177
174
|
const text = resolvedFormat === "name" ? name : resolvedFormat === "export" ? `export ${name}="${value}"` : value;
|
|
178
175
|
const buttonLabel = label ?? `Copy ${resolvedFormat}`;
|
|
179
|
-
|
|
180
|
-
|
|
181
|
-
await navigator.clipboard.writeText(text);
|
|
182
|
-
setCopied(true);
|
|
183
|
-
onCopy?.();
|
|
184
|
-
if (timeoutRef.current !== null) window.clearTimeout(timeoutRef.current);
|
|
185
|
-
timeoutRef.current = window.setTimeout(() => setCopied(false), timeout);
|
|
186
|
-
} catch (error) {
|
|
187
|
-
onError?.(error);
|
|
188
|
-
}
|
|
189
|
-
onClick?.(e);
|
|
190
|
-
}, [
|
|
191
|
-
onClick,
|
|
192
|
-
onCopy,
|
|
193
|
-
onError,
|
|
176
|
+
return /* @__PURE__ */ jsx(CopyButton, {
|
|
177
|
+
...props,
|
|
194
178
|
text,
|
|
195
|
-
|
|
196
|
-
|
|
197
|
-
React.useEffect(() => () => {
|
|
198
|
-
if (timeoutRef.current !== null) window.clearTimeout(timeoutRef.current);
|
|
199
|
-
}, []);
|
|
200
|
-
return /* @__PURE__ */ jsxs(Tooltip, { children: [/* @__PURE__ */ jsx(TooltipTrigger, { render: /* @__PURE__ */ jsx(Button, {
|
|
201
|
-
variant: "ghost",
|
|
202
|
-
size: "icon",
|
|
203
|
-
"aria-label": buttonLabel,
|
|
179
|
+
label: buttonLabel,
|
|
180
|
+
timeout,
|
|
204
181
|
className: cx("environment-variables__copy", className),
|
|
205
|
-
|
|
206
|
-
|
|
207
|
-
|
|
208
|
-
})
|
|
182
|
+
onCopy,
|
|
183
|
+
onError,
|
|
184
|
+
onClick
|
|
185
|
+
});
|
|
209
186
|
}
|
|
210
187
|
function EnvironmentVariableRequired({ className, children, ref, ...props }) {
|
|
211
188
|
return /* @__PURE__ */ jsx(Badge, {
|
|
@@ -1,25 +1,11 @@
|
|
|
1
1
|
import { t as cx } from "../class-names-9UtZwb0J.js";
|
|
2
|
+
import { n as mergeRefs } from "../merge-refs-DF_7w2x_.js";
|
|
2
3
|
import * as React from "react";
|
|
3
4
|
import { jsx } from "react/jsx-runtime";
|
|
4
5
|
//#region src/components/Marker.tsx
|
|
5
6
|
function markerVariants({ variant = "default", className } = {}) {
|
|
6
7
|
return cx("marker", `marker--${variant ?? "default"}`, className);
|
|
7
8
|
}
|
|
8
|
-
function assignRef(ref, value) {
|
|
9
|
-
if (!ref) return;
|
|
10
|
-
if (typeof ref === "function") {
|
|
11
|
-
ref(value);
|
|
12
|
-
return;
|
|
13
|
-
}
|
|
14
|
-
ref.current = value;
|
|
15
|
-
}
|
|
16
|
-
function mergeRefs(...refs) {
|
|
17
|
-
const activeRefs = refs.filter(Boolean);
|
|
18
|
-
if (activeRefs.length === 0) return void 0;
|
|
19
|
-
return (value) => {
|
|
20
|
-
for (const activeRef of activeRefs) assignRef(activeRef, value);
|
|
21
|
-
};
|
|
22
|
-
}
|
|
23
9
|
function isEventHandler(propName, value) {
|
|
24
10
|
return /^on[A-Z]/.test(propName) && typeof value === "function";
|
|
25
11
|
}
|
|
@@ -1,16 +1,30 @@
|
|
|
1
1
|
import { McpServerCard } from "../utils/mcp-server-catalog.js";
|
|
2
2
|
import * as React from "react";
|
|
3
|
+
import { MCPServer, MCPServersState } from "agents";
|
|
3
4
|
|
|
4
5
|
//#region src/components/McpServerPicker.d.ts
|
|
5
6
|
interface McpServerPickerProps {
|
|
6
7
|
/** MCP servers to show in the plus-menu picker. */
|
|
7
8
|
servers: readonly McpServerCard[];
|
|
8
9
|
/** Called when the user chooses a server; hosts own OAuth and connection state. */
|
|
9
|
-
onConnect
|
|
10
|
+
onConnect?: (server: McpServerCard) => void | Promise<void>;
|
|
11
|
+
/** Upstream Agents SDK MCP state from `getMcpServers()` or `useAgent({ onMcpUpdate })`. */
|
|
12
|
+
mcp?: MCPServersState;
|
|
13
|
+
/** Called when an OAuth server needs user authorization. */
|
|
14
|
+
onAuthorize?: McpServerConnectionAction;
|
|
15
|
+
/** Called when a failed server should retry through an app-owned Agent RPC. */
|
|
16
|
+
onRetry?: McpServerConnectionAction;
|
|
17
|
+
/** Called when a ready/connected server should refresh discovery through an app-owned Agent RPC. */
|
|
18
|
+
onRefresh?: McpServerConnectionAction;
|
|
19
|
+
/** Called when a server transport should close but the stored config should remain. */
|
|
20
|
+
onDisconnect?: McpServerConnectionAction;
|
|
10
21
|
/** Offset from the plus trigger to the menu, useful for prompt composers. */
|
|
11
22
|
sideOffset?: number;
|
|
23
|
+
/** Accessible name for the plus trigger. */
|
|
24
|
+
triggerLabel?: string;
|
|
12
25
|
}
|
|
13
|
-
type
|
|
26
|
+
type McpServerConnectionAction = (serverId: string, server: MCPServer) => void | Promise<void>;
|
|
27
|
+
type McpServerPickerItemsProps = Omit<McpServerPickerProps, "sideOffset" | "triggerLabel">;
|
|
14
28
|
/**
|
|
15
29
|
* Prompt plus-menu picker for choosing an MCP server and handing connection
|
|
16
30
|
* work back to the host app.
|
|
@@ -18,11 +32,22 @@ type McpServerPickerItemsProps = Pick<McpServerPickerProps, "servers" | "onConne
|
|
|
18
32
|
declare function McpServerPicker({
|
|
19
33
|
servers,
|
|
20
34
|
onConnect,
|
|
21
|
-
|
|
35
|
+
mcp,
|
|
36
|
+
onAuthorize,
|
|
37
|
+
onDisconnect,
|
|
38
|
+
onRefresh,
|
|
39
|
+
onRetry,
|
|
40
|
+
sideOffset,
|
|
41
|
+
triggerLabel
|
|
22
42
|
}: McpServerPickerProps): React.JSX.Element;
|
|
23
43
|
declare function McpServerPickerItems({
|
|
24
44
|
servers,
|
|
25
|
-
onConnect
|
|
26
|
-
|
|
45
|
+
onConnect,
|
|
46
|
+
mcp,
|
|
47
|
+
onAuthorize,
|
|
48
|
+
onDisconnect,
|
|
49
|
+
onRefresh,
|
|
50
|
+
onRetry
|
|
51
|
+
}: McpServerPickerItemsProps): React.JSX.Element;
|
|
27
52
|
//#endregion
|
|
28
|
-
export { McpServerPicker, McpServerPickerItems, McpServerPickerItemsProps, McpServerPickerProps };
|
|
53
|
+
export { McpServerConnectionAction, McpServerPicker, McpServerPickerItems, McpServerPickerItemsProps, McpServerPickerProps };
|