@darqlabs/curator-sdk-react 0.6.1 → 0.8.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 (56) hide show
  1. package/README.md +18 -0
  2. package/dist/cjs/CuratorAdapter.d.ts +37 -2
  3. package/dist/cjs/CuratorAdapter.d.ts.map +1 -1
  4. package/dist/cjs/CuratorAdapter.js +119 -20
  5. package/dist/cjs/CuratorAdapter.js.map +1 -1
  6. package/dist/cjs/CuratorChat.d.ts +8 -0
  7. package/dist/cjs/CuratorChat.d.ts.map +1 -1
  8. package/dist/cjs/CuratorChat.js +28 -8
  9. package/dist/cjs/CuratorChat.js.map +1 -1
  10. package/dist/cjs/historyMessages.d.ts +20 -1
  11. package/dist/cjs/historyMessages.d.ts.map +1 -1
  12. package/dist/cjs/historyMessages.js +25 -3
  13. package/dist/cjs/historyMessages.js.map +1 -1
  14. package/dist/cjs/index.d.ts +1 -0
  15. package/dist/cjs/index.d.ts.map +1 -1
  16. package/dist/cjs/index.js.map +1 -1
  17. package/dist/cjs/mcpApps/McpAppContext.d.ts +39 -0
  18. package/dist/cjs/mcpApps/McpAppContext.d.ts.map +1 -0
  19. package/dist/cjs/mcpApps/McpAppContext.js +19 -0
  20. package/dist/cjs/mcpApps/McpAppContext.js.map +1 -0
  21. package/dist/cjs/mcpApps/McpAppToolPart.d.ts +27 -0
  22. package/dist/cjs/mcpApps/McpAppToolPart.d.ts.map +1 -0
  23. package/dist/cjs/mcpApps/McpAppToolPart.js +275 -0
  24. package/dist/cjs/mcpApps/McpAppToolPart.js.map +1 -0
  25. package/dist/cjs/mcpApps/hostBridge.d.ts +127 -0
  26. package/dist/cjs/mcpApps/hostBridge.d.ts.map +1 -0
  27. package/dist/cjs/mcpApps/hostBridge.js +306 -0
  28. package/dist/cjs/mcpApps/hostBridge.js.map +1 -0
  29. package/dist/esm/CuratorAdapter.d.ts +37 -2
  30. package/dist/esm/CuratorAdapter.d.ts.map +1 -1
  31. package/dist/esm/CuratorAdapter.js +119 -20
  32. package/dist/esm/CuratorAdapter.js.map +1 -1
  33. package/dist/esm/CuratorChat.d.ts +8 -0
  34. package/dist/esm/CuratorChat.d.ts.map +1 -1
  35. package/dist/esm/CuratorChat.js +28 -8
  36. package/dist/esm/CuratorChat.js.map +1 -1
  37. package/dist/esm/historyMessages.d.ts +20 -1
  38. package/dist/esm/historyMessages.d.ts.map +1 -1
  39. package/dist/esm/historyMessages.js +25 -3
  40. package/dist/esm/historyMessages.js.map +1 -1
  41. package/dist/esm/index.d.ts +1 -0
  42. package/dist/esm/index.d.ts.map +1 -1
  43. package/dist/esm/index.js.map +1 -1
  44. package/dist/esm/mcpApps/McpAppContext.d.ts +39 -0
  45. package/dist/esm/mcpApps/McpAppContext.d.ts.map +1 -0
  46. package/dist/esm/mcpApps/McpAppContext.js +15 -0
  47. package/dist/esm/mcpApps/McpAppContext.js.map +1 -0
  48. package/dist/esm/mcpApps/McpAppToolPart.d.ts +27 -0
  49. package/dist/esm/mcpApps/McpAppToolPart.d.ts.map +1 -0
  50. package/dist/esm/mcpApps/McpAppToolPart.js +271 -0
  51. package/dist/esm/mcpApps/McpAppToolPart.js.map +1 -0
  52. package/dist/esm/mcpApps/hostBridge.d.ts +127 -0
  53. package/dist/esm/mcpApps/hostBridge.d.ts.map +1 -0
  54. package/dist/esm/mcpApps/hostBridge.js +300 -0
  55. package/dist/esm/mcpApps/hostBridge.js.map +1 -0
  56. package/package.json +5 -4
