@miragon/mcp-toolkit-ui 0.10.1 → 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 (49) hide show
  1. package/README.md +7 -7
  2. package/dist/app/adapt-data-widget.d.ts +26 -5
  3. package/dist/app/adapt-data-widget.d.ts.map +1 -1
  4. package/dist/app/adapt-data-widget.js +39 -5
  5. package/dist/app/adapt-data-widget.js.map +1 -1
  6. package/dist/app/host-bridge.d.ts +52 -46
  7. package/dist/app/host-bridge.d.ts.map +1 -1
  8. package/dist/app/host-bridge.js +30 -52
  9. package/dist/app/host-bridge.js.map +1 -1
  10. package/dist/app/index.d.ts +5 -4
  11. package/dist/app/index.d.ts.map +1 -1
  12. package/dist/app/index.js +9 -8
  13. package/dist/app/index.js.map +1 -1
  14. package/dist/app/mcp-app-view.d.ts.map +1 -1
  15. package/dist/app/mcp-app-view.js +37 -24
  16. package/dist/app/mcp-app-view.js.map +1 -1
  17. package/dist/app/mcp-toolkit-app.d.ts +21 -10
  18. package/dist/app/mcp-toolkit-app.d.ts.map +1 -1
  19. package/dist/app/mcp-toolkit-app.js +26 -12
  20. package/dist/app/mcp-toolkit-app.js.map +1 -1
  21. package/dist/app/mcp-use-host-bridge.d.ts +29 -0
  22. package/dist/app/mcp-use-host-bridge.d.ts.map +1 -0
  23. package/dist/app/mcp-use-host-bridge.js +120 -0
  24. package/dist/app/mcp-use-host-bridge.js.map +1 -0
  25. package/dist/app/use-host-actions.d.ts +6 -6
  26. package/dist/app/use-host-actions.js +6 -6
  27. package/dist/app/widget-fixture.d.ts +24 -21
  28. package/dist/app/widget-fixture.d.ts.map +1 -1
  29. package/dist/app/widget-fixture.js +27 -123
  30. package/dist/app/widget-fixture.js.map +1 -1
  31. package/dist/hooks/use-tool-result-recovery.d.ts +40 -15
  32. package/dist/hooks/use-tool-result-recovery.d.ts.map +1 -1
  33. package/dist/hooks/use-tool-result-recovery.js +57 -4
  34. package/dist/hooks/use-tool-result-recovery.js.map +1 -1
  35. package/dist/index.js +1 -1
  36. package/dist/index.js.map +1 -1
  37. package/package.json +16 -8
  38. package/src/app/adapt-data-widget.tsx +50 -6
  39. package/src/app/host-bridge.test.ts +107 -0
  40. package/src/app/host-bridge.tsx +85 -82
  41. package/src/app/index.ts +15 -10
  42. package/src/app/mcp-app-view.tsx +41 -32
  43. package/src/app/mcp-toolkit-app.tsx +33 -16
  44. package/src/app/mcp-use-host-bridge.tsx +164 -0
  45. package/src/app/use-host-actions.tsx +6 -6
  46. package/src/app/widget-fixture.tsx +35 -156
  47. package/src/hooks/use-tool-result-recovery.ts +75 -19
  48. package/src/index.ts +1 -1
  49. package/ui-catalog.json +81 -27
@@ -1,15 +1,7 @@
1
- import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
2
- import { createContext, useContext, useEffect, useMemo, useRef, useSyncExternalStore, } from "react";
3
- import { useWidget } from "mcp-use/react";
1
+ import { jsx as _jsx } from "react/jsx-runtime";
2
+ import { createContext, useContext, useMemo } from "react";
4
3
  import { AppQueryProvider } from "../providers/query-provider.js";
5
4
  import { HostBridgeProvider, createStandaloneHostBridge } from "./host-bridge.js";
6
- /**
7
- * Key `mcp-use` writes the serialized model-context string under when it flushes
8
- * to `window.openai.setWidgetState`. Mirrors `MODEL_CONTEXT_KEY` in
9
- * `mcp-use/react` (not exported, so duplicated here). The harness intercepts
10
- * `setWidgetState` and reads this field to surface what the model would see.
11
- */
12
- const MODEL_CONTEXT_KEY = "__model_context";
13
5
  /**
14
6
  * Pure, host-free registry of fake tool implementations. Drives every
15
7
  * `callTool` path the harness exposes (`window.openai.callTool`, the toolkit's
@@ -89,9 +81,10 @@ export function useFixtureHost() {
89
81
  return useContext(FixtureHostContext);
90
82
  }
91
83
  /**
92
- * Default host-context globals a widget sees in the harness. Chosen to be
93
- * harmless and inert: inline display, light theme, desktop, no safe-area
94
- * insets. Overridable per-mount via {@link WidgetFixtureHostProps.globals}.
84
+ * Default host-context values the harness reports. Only `theme` is read since
85
+ * the mcp-use 2.x move (the other host globals were consumed by the 1.x
86
+ * `window.openai` shim); the object keeps its shape so existing playground
87
+ * setups that spread overrides keep compiling.
95
88
  */
96
89
  const DEFAULT_GLOBALS = {
97
90
  theme: "light",
@@ -104,60 +97,6 @@ const DEFAULT_GLOBALS = {
104
97
  capabilities: { hover: true, touch: false },
105
98
  },
106
99
  };
107
- /**
108
- * Build the `window.openai` shim the `mcp-use` React hooks read from. Routes
109
- * `callTool` through the fixture registry and reports every other bridge verb
110
- * to `onHostAction`. Returns `null` outside a browser-like environment (SSR)
111
- * so the harness degrades to a plain render rather than throwing.
112
- */
113
- function buildOpenAiShim(registry, toolOutput, toolInput, globals, onHostAction, onModelContext) {
114
- if (typeof window === "undefined")
115
- return null;
116
- return {
117
- ...DEFAULT_GLOBALS,
118
- ...globals,
119
- toolInput,
120
- toolOutput,
121
- toolResponseMetadata: null,
122
- widgetState: null,
123
- callTool: async (name, args) => {
124
- onHostAction?.({ type: "callTool", name, args });
125
- return registry.call(name, args);
126
- },
127
- sendFollowUpMessage: (args) => {
128
- onHostAction?.({ type: "sendFollowUpMessage", prompt: args.prompt });
129
- return Promise.resolve();
130
- },
131
- openExternal: (payload) => {
132
- onHostAction?.({ type: "openExternal", href: payload.href });
133
- },
134
- requestDisplayMode: (args) => {
135
- onHostAction?.({ type: "requestDisplayMode", mode: args.mode });
136
- return Promise.resolve({ mode: args.mode });
137
- },
138
- setWidgetState: (state) => {
139
- onHostAction?.({ type: "setWidgetState", state });
140
- // `mcp-use` flushes the serialized `<ModelContext>` tree through
141
- // setWidgetState under MODEL_CONTEXT_KEY — surface it as the model view.
142
- const ctx = state?.[MODEL_CONTEXT_KEY];
143
- if (typeof ctx === "string")
144
- onModelContext?.(ctx);
145
- return Promise.resolve();
146
- },
147
- notifyIntrinsicHeight: () => Promise.resolve(),
148
- };
149
- }
150
- /**
151
- * Renders nothing but mounts a `useWidget()` so `mcp-use` registers its
152
- * model-context flush handler — even for widgets that never call `useWidget`
153
- * themselves (e.g. a simple `({ keys })` card). Without this, a widget's
154
- * `<ModelContext>` would render but never flush, and `onModelContext` would
155
- * stay silent. The flush routes through our `setWidgetState` shim above.
156
- */
157
- function ModelContextPump() {
158
- useWidget();
159
- return null;
160
- }
161
100
  /**
162
101
  * Build the `WidgetProps` envelope the harness passes to the widget. Seeds a
163
102
  * single pipeline step from `data` (keyed by `dataType` when given) and uses
@@ -186,66 +125,37 @@ export function buildFixtureWidgetProps(data, dataType) {
186
125
  * without booting a real MCP host or backend.
187
126
  *
188
127
  * ### What it mocks
189
- * - **`window.openai`** — the `mcp-use` Apps-SDK bridge `useWidget`/`useCallTool`
190
- * read from. Installed on mount, removed on unmount. `callTool` is routed to a
191
- * {@link FixtureCallToolRegistry} built from `tools`; `sendFollowUpMessage`,
192
- * `openExternal`, etc. are reported to `onHostAction`.
128
+ * - **A {@link HostBridge}** — a `createStandaloneHostBridge` over the fixture
129
+ * registry and callbacks, provided via `HostBridgeProvider`. `callTool`
130
+ * resolves against the {@link FixtureCallToolRegistry} built from `tools`;
131
+ * `sendFollowup` / `openExternal` are reported to `onHostAction`;
132
+ * `setModelContext` feeds `onModelContext`, so you can *see* what the model
133
+ * would (adapted widgets report through this bridge outside a real view).
193
134
  * - **The toolkit `AppQueryProvider`** — so widgets that fetch via `useToolQuery`
194
135
  * (e.g. generated `use*` hooks) resolve against the same registry.
195
- * - **`ModelContext`** — a flush handler captures the serialized context string
196
- * and forwards it to `onModelContext`, so you can *see* what the model would.
197
- * - **A {@link HostBridge}** — a `createStandaloneHostBridge` over the same
198
- * registry and callbacks, provided via `HostBridgeProvider`, so widgets
199
- * written against `useHostBridge` (the host-portable pattern) are simulated
200
- * from the same single source as the `window.openai` shim above.
201
136
  *
202
137
  * ### Boundaries
203
- * `mcp-use`'s hooks select their provider from `window.openai` presence; this
204
- * harness deliberately drives the Apps-SDK path (sets `window.openai`) rather
205
- * than the `postMessage` bridge, which only activates inside a cross-origin
206
- * iframe. The shim is intentionally minimal — it is not a host, and host
207
- * features beyond the bridge verbs above are out of scope.
138
+ * The harness simulates the **host-portable pattern** (`useHostBridge`,
139
+ * `useToolQuery`) — the surface the toolkit's skills teach. It does not
140
+ * simulate the mcp-use 2.x view runtime: since 2.x the `mcp-use/react` hooks
141
+ * only run under a `bootstrapView`-mounted view speaking the ext-apps
142
+ * postMessage protocol (the 1.x `window.openai` shim this harness used to
143
+ * install has no equivalent seam). A widget that calls `mcp-use/react` hooks
144
+ * directly must be exercised against a real host — or rewritten against
145
+ * `useHostBridge`, which is the portable contract anyway.
208
146
  */