@@ -0,0 +1,271 @@
1
+ import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
2
+ /**
3
+ * The tool-call part renderer for MCP Apps.
4
+ *
5
+ * Two shapes, decided by whether the part carries `mcp.app` with a session:
6
+ *
7
+ * live view `tool_call.started` on THIS stream carried an app session →
8
+ * load the view's HTML through the Curator data plane, mount it
9
+ * in a sandboxed frame (safe-content-frame: hashed third-party
10
+ * origin), and run the SEP-1865 host bridge against it.
11
+ * static card anything else — a call reloaded from history, a call whose
12
+ * session could not be minted, or MCP Apps disabled → a
13
+ * non-interactive card with the tool's title and status. No
14
+ * arguments, no result, no session ever reach the DOM here.
15
+ *
16
+ * Credentials never enter the frame: every host call runs in the parent
17
+ * through the SDK, which holds the API key and end-user JWT.
18
+ */
19
+ import { useEffect, useMemo, useRef, useState } from "react";
20
+ import { useAui } from "@assistant-ui/react";
21
+ import { SafeContentFrame } from "safe-content-frame";
22
+ import { McpAppHostBridge } from "./hostBridge.js";
23
+ import { APP_SESSION_METADATA_KEY, APP_TOOL_METADATA_KEY, useMcpAppContext, } from "./McpAppContext.js";
24
+ const DEFAULT_MAX_HEIGHT = 480;
25
+ const INITIAL_HEIGHT = 160;
26
+ const INIT_TIMEOUT_MS = 8_000;
27
+ function appOf(part) {
28
+ const app = part.mcp?.app;
29
+ if (!app || typeof app.resourceUri !== "string" || !app.resourceUri.startsWith("ui://"))
30
+ return undefined;
31
+ return app;
32
+ }
33
+ /**
34
+ * "pick_customer" / "mcp_mcps_d86199d7ac64_pick_customer" → "Pick customer".
35
+ * Sanitized MCP names are `mcp_<server_id>_<tool>` and server ids are
36
+ * themselves `mcps_<hex>`, so two prefixes come off, not one — one left the
37
+ * card titled "D86199d7ac64 pick customer".
38
+ */
39
+ export function humanizeToolName(name) {
40
+ const tail = name.replace(/^mcp_(?:mcps_)?[a-z0-9]+_/i, "");
41
+ const spaced = tail.replace(/[_-]+/g, " ").trim();
42
+ return spaced ? spaced.charAt(0).toUpperCase() + spaced.slice(1) : name;
43
+ }
44
+ function resultText(result) {
45
+ if (!result || typeof result !== "object")
46
+ return null;
47
+ const content = result.content;
48
+ if (!Array.isArray(content))
49
+ return null;
50
+ const first = content.find((c) => c && typeof c === "object" && c.type === "text");
51
+ return typeof first?.text === "string" && first.text ? first.text : null;
52
+ }
53
+ export function McpAppToolPart(part) {
54
+ const ctx = useMcpAppContext();
55
+ const app = appOf(part);
56
+ const session = app?.serverId;
57
+ const live = !!ctx && ctx.options.enabled !== false && !!app && !!session;
58
+ if (!live)
59
+ return _jsx(StaticToolCard, { part: part });
60
+ return _jsx(LiveMcpAppView, { part: part, ctx: ctx, session: session, resourceUri: app.resourceUri });
61
+ }
62
+ // ── static card ──────────────────────────────────────────────────────────
63
+ function StaticToolCard({ part }) {
64
+ const title = humanizeToolName(part.toolName);
65
+ const failed = part.isError === true;
66
+ const text = resultText(part.result) ?? (failed ? "The tool could not complete." : "Interactive view expired");
67
+ return (_jsxs("div", { "data-curator-part": "mcp-app-card", style: cardStyle, children: [_jsx("span", { style: cardTitleStyle, children: title }), _jsx("span", { style: cardMetaStyle, children: text })] }));
68
+ }
69
+ function LiveMcpAppView({ part, ctx, session, resourceUri, }) {
70
+ const aui = useAui();
71
+ const containerRef = useRef(null);
72
+ const bridgeRef = useRef(null);
73
+ const inFlightMessageRef = useRef(false);
74
+ const [state, setState] = useState({ kind: "loading" });
75
+ const [height, setHeight] = useState(INITIAL_HEIGHT);
76
+ const maxHeight = ctx.options.maxHeight ?? DEFAULT_MAX_HEIGHT;
77
+ // Latest part fields, readable from the long-lived bridge without
78
+ // re-creating it: the frame must survive re-renders, and the part updates
79
+ // several times (args → result) during one turn.
80
+ const latest = useRef({ part, ctx });
81
+ latest.current = { part, ctx };
82
+ const title = useMemo(() => humanizeToolName(part.toolName), [part.toolName]);
83
+ useEffect(() => {
84
+ const container = containerRef.current;
85
+ if (!container)
86
+ return;
87
+ let cancelled = false;
88
+ let rendered = null;
89
+ let bridge = null;
90
+ let onWindowMessage = null;
91
+ let initTimer;
92
+ const teardown = () => {
93
+ if (onWindowMessage)
94
+ window.removeEventListener("message", onWindowMessage);
95
+ if (initTimer)
96
+ clearTimeout(initTimer);
97
+ const b = bridge;
98
+ bridge = null;
99
+ bridgeRef.current = null;
100
+ const r = rendered;
101
+ rendered = null;
102
+ if (b)
103
+ void b.teardown(300).finally(() => r?.dispose());
104
+ else
105
+ r?.dispose();
106
+ };
107
+ (async () => {
108
+ let resource;
109
+ try {
110
+ resource = await ctx.chat.mcpApps.readResource({ session, uri: resourceUri });
111
+ }
112
+ catch (err) {
113
+ if (!cancelled)
114
+ setState({ kind: "error", message: err?.message || "The view could not be loaded." });
115
+ return;
116
+ }
117
+ if (cancelled)
118
+ return;
119
+ const frame = new SafeContentFrame(ctx.options.sandboxProduct ?? "curator", {
120
+ sandbox: ["allow-forms"],
121
+ });
122
+ try {
123
+ rendered = await frame.renderHtml(resource.html, container);
124
+ }
125
+ catch (err) {
126
+ if (!cancelled)
127
+ setState({ kind: "error", message: err?.message || "The view could not be shown." });
128
+ return;
129
+ }
130
+ if (cancelled) {
131
+ rendered.dispose();
132
+ return;
133
+ }
134
+ const r = rendered;
135
+ bridge = new McpAppHostBridge({
136
+ post: (m) => r.sendMessage(m),
137
+ hostInfo: { name: "Curator", version: "1" },
138
+ hostContext: {
139
+ theme: ctx.theme,
140
+ displayMode: "inline",
141
+ availableDisplayModes: ["inline"],
142
+ platform: "web",
143
+ locale: typeof navigator !== "undefined" ? navigator.language : undefined,
144
+ containerDimensions: { width: container.clientWidth || undefined, maxHeight },
145
+ },
146
+ handlers: {
147
+ callTool: async ({ name, arguments: args, _meta }) => {
148
+ const idempotencyKey = typeof _meta?.idempotencyKey === "string" ? _meta.idempotencyKey : undefined;
149
+ const result = await latest.current.ctx.chat.mcpApps.callTool({
150
+ session,
151
+ name,
152
+ arguments: args ?? {},
153
+ ...(idempotencyKey ? { idempotencyKey } : {}),
154
+ });
155
+ return result;
156
+ },
157
+ sendMessage: async (text) => {
158
+ // One app message in flight per view: a double-fire from the view
159
+ // becomes one turn, and the server dedupes the rest.
160
+ if (inFlightMessageRef.current)
161
+ return false;
162
+ inFlightMessageRef.current = true;
163
+ setTimeout(() => {
164
+ inFlightMessageRef.current = false;
165
+ }, 2_000);
166
+ aui.thread.append({
167
+ role: "user",
168
+ content: [{ type: "text", text }],
169
+ metadata: {
170
+ custom: {
171
+ [APP_SESSION_METADATA_KEY]: session,
172
+ [APP_TOOL_METADATA_KEY]: latest.current.part.toolName,
173
+ },
174
+ },
175
+ });
176
+ return true;
177
+ },
178
+ updateModelContext: (params) => {
179
+ latest.current.ctx.options.onModelContextUpdate?.({
180
+ toolCallId: latest.current.part.toolCallId,
181
+ session,
182
+ content: params.content,
183
+ structuredContent: params.structuredContent,
184
+ });
185
+ },
186
+ openLink: (url) => {
187
+ window.open(url, "_blank", "noopener,noreferrer");
188
+ return true;
189
+ },
190
+ onSizeChange: ({ height: h }) => {
191
+ if (typeof h === "number" && h > 0)
192
+ setHeight(Math.min(Math.max(48, Math.round(h)), maxHeight));
193
+ },
194
+ onInitialized: () => {
195
+ if (initTimer)
196
+ clearTimeout(initTimer);
197
+ setState({ kind: "ready" });
198
+ },
199
+ onLog: () => undefined,
200
+ onError: () => undefined,
201
+ },
202
+ });
203
+ bridgeRef.current = bridge;
204
+ onWindowMessage = (e) => {
205
+ if (e.source !== r.iframe.contentWindow || e.origin !== r.origin)
206
+ return;
207
+ bridge?.onMessage(e.data);
208
+ };
209
+ window.addEventListener("message", onWindowMessage);
210
+ // Input is known now; the result may already be, or arrives later.
211
+ const args = latest.current.part.args;
212
+ bridge.setToolInput(args && typeof args === "object" ? args : {});
213
+ const res = latest.current.part.result;
214
+ if (res && typeof res === "object" && Array.isArray(res.content)) {
215
+ bridge.setToolResult(res);
216
+ }
217
+ initTimer = setTimeout(() => {
218
+ if (!cancelled && !bridge?.isInitialized) {
219
+ setState({ kind: "error", message: "The view did not initialize." });
220
+ }
221
+ }, INIT_TIMEOUT_MS);
222
+ })();
223
+ return () => {
224
+ cancelled = true;
225
+ teardown();
226
+ };
227
+ // The frame is bound to one session for its whole life; a new session is a
228
+ // new part, hence a new component instance.
229
+ // eslint-disable-next-line react-hooks/exhaustive-deps
230
+ }, [session, resourceUri]);
231
+ // Deliver the result when it lands after mount.
232
+ const result = part.result;
233
+ useEffect(() => {
234
+ const b = bridgeRef.current;
235
+ if (!b)
236
+ return;
237
+ if (result && typeof result === "object" && Array.isArray(result.content)) {
238
+ b.setToolResult(result);
239
+ }
240
+ }, [result]);
241
+ // Theme changes reach the view as a host-context update.
242
+ useEffect(() => {
243
+ bridgeRef.current?.updateHostContext({ theme: ctx.theme });
244
+ }, [ctx.theme]);
245
+ return (_jsxs("div", { "data-curator-part": "mcp-app", style: viewWrapStyle, children: [_jsxs("div", { "data-curator-part": "mcp-app-header", style: viewHeaderStyle, children: [_jsx("span", { style: cardTitleStyle, children: title }), state.kind === "loading" && _jsx("span", { style: cardMetaStyle, children: "Loading\u2026" }), state.kind === "error" && _jsx("span", { style: cardMetaStyle, children: state.message })] }), _jsx("div", { ref: containerRef, "data-curator-part": "mcp-app-frame", style: { ...frameContainerStyle, height: state.kind === "error" ? 0 : height } })] }));
246
+ }
247
+ // ── styles ───────────────────────────────────────────────────────────────
248
+ const cardStyle = {
249
+ display: "flex",
250
+ flexDirection: "column",
251
+ gap: 2,
252
+ padding: "8px 10px",
253
+ margin: "4px 0",
254
+ borderRadius: 8,
255
+ border: "1px solid var(--curator-border, rgba(0,0,0,0.12))",
256
+ background: "var(--curator-surface, transparent)",
257
+ fontSize: 13,
258
+ };
259
+ const cardTitleStyle = { fontWeight: 600 };
260
+ const cardMetaStyle = { opacity: 0.7, fontSize: 12 };
261
+ const viewWrapStyle = { ...cardStyle, padding: 0, overflow: "hidden" };
262
+ const viewHeaderStyle = {
263
+ display: "flex",
264
+ justifyContent: "space-between",
265
+ alignItems: "baseline",
266
+ gap: 8,
267
+ padding: "6px 10px",
268
+ borderBottom: "1px solid var(--curator-border, rgba(0,0,0,0.08))",
269
+ };
270
+ const frameContainerStyle = { width: "100%", transition: "height 200ms ease-out" };
271
+ //# sourceMappingURL=McpAppToolPart.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"McpAppToolPart.js","sourceRoot":"","sources":["../../../src/mcpApps/McpAppToolPart.tsx"],"names":[],"mappings":"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"}
@@ -0,0 +1,127 @@
1
+ /**
2
+ * Host side of the MCP Apps (SEP-1865) bridge: JSON-RPC 2.0 over a message
3
+ * transport, from the widget to one rendered view.
4
+ *
5
+ * Pure. Knows nothing about React, iframes or the network: the caller hands
6
+ * it a `post` function to reach the view and feeds it every message the view
7
+ * sends. Everything the view may ask for is a `handlers` callback, so the
8
+ * whole protocol can be exercised in a unit test with a fake view.
9
+ *
10
+ * What the view may do, and what this bridge does with it:
11
+ *
12
+ * ui/initialize → handshake; answers with host info,
13
+ * capabilities and context
14
+ * ui/notifications/initialized → view is ready; deliver the tool input,
15
+ * then the tool result once known
16
+ * tools/call → handlers.callTool (the Curator data plane)
17
+ * ui/message → handlers.sendMessage (app-reported text)
18
+ * ui/update-model-context → handlers.updateModelContext (surfaced only)
19
+ * ui/open-link → handlers.openLink (http(s) only)
20
+ * ui/request-display-mode → always `inline` in v1
21
+ * ui/notifications/size-changed → handlers.onSizeChange
22
+ * notifications/message → handlers.onLog
23
+ * ping → {}
24
+ * anything else → JSON-RPC "method not found"
25
+ *
26
+ * Method names are the ones ext-apps 2.0 emits (`ui/…`). The deprecated
27
+ * `notifications/…` spellings assistant-ui also accepts are NOT supported:
28
+ * fewer names to reason about, and our reference view uses the current SDK.
29
+ */
30
+ export declare const MCP_APPS_PROTOCOL_VERSION = "2026-01-26";
31
+ export interface CallToolResultLike {
32
+ content: Array<Record<string, unknown>>;
33
+ structuredContent?: Record<string, unknown>;
34
+ isError?: boolean;
35
+ _meta?: Record<string, unknown>;
36
+ }
37
+ export interface HostContext {
38
+ theme?: "light" | "dark";
39
+ displayMode?: "inline";
40
+ availableDisplayModes?: Array<"inline">;
41
+ platform?: "web";
42
+ locale?: string;
43
+ styles?: {
44
+ variables?: Record<string, string>;
45
+ };
46
+ containerDimensions?: {
47
+ width?: number;
48
+ maxHeight?: number;
49
+ };
50
+ [k: string]: unknown;
51
+ }
52
+ export interface HostBridgeHandlers {
53
+ callTool: (params: {
54
+ name: string;
55
+ arguments?: Record<string, unknown>;
56
+ _meta?: Record<string, unknown>;
57
+ }) => Promise<CallToolResultLike>;
58
+ /** App-reported text from the view. Return false to refuse. */
59
+ sendMessage: (text: string) => Promise<boolean>;
60
+ updateModelContext?: (params: {
61
+ content?: unknown;
62
+ structuredContent?: unknown;
63
+ }) => void;
64
+ openLink?: (url: string) => boolean;
65
+ onSizeChange?: (size: {
66
+ width?: number;
67
+ height?: number;
68
+ }) => void;
69
+ onLog?: (params: unknown) => void;
70
+ onInitialized?: () => void;
71
+ onError?: (error: Error) => void;
72
+ }
73
+ export interface HostBridgeOptions {
74
+ post: (message: unknown) => void;
75
+ handlers: HostBridgeHandlers;
76
+ hostInfo?: {
77
+ name: string;
78
+ version: string;
79
+ };
80
+ hostContext?: HostContext;
81
+ /** Cap on the text a view may put in the transcript. */
82
+ maxMessageChars?: number;
83
+ }
84
+ /**
85
+ * The text of a spec-shaped `ui/message`: `{ role, content: [{type:"text", text}] }`.
86
+ * Also accepts a bare `{ text }` for lenient views. Control characters are
87
+ * stripped and the length capped; the result is plain text, never markup.
88
+ */
89
+ export declare function extractMessageText(params: unknown, maxChars?: number): string | null;
90
+ /** Only web links leave the sandbox. */
91
+ export declare function isOpenableUrl(url: unknown): url is string;
92
+ export declare class McpAppHostBridge {
93
+ private readonly post;
94
+ private readonly handlers;
95
+ private readonly hostInfo;
96
+ private hostContext;
97
+ private readonly maxMessageChars;
98
+ private initialized;
99
+ private closed;
100
+ private nextId;
101
+ private readonly pending;
102
+ /** Tool input, delivered on `initialized` (or immediately when already ready). */
103
+ private toolInput;
104
+ private toolInputSent;
105
+ /** Tool result, delivered after input once known. */
106
+ private toolResult;
107
+ private toolResultSent;
108
+ constructor(opts: HostBridgeOptions);
109
+ get isInitialized(): boolean;
110
+ setToolInput(args: Record<string, unknown>): void;
111
+ setToolResult(result: CallToolResultLike): void;
112
+ notifyToolCancelled(reason: string): void;
113
+ updateHostContext(patch: HostContext): void;
114
+ /** Ask the view to tear down; resolves when it answers or after `timeoutMs`. */
115
+ teardown(timeoutMs?: number): Promise<void>;
116
+ close(): void;
117
+ /** Feed one message received from the view. Non-JSON-RPC traffic is ignored. */
118
+ onMessage(data: unknown): void;
119
+ private handleRequest;
120
+ private handleNotification;
121
+ private flush;
122
+ private notify;
123
+ private request;
124
+ private respond;
125
+ private error;
126
+ }
127
+ //# sourceMappingURL=hostBridge.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"hostBridge.d.ts","sourceRoot":"","sources":["../../../src/mcpApps/hostBridge.ts"],"names":[],"mappings":"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"}