209
147
  export function WidgetFixtureHost({ widget: Widget, data = {}, dataType, tools, globals, onModelContext, onHostAction, }) {
210
148
  // One registry per `tools` identity. Rebuilt when the fixture map changes so
211
149
  // edits in the playground take effect without a full remount.
212
150
  const registry = useMemo(() => new FixtureCallToolRegistry(tools), [tools]);
213
- // Latest callbacks without re-installing the shim on every render. Updated in
214
- // an effect (not during render) so the shim's closures always see the newest
215
- // handler while the `window.openai` install effect stays stable.
216
- const onHostActionRef = useRef(onHostAction);
217
- const onModelContextRef = useRef(onModelContext);
218
- useEffect(() => {
219
- onHostActionRef.current = onHostAction;
220
- onModelContextRef.current = onModelContext;
221
- });
222
151
  const widgetProps = useMemo(() => buildFixtureWidgetProps(data, dataType), [data, dataType]);
223
- // Install the `window.openai` shim for the lifetime of this mount. Wake any
224
- // already-mounted `mcp-use` hooks via the `set_globals` event they listen for.
225
- useEffect(() => {
226
- if (typeof window === "undefined")
227
- return;
228
- const shim = buildOpenAiShim(registry, data ?? null, data ?? {}, globals ?? {}, (action) => onHostActionRef.current?.(action), (text) => onModelContextRef.current?.(text));
229
- if (!shim)
230
- return;
231
- const prev = window.openai;
232
- window.openai = shim;
233
- window.dispatchEvent(new CustomEvent("openai:set_globals", { detail: { globals: shim } }));
234
- return () => {
235
- ;
236
- window.openai = prev;
237
- };
238
- }, [registry, data, globals]);
239
152
  const callTool = useMemo(() => async (name, args) => registry.call(name, args ?? {}), [registry]);
240
- // A standalone host bridge over the same registry + callbacks, so portable
241
- // widgets written against `useHostBridge` (rather than the `mcp-use` host
242
- // hooks) are simulated from the *same* source as the `window.openai` shim.
243
- // It logs through the same `HostActionLog` channel, so the playground's
244
- // activity log shows tool calls, follow-ups, and links identically whether the
245
- // widget uses the mcp-use path or the host bridge. Reading globals.theme keeps
246
- // the bridge's reported theme in sync with the shim. Depends on the callback
247
- // props directly (not the refs) — a fresh Provider value on callback change is
248
- // fine for a dev harness, and keeps the bridge's closures pure of ref reads.
153
+ // The standalone host bridge is the harness's single simulation source: it
154
+ // logs every verb through the `HostActionLog` channel for the playground's
155
+ // activity log. Depends on the callback props directly — a fresh Provider
156
+ // value on callback change is fine for a dev harness. Only `globals.theme`
157
+ // still influences the simulated host (the remaining globals fed the 1.x
158
+ // `window.openai` shim).
249
159
  const bridgeTheme = (globals?.theme ?? DEFAULT_GLOBALS.theme) === "dark" ? "dark" : "light";
250
160
  const bridge = useMemo(() => createStandaloneHostBridge({
251
161
  callTool: (name, args) => {
@@ -259,15 +169,9 @@ export function WidgetFixtureHost({ widget: Widget, data = {}, dataType, tools,
259
169
  theme: bridgeTheme,
260
170
  }), [registry, data, bridgeTheme, onHostAction, onModelContext]);
261
171
  const value = useMemo(() => ({ registry }), [registry]);
262
- // Mount the model-context pump only on the client. The pump calls `mcp-use`'s
263
- // `useWidget`, whose `useSyncExternalStore` lacks a server snapshot and throws
264
- // under `react-dom/server` — gating it keeps the harness (and any widget
265
- // rendered through it) SSR-safe. `useSyncExternalStore` with a `false` server
266
- // snapshot is the idiomatic "are we on the client?" check (no setState-in-effect).
267
- const isClient = useSyncExternalStore(() => () => { }, () => true, () => false);
268
172
  // Spread `widgetProps` (keys/context) AND a `data` alias so both adapted
269
173
  // widgets and raw `({ data })` widgets read their fixture from one mount.
270
174
  const RenderWidget = Widget;
271
- return (_jsxs(FixtureHostContext.Provider, { value: value, children: [isClient && _jsx(ModelContextPump, {}), _jsx(HostBridgeProvider, { bridge: bridge, children: _jsx(AppQueryProvider, { callTool: callTool, children: _jsx(RenderWidget, { ...widgetProps, data: data }) }) })] }));
175
+ return (_jsx(FixtureHostContext.Provider, { value: value, children: _jsx(HostBridgeProvider, { bridge: bridge, children: _jsx(AppQueryProvider, { callTool: callTool, children: _jsx(RenderWidget, { ...widgetProps, data: data }) }) }) }));
272
176
  }
273
177
  //# sourceMappingURL=widget-fixture.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"widget-fixture.js","sourceRoot":"","sources":["../../src/app/widget-fixture.tsx"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"widget-fixture.js","sourceRoot":"","sources":["../../src/app/widget-fixture.tsx"],"names":[],"mappings":"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"}
@@ -1,37 +1,62 @@
1
1
  /**
2
2
  * Recovery for hosts that deliver the `ui/notifications/tool-result`
3
3
  * notification without `structuredContent` (observed on claude.ai and Claude
4
- * Desktop, which forward only the model-facing `content` blocks). The
5
- * mcp-use bridge then hands the widget an empty props object and the shell
6
- * would idle on its loading skeleton forever.
4
+ * Desktop, which forward only the model-facing `content` blocks). Since
5
+ * mcp-use 2.x such a result is not even observable: the `useToolContext`
6
+ * latch ignores content-only successes, so the tool status stays `"pending"`
7
+ * forever and the shell would idle on its loading skeleton.
7
8
  *
8
- * When the result is ready but the payload is invalid, the hook re-executes
9
- * the originating tool once via the host bridge's official `callTool` —
10
- * tool-call RESPONSES carry `structuredContent` intact on those hosts — and
11
- * exposes the decoded payload. Spec-conforming hosts (e.g. the mcp-use
12
- * inspector) deliver a valid payload up front, so the recovery never fires
13
- * there.
9
+ * Because the stripped notification is invisible, readiness is inferred two
10
+ * ways: the hard `resultReady` signal (the latch fired but the payload is
11
+ * invalid), or a grace timer — once the originating tool is known and no
12
+ * result has latched within
13
+ * {@link ToolResultRecoveryOptions.assumeStrippedAfterMs}, the result is
14
+ * assumed delivered-but-stripped. Either way the hook re-executes the
15
+ * originating tool once via the host bridge's official `callTool` — tool-call
16
+ * RESPONSES carry `structuredContent` intact on those hosts — and exposes the
17
+ * decoded payload. Spec-conforming hosts (e.g. the mcp-use inspector) deliver
18
+ * a valid payload up front, so the recovery never fires there.
14
19
  *
15
20
  * Assumes the originating tool is a read-only render pipeline (true for all
16
21
  * toolkit `render-view`/`show_*` tools) — the re-execution must be safe to
17
- * repeat.
22
+ * repeat, and may rarely run concurrently with the original invocation when
23
+ * the grace timer beats a slow but conforming host.
18
24
  */
25
+ /**
26
+ * Default grace period before a silent latch counts as a stripped result.
27
+ * Long enough for a conforming host to latch a typical render tool first,
28
+ * short enough that users on stripping hosts are not left staring at the
29
+ * skeleton noticeably.
30
+ */
31
+ export declare const DEFAULT_ASSUME_STRIPPED_AFTER_MS = 2500;
19
32
  export interface ToolResultRecoveryOptions {
20
- /** `!isPending` from `useWidget` — the host reported a finished tool call. */
33
+ /**
34
+ * The latch fired (`useToolContext().status !== "pending"`) — a structured
35
+ * result or tool error arrived. On hosts that strip `structuredContent`
36
+ * this never turns true; the grace timer below covers that case.
37
+ */
21
38
  resultReady: boolean;
22
- /** The props the host delivered (`useWidget().props`). */
39
+ /** The payload the host delivered (`useToolContext().toolOutput`). */
23
40
  props: unknown;
24
41
  /**
25
42
  * Validates a candidate payload. MUST be referentially stable (module-level
26
43
  * function or memoised) — it is an effect dependency.
27
44
  */
28
45
  isValid: (value: unknown) => boolean;
29
- /** The tool arguments from `ui/notifications/tool-input` (`useWidget().toolInput`). */
46
+ /** The tool arguments from `ui/notifications/tool-input` (`useToolContext().toolInput`). */
30
47
  toolInput: Record<string, unknown> | null | undefined;
31
- /** Raw host context (`useWidget().hostContext`); `toolInfo` names the originating tool. */
48
+ /** Raw host context (`useHostContext().hostContext`); `toolInfo` names the originating tool. */
32
49
  hostContext: Record<string, unknown> | null | undefined;
33
- /** The bridge's `callTool` (`useWidget().callTool`). */
50
+ /** The host bridge's `callTool`. */
34
51
  callTool: (name: string, args: Record<string, unknown>) => Promise<unknown>;
52
+ /**
53
+ * Grace period in ms after which a silent latch counts as a stripped
54
+ * result. Armed once the originating tool is known while `resultReady` is
55
+ * still false; re-armed on every `toolInput` update, because streaming
56
+ * arguments mean the invocation may not have finished yet. Defaults to
57
+ * {@link DEFAULT_ASSUME_STRIPPED_AFTER_MS}.
58
+ */
59
+ assumeStrippedAfterMs?: number;
35
60
  }
36
61
  export interface ToolResultRecoveryState<T> {
37
62
  /** The recovered payload, `null` until the re-execution resolved (or when it failed). */
@@ -1 +1 @@
1
- {"version":3,"file":"use-tool-result-recovery.d.ts","sourceRoot":"","sources":["../../src/hooks/use-tool-result-recovery.ts"],"names":[],"mappings":"AAGA;;;;;;;;;;;;;;;;;GAiBG;AAEH,MAAM,WAAW,yBAAyB;IACxC,8EAA8E;IAC9E,WAAW,EAAE,OAAO,CAAA;IACpB,0DAA0D;IAC1D,KAAK,EAAE,OAAO,CAAA;IACd;;;OAGG;IACH,OAAO,EAAE,CAAC,KAAK,EAAE,OAAO,KAAK,OAAO,CAAA;IACpC,uFAAuF;IACvF,SAAS,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,IAAI,GAAG,SAAS,CAAA;IACrD,2FAA2F;IAC3F,WAAW,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,IAAI,GAAG,SAAS,CAAA;IACvD,wDAAwD;IACxD,QAAQ,EAAE,CAAC,IAAI,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,KAAK,OAAO,CAAC,OAAO,CAAC,CAAA;CAC5E;AAED,MAAM,WAAW,uBAAuB,CAAC,CAAC;IACxC,yFAAyF;IACzF,IAAI,EAAE,CAAC,GAAG,IAAI,CAAA;IACd,oGAAoG;IACpG,MAAM,EAAE,OAAO,CAAA;CAChB;AAID;;;;GAIG;AACH,wBAAgB,uBAAuB,CAAC,WAAW,EAAE,OAAO,GAAG,MAAM,GAAG,SAAS,CAehF;AAED;;;GAGG;AACH,wBAAgB,qBAAqB,CAAC,CAAC,EACrC,MAAM,EAAE,OAAO,EACf,OAAO,EAAE,CAAC,KAAK,EAAE,OAAO,KAAK,OAAO,GACnC,CAAC,GAAG,IAAI,CAQV;AAED,wBAAgB,qBAAqB,CAAC,CAAC,EACrC,OAAO,EAAE,yBAAyB,GACjC,uBAAuB,CAAC,CAAC,CAAC,CAqD5B"}
1
+ {"version":3,"file":"use-tool-result-recovery.d.ts","sourceRoot":"","sources":["../../src/hooks/use-tool-result-recovery.ts"],"names":[],"mappings":"AAGA;;;;;;;;;;;;;;;;;;;;;;;GAuBG;AAEH;;;;;GAKG;AACH,eAAO,MAAM,gCAAgC,OAAO,CAAA;AAEpD,MAAM,WAAW,yBAAyB;IACxC;;;;OAIG;IACH,WAAW,EAAE,OAAO,CAAA;IACpB,sEAAsE;IACtE,KAAK,EAAE,OAAO,CAAA;IACd;;;OAGG;IACH,OAAO,EAAE,CAAC,KAAK,EAAE,OAAO,KAAK,OAAO,CAAA;IACpC,4FAA4F;IAC5F,SAAS,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,IAAI,GAAG,SAAS,CAAA;IACrD,gGAAgG;IAChG,WAAW,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,IAAI,GAAG,SAAS,CAAA;IACvD,oCAAoC;IACpC,QAAQ,EAAE,CAAC,IAAI,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,KAAK,OAAO,CAAC,OAAO,CAAC,CAAA;IAC3E;;;;;;OAMG;IACH,qBAAqB,CAAC,EAAE,MAAM,CAAA;CAC/B;AAED,MAAM,WAAW,uBAAuB,CAAC,CAAC;IACxC,yFAAyF;IACzF,IAAI,EAAE,CAAC,GAAG,IAAI,CAAA;IACd,oGAAoG;IACpG,MAAM,EAAE,OAAO,CAAA;CAChB;AAID;;;;GAIG;AACH,wBAAgB,uBAAuB,CAAC,WAAW,EAAE,OAAO,GAAG,MAAM,GAAG,SAAS,CAehF;AAED;;;GAGG;AACH,wBAAgB,qBAAqB,CAAC,CAAC,EACrC,MAAM,EAAE,OAAO,EACf,OAAO,EAAE,CAAC,KAAK,EAAE,OAAO,KAAK,OAAO,GACnC,CAAC,GAAG,IAAI,CAQV;AAED,wBAAgB,qBAAqB,CAAC,CAAC,EACrC,OAAO,EAAE,yBAAyB,GACjC,uBAAuB,CAAC,CAAC,CAAC,CAmF5B"}
@@ -1,5 +1,36 @@
1
1
  import { useEffect, useRef, useState } from "react";
2
2
  import { parseToolResult } from "../lib/parse-tool-result.js";
3
+ /**
4
+ * Recovery for hosts that deliver the `ui/notifications/tool-result`
5
+ * notification without `structuredContent` (observed on claude.ai and Claude
6
+ * Desktop, which forward only the model-facing `content` blocks). Since
7
+ * mcp-use 2.x such a result is not even observable: the `useToolContext`
8
+ * latch ignores content-only successes, so the tool status stays `"pending"`
9
+ * forever and the shell would idle on its loading skeleton.
10
+ *
11
+ * Because the stripped notification is invisible, readiness is inferred two
12
+ * ways: the hard `resultReady` signal (the latch fired but the payload is
13
+ * invalid), or a grace timer — once the originating tool is known and no
14
+ * result has latched within
15
+ * {@link ToolResultRecoveryOptions.assumeStrippedAfterMs}, the result is
16
+ * assumed delivered-but-stripped. Either way the hook re-executes the
17
+ * originating tool once via the host bridge's official `callTool` — tool-call
18
+ * RESPONSES carry `structuredContent` intact on those hosts — and exposes the
19
+ * decoded payload. Spec-conforming hosts (e.g. the mcp-use inspector) deliver
20
+ * a valid payload up front, so the recovery never fires there.
21
+ *
22
+ * Assumes the originating tool is a read-only render pipeline (true for all
23
+ * toolkit `render-view`/`show_*` tools) — the re-execution must be safe to
24
+ * repeat, and may rarely run concurrently with the original invocation when
25
+ * the grace timer beats a slow but conforming host.
26
+ */
27
+ /**
28
+ * Default grace period before a silent latch counts as a stripped result.
29
+ * Long enough for a conforming host to latch a typical render tool first,
30
+ * short enough that users on stripping hosts are not left staring at the
31
+ * skeleton noticeably.
32
+ */
33
+ export const DEFAULT_ASSUME_STRIPPED_AFTER_MS = 2500;
3
34
  const IDLE = { data: null, failed: false };
4
35
  /**
5
36
  * Resolves the originating tool name from the host context's `toolInfo`.
@@ -40,7 +71,7 @@ export function decodeRecoveredResult(result, isValid) {
40
71
  return decoded !== null && isValid(decoded) ? decoded : null;
41
72
  }
42
73
  export function useToolResultRecovery(options) {
43
- const { resultReady, props, isValid, toolInput, hostContext, callTool } = options;
74
+ const { resultReady, props, isValid, toolInput, hostContext, callTool, assumeStrippedAfterMs = DEFAULT_ASSUME_STRIPPED_AFTER_MS, } = options;
44
75
  const [state, setState] = useState(IDLE);
45
76
  // Single-flight: the promise ref survives StrictMode's dev-mode
46
77
  // effect re-run (cleanup + setup on the same instance), so the re-run
@@ -48,16 +79,38 @@ export function useToolResultRecovery(options) {
48
79
  const flightRef = useRef(null);
49
80
  const flightInputRef = useRef(null);
50
81
  const toolName = resolveRecoveryToolName(hostContext);
82
+ // A stripped result is unobservable (the 2.x latch ignores content-only
83
+ // results), so infer it: once a recovery could fire but the latch has been
84
+ // silent for the grace period, treat the result as delivered-but-stripped.
85
+ // Re-armed on every toolInput identity change — streaming arguments mean
86
+ // the invocation may still be running, so the grace period starts over.
87
+ // The re-arm is a render-phase reset (not an effect) so the cascading-
88
+ // render lint stays satisfied; the timer effect below restarts anyway
89
+ // because toolInput is one of its dependencies.
90
+ const [assumedReady, setAssumedReady] = useState(false);
91
+ const [prevTimerInput, setPrevTimerInput] = useState(toolInput);
92
+ if (prevTimerInput !== toolInput) {
93
+ setPrevTimerInput(toolInput);
94
+ if (assumedReady)
95
+ setAssumedReady(false);
96
+ }
97
+ useEffect(() => {
98
+ if (resultReady || toolName === undefined)
99
+ return;
100
+ const timer = setTimeout(() => setAssumedReady(true), assumeStrippedAfterMs);
101
+ return () => clearTimeout(timer);
102
+ }, [resultReady, toolName, toolInput, assumeStrippedAfterMs]);
103
+ const ready = resultReady || assumedReady;
51
104
  useEffect(() => {
52
105
  // A new tool run (result no longer ready, or fresh tool-input identity)
53
106
  // invalidates any previous recovery attempt and re-arms the single-flight.
54
- if (flightRef.current && (!resultReady || flightInputRef.current !== toolInput)) {
107
+ if (flightRef.current && (!ready || flightInputRef.current !== toolInput)) {
55
108
  flightRef.current = null;
56
109
  setState((prev) => (prev.data === null && !prev.failed ? prev : IDLE));
57
110
  }
58
111
  // Never fire on conforming hosts (valid payload) or before the
59
112
  // originating tool is known.
60
- if (!resultReady || isValid(props) || toolName === undefined)
113
+ if (!ready || isValid(props) || toolName === undefined)
61
114
  return;
62
115
  if (!flightRef.current) {
63
116
  flightInputRef.current = toolInput;
@@ -87,7 +140,7 @@ export function useToolResultRecovery(options) {
87
140
  return () => {
88
141
  stale = true;
89
142
  };
90
- }, [resultReady, props, isValid, toolName, toolInput, callTool]);
143
+ }, [ready, props, isValid, toolName, toolInput, callTool]);
91
144
  return state;
92
145
  }
93
146
  //# sourceMappingURL=use-tool-result-recovery.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"use-tool-result-recovery.js","sourceRoot":"","sources":["../../src/hooks/use-tool-result-recovery.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"use-tool-result-recovery.js","sourceRoot":"","sources":["../../src/hooks/use-tool-result-recovery.ts"],"names":[],"mappings":"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"}
package/dist/index.js CHANGED
@@ -49,7 +49,7 @@ export { LocaleProvider, useLocale, useTranslate } from "./locale/index.js";
49
49
  // NOTE: MCP App shell (McpAppView, WidgetRenderer) is exported from the
50
50
  // `./app` subpath only. Keeping it out of the main barrel prevents consumers
51
51
  // that only need primitives (e.g. an admin portal) from pulling `mcp-use/react`
52
- // and its langchain transitive peer into their Vite bundle.
52
+ // — the 2.x view runtime and its ext-apps transitive — into their Vite bundle.
53
53
  // Utils
54
54
  export { cn } from "./lib/utils.js";
55
55
  export { parseToolResult, parseViewToolResult } from "./lib/parse-tool-result.js";
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"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"}
package/package.json CHANGED
@@ -1,7 +1,12 @@
1
1
  {
2
2
  "name": "@miragon/mcp-toolkit-ui",
3
- "version": "0.10.1",
3
+ "version": "1.1.0",
4
4
  "description": "React UI for MCP servers: shadcn primitives, composite components, TanStack Query hooks, and the MCP App shell (McpAppView + WidgetRenderer).",
5
+ "repository": {
6
+ "type": "git",
7
+ "url": "git+https://github.com/Miragon/mcp-toolkit.git",
8
+ "directory": "packages/ui"
9
+ },
5
10
  "type": "module",
6
11
  "sideEffects": [
7
12
  "**/*.css"
@@ -33,11 +38,11 @@
33
38
  "access": "public"
34
39
  },
35
40
  "peerDependencies": {
36
- "mcp-use": "1.34.5",
41
+ "mcp-use": "2.1.0",
37
42
  "react": "19.2.8",
38
43
  "react-dom": "19.2.8",
39
44
  "tailwindcss": "4.3.3",
40
- "@miragon/mcp-toolkit-core": "0.10.1"
45
+ "@miragon/mcp-toolkit-core": "1.1.0"
41
46
  },
42
47
  "dependencies": {
43
48
  "@base-ui/react": "1.6.0",
@@ -45,21 +50,24 @@
45
50
  "@tanstack/react-query": "5.101.4",
46
51
  "class-variance-authority": "0.7.1",
47
52
  "clsx": "2.1.1",
48
- "lucide-react": "1.25.0",
53
+ "lucide-react": "0.562.0",
49
54
  "radix-ui": "1.6.7",
50
55
  "tailwind-merge": "3.6.0",
51
56
  "tw-animate-css": "1.4.0"
52
57
  },
53
58
  "devDependencies": {
54
- "@types/react": "19.2.17",
55
- "@types/react-dom": "19.2.3",
56
- "mcp-use": "1.34.5",
59
+ "@types/react": "19.2.18",
60
+ "@types/react-dom": "19.2.4",
61
+ "mcp-use": "2.1.0",
57
62
  "react": "19.2.8",
58
63
  "react-dom": "19.2.8",
59
64
  "tailwindcss": "4.3.3",
60
65
  "typescript": "6.0.3",
61
66
  "vitest": "4.1.10",
62
- "@miragon/mcp-toolkit-core": "0.10.1"
67
+ "@miragon/mcp-toolkit-core": "1.1.0"
68
+ },
69
+ "engines": {
70
+ "node": ">=22.22.2"
63
71
  },
64
72
  "scripts": {
65
73
  "build": "tsc -p tsconfig.build.json",
@@ -1,6 +1,8 @@
1
- import type { ComponentType } from "react"
1
+ import { useEffect, type ComponentType, type ReactNode } from "react"
2
2
  import { ModelContext } from "mcp-use/react"
3
3
  import type { WidgetProps } from "@miragon/mcp-toolkit-core"
4
+ import { useHostBridgeOrNull } from "./host-bridge.js"
5
+ import { useIsInsideMcpUseView } from "./mcp-use-host-bridge.js"
4
6
  import type { WidgetComponent } from "./widget-renderer.js"
5
7
 
6
8
  /**
@@ -14,6 +16,44 @@ export type DescribeForModel<T> = (
14
16
  props: Readonly<Record<string, unknown>>,
15
17
  ) => string
16
18
 
19
+ /**
20
+ * Model-context reporting that works on every host — the host-portable
21
+ * replacement for rendering `mcp-use/react`'s `ModelContext` directly.
22
+ *
23
+ * mcp-use 2.x's `ModelContext` registers with the view runtime and THROWS
24
+ * outside a `bootstrapView` mount, so it is only rendered inside an mcp-use
25
+ * view (where it aggregates nested nodes into one tree). Everywhere else —
26
+ * ChatGPT via `createChatGptHostBridge`, the `WidgetFixtureHost` harness,
27
+ * standalone apps — the description flows through the bridge's
28
+ * `setModelContext` instead (last-writer-wins; fine for the single-widget
29
+ * mounts those hosts render).
30
+ *
31
+ * Widgets that self-fetch and report their own context (cockpit views like
32
+ * `TasksBoard`) must use this instead of importing `ModelContext` from
33
+ * `mcp-use/react` — the direct import crashes the widget in every non-view
34
+ * mount, starting with the widget playground.
35
+ */
36
+ export function HostModelContext({
37
+ content,
38
+ children,
39
+ }: {
40
+ content: string
41
+ children: ReactNode
42
+ }): ReactNode {
43
+ const insideView = useIsInsideMcpUseView()
44
+ if (insideView) return <ModelContext content={content}>{children}</ModelContext>
45
+ return <BridgeModelContext content={content}>{children}</BridgeModelContext>
46
+ }
47
+
48
+ function BridgeModelContext({ content, children }: { content: string; children: ReactNode }) {
49
+ const bridge = useHostBridgeOrNull()
50
+ const setModelContext = bridge?.setModelContext
51
+ useEffect(() => {
52
+ setModelContext?.(content)
53
+ }, [setModelContext, content])
54
+ return children
55
+ }
56
+
17
57
  /**
18
58
  * Wraps a "single-data" widget component (signature `({ data }: { data: T | null })`)
19
59
  * so it can be registered as a framework {@link WidgetComponent} (which receives
@@ -28,11 +68,11 @@ export type DescribeForModel<T> = (
28
68
  * times in one view with different scoping (e.g. one tab per process key).
29
69
  *
30
70
  * When `describeForModel` is provided the adapter wraps the widget in a
31
- * `ModelContext` so the model knows what the user is looking at (view identity,
32
- * active filters, headline numbers) without per-widget boilerplate. The
33
- * description is only rendered once the step data is present; widgets that
71
+ * `HostModelContext` so the model knows what the user is looking at (view
72
+ * identity, active filters, headline numbers) without per-widget boilerplate.
73
+ * The description is only rendered once the step data is present; widgets that
34
74
  * self-fetch when the adapter has no data (cockpit views) must render their own
35
- * `<ModelContext>` instead.
75
+ * `<HostModelContext>` instead.
36
76
  */
37
77
  export function adaptDataWidget<T>(
38
78
  Widget: ComponentType<{ data: T | null } & Record<string, unknown>>,
@@ -44,7 +84,11 @@ export function adaptDataWidget<T>(
44
84
  const data = (stepResult?.data ?? null) as T | null
45
85
  const widget = <Widget {...(widgetProps ?? {})} data={data} />
46
86
  if (data == null || !describeForModel) return widget
47
- return <ModelContext content={describeForModel(data, widgetProps ?? {})}>{widget}</ModelContext>
87
+ return (
88
+ <HostModelContext content={describeForModel(data, widgetProps ?? {})}>
89
+ {widget}
90
+ </HostModelContext>
91
+ )
48
92
  }
49
93
  AdaptedWidget.displayName = `Adapted(${Widget.displayName ?? Widget.name ?? "Widget"})`
50
94
  return AdaptedWidget