@nimblebrain/synapse 0.19.0 → 0.20.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/README.md +20 -25
- package/dist/check-JEM5PN64.cjs +435 -0
- package/dist/check-JEM5PN64.cjs.map +1 -0
- package/dist/check-YDZUQT6A.js +429 -0
- package/dist/check-YDZUQT6A.js.map +1 -0
- package/dist/{chunk-RU64F5RS.cjs → chunk-BNF352SA.cjs} +57 -146
- package/dist/chunk-BNF352SA.cjs.map +1 -0
- package/dist/{chunk-DRLVEHCD.js → chunk-DJS2FKBN.js} +21 -79
- package/dist/chunk-DJS2FKBN.js.map +1 -0
- package/dist/chunk-H3INUKA3.js +32 -0
- package/dist/chunk-H3INUKA3.js.map +1 -0
- package/dist/chunk-HQLSVUOR.cjs +667 -0
- package/dist/chunk-HQLSVUOR.cjs.map +1 -0
- package/dist/{chunk-NP7ROSH2.cjs → chunk-ISV6HFQE.cjs} +14 -7
- package/dist/chunk-ISV6HFQE.cjs.map +1 -0
- package/dist/chunk-TR2YNWZ5.js +658 -0
- package/dist/chunk-TR2YNWZ5.js.map +1 -0
- package/dist/{chunk-OYLZ5OCK.js → chunk-UKP4W6DI.js} +57 -146
- package/dist/chunk-UKP4W6DI.js.map +1 -0
- package/dist/{chunk-SZWHFTXV.cjs → chunk-YSL7KJNU.cjs} +21 -81
- package/dist/chunk-YSL7KJNU.cjs.map +1 -0
- package/dist/codegen/cli.cjs +41 -4
- package/dist/codegen/cli.cjs.map +1 -1
- package/dist/codegen/cli.js +41 -4
- package/dist/codegen/cli.js.map +1 -1
- package/dist/codegen/index.cjs +0 -1
- package/dist/codegen/index.d.cts +1 -1
- package/dist/codegen/index.d.ts +1 -1
- package/dist/codegen/index.js +0 -1
- package/dist/connect.iife.global.js +34 -34
- package/dist/{detect-DZMJsyvZ.d.cts → detect-DVGaL2bH.d.cts} +39 -33
- package/dist/{detect-DBwc8a21.d.ts → detect-DVGaL2bH.d.ts} +39 -33
- package/dist/host/index.cjs +17 -18
- package/dist/host/index.d.cts +11 -27
- package/dist/host/index.d.ts +11 -27
- package/dist/host/index.js +2 -3
- package/dist/index.cjs +30 -19
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +72 -26
- package/dist/index.d.ts +72 -26
- package/dist/index.js +8 -9
- package/dist/index.js.map +1 -1
- package/dist/react/index.cjs +9 -10
- package/dist/react/index.cjs.map +1 -1
- package/dist/react/index.d.cts +36 -8
- package/dist/react/index.d.ts +36 -8
- package/dist/react/index.js +3 -4
- package/dist/react/index.js.map +1 -1
- package/dist/schema-reader-776246MJ.js +3 -0
- package/dist/{schema-reader-GM4A4L44.js.map → schema-reader-776246MJ.js.map} +1 -1
- package/dist/{schema-reader-MWBRQ2TQ.cjs → schema-reader-B6LTGBMJ.cjs} +2 -3
- package/dist/{schema-reader-MWBRQ2TQ.cjs.map → schema-reader-B6LTGBMJ.cjs.map} +1 -1
- package/dist/{server-LR6T6C44.cjs → server-BR5MNFOB.cjs} +13 -14
- package/dist/server-BR5MNFOB.cjs.map +1 -0
- package/dist/{server-UHPEE55X.js → server-OOEEWAEG.js} +13 -14
- package/dist/server-OOEEWAEG.js.map +1 -0
- package/dist/synapse-runtime.iife.global.js +34 -34
- package/dist/synapse-ui.iife.global.js +4 -4
- package/dist/type-generator-MZ4X4DE5.js +3 -0
- package/dist/{type-generator-ZYSVFK3X.js.map → type-generator-MZ4X4DE5.js.map} +1 -1
- package/dist/{type-generator-YTPFWLVG.cjs → type-generator-UA3L4OIA.cjs} +2 -3
- package/dist/{type-generator-YTPFWLVG.cjs.map → type-generator-UA3L4OIA.cjs.map} +1 -1
- package/dist/{types-CG08aO82.d.cts → types-BxPfGHKO.d.cts} +35 -43
- package/dist/{types-CG08aO82.d.ts → types-BxPfGHKO.d.ts} +35 -43
- package/dist/ui/base.cjs +0 -1
- package/dist/ui/base.cjs.map +1 -1
- package/dist/ui/base.js +0 -1
- package/dist/ui/base.js.map +1 -1
- package/dist/ui/index.cjs +0 -1
- package/dist/ui/index.cjs.map +1 -1
- package/dist/ui/index.js +0 -1
- package/dist/ui/index.js.map +1 -1
- package/dist/vite/index.cjs +10 -10
- package/dist/vite/index.cjs.map +1 -1
- package/dist/vite/index.js +6 -6
- package/dist/vite/index.js.map +1 -1
- package/dist/{writer-HDRCQSX2.cjs → writer-NDK4U6C5.cjs} +3 -3
- package/dist/{writer-HDRCQSX2.cjs.map → writer-NDK4U6C5.cjs.map} +1 -1
- package/dist/{writer-QNDPMEYD.js → writer-ZNBXYUYC.js} +3 -3
- package/dist/{writer-QNDPMEYD.js.map → writer-ZNBXYUYC.js.map} +1 -1
- package/package.json +6 -3
- package/dist/chunk-54W6IAHM.js +0 -24
- package/dist/chunk-54W6IAHM.js.map +0 -1
- package/dist/chunk-DRLVEHCD.js.map +0 -1
- package/dist/chunk-NP7ROSH2.cjs.map +0 -1
- package/dist/chunk-OYLZ5OCK.js.map +0 -1
- package/dist/chunk-P5DBJFSQ.js +0 -8459
- package/dist/chunk-P5DBJFSQ.js.map +0 -1
- package/dist/chunk-PZ5AY32C.js +0 -9
- package/dist/chunk-PZ5AY32C.js.map +0 -1
- package/dist/chunk-Q7SFCCGT.cjs +0 -11
- package/dist/chunk-Q7SFCCGT.cjs.map +0 -1
- package/dist/chunk-QXDCA7QW.cjs +0 -8466
- package/dist/chunk-QXDCA7QW.cjs.map +0 -1
- package/dist/chunk-RU64F5RS.cjs.map +0 -1
- package/dist/chunk-SZWHFTXV.cjs.map +0 -1
- package/dist/schema-reader-GM4A4L44.js +0 -4
- package/dist/server-LR6T6C44.cjs.map +0 -1
- package/dist/server-UHPEE55X.js.map +0 -1
- package/dist/type-generator-ZYSVFK3X.js +0 -4
|
@@ -1,26 +1,23 @@
|
|
|
1
|
-
import { f as FontFaceDescriptor } from './types-CG08aO82.cjs';
|
|
2
|
-
|
|
3
1
|
/**
|
|
4
2
|
* Cross-host UI client — types and wire constants.
|
|
5
3
|
*
|
|
6
4
|
* The cross-host client (`connectUI`) renders one Synapse-authored component in
|
|
7
|
-
*
|
|
8
|
-
*
|
|
9
|
-
* a host protocol. This is a **push-first** surface: the tool output that spawned
|
|
5
|
+
* any MCP Apps host (ChatGPT, Claude, NimbleBrain) and standalone. Apps code
|
|
6
|
+
* against `synapse.*` and never touch the bridge. This is a **push-first** surface: the tool output that spawned
|
|
10
7
|
* the widget is delivered at render (`data()` / `onData()`); `callTool()` is the
|
|
11
8
|
* pull escape hatch, advertised per host via `capabilities()`.
|
|
12
9
|
*
|
|
13
10
|
* This layer intentionally has ZERO dependency on `@modelcontextprotocol/*` — the
|
|
14
|
-
*
|
|
15
|
-
*
|
|
11
|
+
* bridge is JSON-RPC over `postMessage`, spoken by hand, so the IIFE that apps
|
|
12
|
+
* inline stays tiny (no Zod, no ext-apps schemas).
|
|
16
13
|
*/
|
|
17
14
|
/**
|
|
18
|
-
* The
|
|
19
|
-
*
|
|
20
|
-
*
|
|
15
|
+
* The bridge the client resolved to, as reported by `synapse.host()`:
|
|
16
|
+
* `"mcp-apps"` in a frame, `"generic"` standalone. It names the bridge, not the
|
|
17
|
+
* product — every framing host speaks the same one. Apps should rarely branch on
|
|
18
|
+
* it; `capabilities()` is the supported way to feature-detect.
|
|
21
19
|
*/
|
|
22
|
-
|
|
23
|
-
type HostKind = "chatgpt" | "claude" | "nimblebrain" | "generic";
|
|
20
|
+
type HostKind = "mcp-apps" | "generic";
|
|
24
21
|
/** Resolved theme. `mode` always resolves to light or dark. `tokens` are CSS
|
|
25
22
|
* custom properties the host publishes — the MCP Apps adapter reads them from
|
|
26
23
|
* `hostContext.styles.variables`; where a host sends none they stay empty and the
|
|
@@ -28,9 +25,6 @@ type HostKind = "chatgpt" | "claude" | "nimblebrain" | "generic";
|
|
|
28
25
|
interface SynapseUITheme {
|
|
29
26
|
mode: "light" | "dark";
|
|
30
27
|
tokens: Record<string, string>;
|
|
31
|
-
/** Font faces the host wants loaded. Absent where the host sends none, which
|
|
32
|
-
* leaves the SDK's web-safe fallbacks in force. See `FontFaceDescriptor`. */
|
|
33
|
-
fontFaces?: FontFaceDescriptor[];
|
|
34
28
|
}
|
|
35
29
|
/** What the active host actually supports. `data()`/`onData()`/`theme()`/
|
|
36
30
|
* `resize()` work everywhere; these three vary. */
|
|
@@ -46,6 +40,18 @@ interface HostCapabilities {
|
|
|
46
40
|
declare class HostUnsupportedError extends Error {
|
|
47
41
|
constructor(feature: string, host: HostKind);
|
|
48
42
|
}
|
|
43
|
+
/**
|
|
44
|
+
* Thrown by `callTool()` when the tool result says the call failed
|
|
45
|
+
* (`isError: true`). MCP reports a tool failure inside the result rather than as
|
|
46
|
+
* a JSON-RPC error, and a host reports a refusal the same way — ChatGPT answers a
|
|
47
|
+
* call to a tool the app may not see with an `isError` result — so without this a
|
|
48
|
+
* failure would resolve as if it were data. The message is the result's first
|
|
49
|
+
* text block; the whole result is on `result`.
|
|
50
|
+
*/
|
|
51
|
+
declare class ToolCallError extends Error {
|
|
52
|
+
readonly result: unknown;
|
|
53
|
+
constructor(name: string, result: unknown);
|
|
54
|
+
}
|
|
49
55
|
interface ConnectUIOptions {
|
|
50
56
|
/** App name — informational; forwarded to hosts that accept an appInfo. */
|
|
51
57
|
name?: string;
|
|
@@ -54,18 +60,17 @@ interface ConnectUIOptions {
|
|
|
54
60
|
/**
|
|
55
61
|
* Force a host adapter instead of auto-detecting. Used by preview harnesses,
|
|
56
62
|
* SSR, and tests; production apps omit it and let the SDK feature-detect.
|
|
57
|
-
* `"
|
|
58
|
-
* `"generic"` → inline adapter.
|
|
63
|
+
* `"mcp-apps"` → MCP Apps standard adapter, `"generic"` → inline adapter.
|
|
59
64
|
*/
|
|
60
65
|
host?: HostKind;
|
|
61
66
|
/**
|
|
62
67
|
* `id` of the `<script type="application/json">` element carrying pushed data
|
|
63
|
-
* baked into the HTML (the
|
|
68
|
+
* baked into the HTML (the SSR / standalone path). Defaults to
|
|
64
69
|
* {@link SYNAPSE_DATA_ELEMENT_ID}.
|
|
65
70
|
*/
|
|
66
71
|
dataElementId?: string;
|
|
67
72
|
/**
|
|
68
|
-
* Auto-report content height to the host on layout changes (
|
|
73
|
+
* Auto-report content height to the host on layout changes (MCP Apps only).
|
|
69
74
|
* Defaults to `true`. Set `false` to size manually via `resize()`.
|
|
70
75
|
*/
|
|
71
76
|
autoResize?: boolean;
|
|
@@ -92,8 +97,10 @@ interface SynapseUIClient {
|
|
|
92
97
|
/** Subscribe to theme changes. The client already applies the theme to the DOM
|
|
93
98
|
* (`data-theme` attribute + CSS variables) before this fires. */
|
|
94
99
|
onTheme(cb: (theme: SynapseUITheme) => void): () => void;
|
|
95
|
-
/** Widget→server tool call.
|
|
96
|
-
*
|
|
100
|
+
/** Widget→server tool call. Resolves with the tool result. Rejects with
|
|
101
|
+
* {@link ToolCallError} when the result reports failure (`isError: true`), and
|
|
102
|
+
* with {@link HostUnsupportedError} where the host advertises no pull
|
|
103
|
+
* (`capabilities().pull === false`). */
|
|
97
104
|
callTool<O = unknown>(name: string, args?: Record<string, unknown>): Promise<O>;
|
|
98
105
|
/** Send a follow-up message to the agent conversation. No-op where unsupported. */
|
|
99
106
|
sendPrompt(text: string): void;
|
|
@@ -132,9 +139,9 @@ interface HostAdapter {
|
|
|
132
139
|
declare const SYNAPSE_DATA_ELEMENT_ID = "synapse-ui-data";
|
|
133
140
|
|
|
134
141
|
/**
|
|
135
|
-
* Connect a Synapse-authored component to whatever host it renders in —
|
|
136
|
-
*
|
|
137
|
-
*
|
|
142
|
+
* Connect a Synapse-authored component to whatever host it renders in — any MCP
|
|
143
|
+
* Apps host, or a plain/standalone page — behind one push-first API. Detects
|
|
144
|
+
* whether it is framed, selects an adapter, and applies the
|
|
138
145
|
* host theme to the DOM before returning.
|
|
139
146
|
*
|
|
140
147
|
* Synchronous: `data()` is populated from baked-in data (where present) on
|
|
@@ -153,20 +160,19 @@ declare function connectUI(options?: ConnectUIOptions): SynapseUIClient;
|
|
|
153
160
|
* unit-testable with a plain object — no full `Window` fake required.
|
|
154
161
|
*/
|
|
155
162
|
interface DetectableWindow {
|
|
156
|
-
openai?: unknown;
|
|
157
163
|
parent?: unknown;
|
|
158
|
-
self?: unknown;
|
|
159
164
|
}
|
|
160
165
|
/**
|
|
161
|
-
*
|
|
166
|
+
* Detect the bridge from the browsing context.
|
|
162
167
|
*
|
|
163
|
-
* -
|
|
164
|
-
*
|
|
165
|
-
*
|
|
168
|
+
* - a nested browsing context (`parent !== self`, or a cross-origin access that
|
|
169
|
+
* throws) → **mcp-apps**: every host that frames a component speaks the MCP
|
|
170
|
+
* Apps standard.
|
|
166
171
|
* - top-level document → **generic** (inline / standalone).
|
|
167
172
|
*
|
|
168
|
-
*
|
|
169
|
-
*
|
|
173
|
+
* Nothing on the window names the host. `window.openai` in particular does not:
|
|
174
|
+
* ChatGPT injects it into every frame it serves, whatever the component is.
|
|
175
|
+
* Which host answered is in the handshake, not here.
|
|
170
176
|
*/
|
|
171
177
|
declare function detectHostKind(win: DetectableWindow): HostKind;
|
|
172
178
|
/** Build the adapter for an explicit host kind (`options.host` or a detected one). */
|
|
@@ -174,4 +180,4 @@ declare function adapterForKind(kind: HostKind, win: Window & typeof globalThis,
|
|
|
174
180
|
/** Select and construct the host adapter, honoring `options.host` when set. */
|
|
175
181
|
declare function selectAdapter(win: Window & typeof globalThis, options: ConnectUIOptions): HostAdapter;
|
|
176
182
|
|
|
177
|
-
export { type ConnectUIOptions as C, type HostAdapter as H, type SynapseUITheme as S, type HostCapabilities as a, type HostKind as b, HostUnsupportedError as c, SYNAPSE_DATA_ELEMENT_ID as d, type SynapseUIClient as e, adapterForKind as f, connectUI as g, detectHostKind as h, selectAdapter as s };
|
|
183
|
+
export { type ConnectUIOptions as C, type HostAdapter as H, type SynapseUITheme as S, ToolCallError as T, type HostCapabilities as a, type HostKind as b, HostUnsupportedError as c, SYNAPSE_DATA_ELEMENT_ID as d, type SynapseUIClient as e, adapterForKind as f, connectUI as g, detectHostKind as h, selectAdapter as s };
|
|
@@ -1,26 +1,23 @@
|
|
|
1
|
-
import { f as FontFaceDescriptor } from './types-CG08aO82.js';
|
|
2
|
-
|
|
3
1
|
/**
|
|
4
2
|
* Cross-host UI client — types and wire constants.
|
|
5
3
|
*
|
|
6
4
|
* The cross-host client (`connectUI`) renders one Synapse-authored component in
|
|
7
|
-
*
|
|
8
|
-
*
|
|
9
|
-
* a host protocol. This is a **push-first** surface: the tool output that spawned
|
|
5
|
+
* any MCP Apps host (ChatGPT, Claude, NimbleBrain) and standalone. Apps code
|
|
6
|
+
* against `synapse.*` and never touch the bridge. This is a **push-first** surface: the tool output that spawned
|
|
10
7
|
* the widget is delivered at render (`data()` / `onData()`); `callTool()` is the
|
|
11
8
|
* pull escape hatch, advertised per host via `capabilities()`.
|
|
12
9
|
*
|
|
13
10
|
* This layer intentionally has ZERO dependency on `@modelcontextprotocol/*` — the
|
|
14
|
-
*
|
|
15
|
-
*
|
|
11
|
+
* bridge is JSON-RPC over `postMessage`, spoken by hand, so the IIFE that apps
|
|
12
|
+
* inline stays tiny (no Zod, no ext-apps schemas).
|
|
16
13
|
*/
|
|
17
14
|
/**
|
|
18
|
-
* The
|
|
19
|
-
*
|
|
20
|
-
*
|
|
15
|
+
* The bridge the client resolved to, as reported by `synapse.host()`:
|
|
16
|
+
* `"mcp-apps"` in a frame, `"generic"` standalone. It names the bridge, not the
|
|
17
|
+
* product — every framing host speaks the same one. Apps should rarely branch on
|
|
18
|
+
* it; `capabilities()` is the supported way to feature-detect.
|
|
21
19
|
*/
|
|
22
|
-
|
|
23
|
-
type HostKind = "chatgpt" | "claude" | "nimblebrain" | "generic";
|
|
20
|
+
type HostKind = "mcp-apps" | "generic";
|
|
24
21
|
/** Resolved theme. `mode` always resolves to light or dark. `tokens` are CSS
|
|
25
22
|
* custom properties the host publishes — the MCP Apps adapter reads them from
|
|
26
23
|
* `hostContext.styles.variables`; where a host sends none they stay empty and the
|
|
@@ -28,9 +25,6 @@ type HostKind = "chatgpt" | "claude" | "nimblebrain" | "generic";
|
|
|
28
25
|
interface SynapseUITheme {
|
|
29
26
|
mode: "light" | "dark";
|
|
30
27
|
tokens: Record<string, string>;
|
|
31
|
-
/** Font faces the host wants loaded. Absent where the host sends none, which
|
|
32
|
-
* leaves the SDK's web-safe fallbacks in force. See `FontFaceDescriptor`. */
|
|
33
|
-
fontFaces?: FontFaceDescriptor[];
|
|
34
28
|
}
|
|
35
29
|
/** What the active host actually supports. `data()`/`onData()`/`theme()`/
|
|
36
30
|
* `resize()` work everywhere; these three vary. */
|
|
@@ -46,6 +40,18 @@ interface HostCapabilities {
|
|
|
46
40
|
declare class HostUnsupportedError extends Error {
|
|
47
41
|
constructor(feature: string, host: HostKind);
|
|
48
42
|
}
|
|
43
|
+
/**
|
|
44
|
+
* Thrown by `callTool()` when the tool result says the call failed
|
|
45
|
+
* (`isError: true`). MCP reports a tool failure inside the result rather than as
|
|
46
|
+
* a JSON-RPC error, and a host reports a refusal the same way — ChatGPT answers a
|
|
47
|
+
* call to a tool the app may not see with an `isError` result — so without this a
|
|
48
|
+
* failure would resolve as if it were data. The message is the result's first
|
|
49
|
+
* text block; the whole result is on `result`.
|
|
50
|
+
*/
|
|
51
|
+
declare class ToolCallError extends Error {
|
|
52
|
+
readonly result: unknown;
|
|
53
|
+
constructor(name: string, result: unknown);
|
|
54
|
+
}
|
|
49
55
|
interface ConnectUIOptions {
|
|
50
56
|
/** App name — informational; forwarded to hosts that accept an appInfo. */
|
|
51
57
|
name?: string;
|
|
@@ -54,18 +60,17 @@ interface ConnectUIOptions {
|
|
|
54
60
|
/**
|
|
55
61
|
* Force a host adapter instead of auto-detecting. Used by preview harnesses,
|
|
56
62
|
* SSR, and tests; production apps omit it and let the SDK feature-detect.
|
|
57
|
-
* `"
|
|
58
|
-
* `"generic"` → inline adapter.
|
|
63
|
+
* `"mcp-apps"` → MCP Apps standard adapter, `"generic"` → inline adapter.
|
|
59
64
|
*/
|
|
60
65
|
host?: HostKind;
|
|
61
66
|
/**
|
|
62
67
|
* `id` of the `<script type="application/json">` element carrying pushed data
|
|
63
|
-
* baked into the HTML (the
|
|
68
|
+
* baked into the HTML (the SSR / standalone path). Defaults to
|
|
64
69
|
* {@link SYNAPSE_DATA_ELEMENT_ID}.
|
|
65
70
|
*/
|
|
66
71
|
dataElementId?: string;
|
|
67
72
|
/**
|
|
68
|
-
* Auto-report content height to the host on layout changes (
|
|
73
|
+
* Auto-report content height to the host on layout changes (MCP Apps only).
|
|
69
74
|
* Defaults to `true`. Set `false` to size manually via `resize()`.
|
|
70
75
|
*/
|
|
71
76
|
autoResize?: boolean;
|
|
@@ -92,8 +97,10 @@ interface SynapseUIClient {
|
|
|
92
97
|
/** Subscribe to theme changes. The client already applies the theme to the DOM
|
|
93
98
|
* (`data-theme` attribute + CSS variables) before this fires. */
|
|
94
99
|
onTheme(cb: (theme: SynapseUITheme) => void): () => void;
|
|
95
|
-
/** Widget→server tool call.
|
|
96
|
-
*
|
|
100
|
+
/** Widget→server tool call. Resolves with the tool result. Rejects with
|
|
101
|
+
* {@link ToolCallError} when the result reports failure (`isError: true`), and
|
|
102
|
+
* with {@link HostUnsupportedError} where the host advertises no pull
|
|
103
|
+
* (`capabilities().pull === false`). */
|
|
97
104
|
callTool<O = unknown>(name: string, args?: Record<string, unknown>): Promise<O>;
|
|
98
105
|
/** Send a follow-up message to the agent conversation. No-op where unsupported. */
|
|
99
106
|
sendPrompt(text: string): void;
|
|
@@ -132,9 +139,9 @@ interface HostAdapter {
|
|
|
132
139
|
declare const SYNAPSE_DATA_ELEMENT_ID = "synapse-ui-data";
|
|
133
140
|
|
|
134
141
|
/**
|
|
135
|
-
* Connect a Synapse-authored component to whatever host it renders in —
|
|
136
|
-
*
|
|
137
|
-
*
|
|
142
|
+
* Connect a Synapse-authored component to whatever host it renders in — any MCP
|
|
143
|
+
* Apps host, or a plain/standalone page — behind one push-first API. Detects
|
|
144
|
+
* whether it is framed, selects an adapter, and applies the
|
|
138
145
|
* host theme to the DOM before returning.
|
|
139
146
|
*
|
|
140
147
|
* Synchronous: `data()` is populated from baked-in data (where present) on
|
|
@@ -153,20 +160,19 @@ declare function connectUI(options?: ConnectUIOptions): SynapseUIClient;
|
|
|
153
160
|
* unit-testable with a plain object — no full `Window` fake required.
|
|
154
161
|
*/
|
|
155
162
|
interface DetectableWindow {
|
|
156
|
-
openai?: unknown;
|
|
157
163
|
parent?: unknown;
|
|
158
|
-
self?: unknown;
|
|
159
164
|
}
|
|
160
165
|
/**
|
|
161
|
-
*
|
|
166
|
+
* Detect the bridge from the browsing context.
|
|
162
167
|
*
|
|
163
|
-
* -
|
|
164
|
-
*
|
|
165
|
-
*
|
|
168
|
+
* - a nested browsing context (`parent !== self`, or a cross-origin access that
|
|
169
|
+
* throws) → **mcp-apps**: every host that frames a component speaks the MCP
|
|
170
|
+
* Apps standard.
|
|
166
171
|
* - top-level document → **generic** (inline / standalone).
|
|
167
172
|
*
|
|
168
|
-
*
|
|
169
|
-
*
|
|
173
|
+
* Nothing on the window names the host. `window.openai` in particular does not:
|
|
174
|
+
* ChatGPT injects it into every frame it serves, whatever the component is.
|
|
175
|
+
* Which host answered is in the handshake, not here.
|
|
170
176
|
*/
|
|
171
177
|
declare function detectHostKind(win: DetectableWindow): HostKind;
|
|
172
178
|
/** Build the adapter for an explicit host kind (`options.host` or a detected one). */
|
|
@@ -174,4 +180,4 @@ declare function adapterForKind(kind: HostKind, win: Window & typeof globalThis,
|
|
|
174
180
|
/** Select and construct the host adapter, honoring `options.host` when set. */
|
|
175
181
|
declare function selectAdapter(win: Window & typeof globalThis, options: ConnectUIOptions): HostAdapter;
|
|
176
182
|
|
|
177
|
-
export { type ConnectUIOptions as C, type HostAdapter as H, type SynapseUITheme as S, type HostCapabilities as a, type HostKind as b, HostUnsupportedError as c, SYNAPSE_DATA_ELEMENT_ID as d, type SynapseUIClient as e, adapterForKind as f, connectUI as g, detectHostKind as h, selectAdapter as s };
|
|
183
|
+
export { type ConnectUIOptions as C, type HostAdapter as H, type SynapseUITheme as S, ToolCallError as T, type HostCapabilities as a, type HostKind as b, HostUnsupportedError as c, SYNAPSE_DATA_ELEMENT_ID as d, type SynapseUIClient as e, adapterForKind as f, connectUI as g, detectHostKind as h, selectAdapter as s };
|
package/dist/host/index.cjs
CHANGED
|
@@ -1,58 +1,57 @@
|
|
|
1
1
|
'use strict';
|
|
2
2
|
|
|
3
|
-
var
|
|
4
|
-
require('../chunk-
|
|
5
|
-
require('../chunk-Q7SFCCGT.cjs');
|
|
3
|
+
var chunkBNF352SA_cjs = require('../chunk-BNF352SA.cjs');
|
|
4
|
+
require('../chunk-YSL7KJNU.cjs');
|
|
6
5
|
|
|
7
6
|
|
|
8
7
|
|
|
9
8
|
Object.defineProperty(exports, "HostUnsupportedError", {
|
|
10
9
|
enumerable: true,
|
|
11
|
-
get: function () { return
|
|
10
|
+
get: function () { return chunkBNF352SA_cjs.HostUnsupportedError; }
|
|
12
11
|
});
|
|
13
12
|
Object.defineProperty(exports, "SYNAPSE_DATA_ELEMENT_ID", {
|
|
14
13
|
enumerable: true,
|
|
15
|
-
get: function () { return
|
|
14
|
+
get: function () { return chunkBNF352SA_cjs.SYNAPSE_DATA_ELEMENT_ID; }
|
|
15
|
+
});
|
|
16
|
+
Object.defineProperty(exports, "ToolCallError", {
|
|
17
|
+
enumerable: true,
|
|
18
|
+
get: function () { return chunkBNF352SA_cjs.ToolCallError; }
|
|
16
19
|
});
|
|
17
20
|
Object.defineProperty(exports, "adapterForKind", {
|
|
18
21
|
enumerable: true,
|
|
19
|
-
get: function () { return
|
|
22
|
+
get: function () { return chunkBNF352SA_cjs.adapterForKind; }
|
|
20
23
|
});
|
|
21
24
|
Object.defineProperty(exports, "applyHostTheme", {
|
|
22
25
|
enumerable: true,
|
|
23
|
-
get: function () { return
|
|
26
|
+
get: function () { return chunkBNF352SA_cjs.applyHostTheme; }
|
|
24
27
|
});
|
|
25
28
|
Object.defineProperty(exports, "coerceMode", {
|
|
26
29
|
enumerable: true,
|
|
27
|
-
get: function () { return
|
|
30
|
+
get: function () { return chunkBNF352SA_cjs.coerceMode; }
|
|
28
31
|
});
|
|
29
32
|
Object.defineProperty(exports, "connectUI", {
|
|
30
33
|
enumerable: true,
|
|
31
|
-
get: function () { return
|
|
32
|
-
});
|
|
33
|
-
Object.defineProperty(exports, "createChatGPTAdapter", {
|
|
34
|
-
enumerable: true,
|
|
35
|
-
get: function () { return chunkRU64F5RS_cjs.createChatGPTAdapter; }
|
|
34
|
+
get: function () { return chunkBNF352SA_cjs.connectUI; }
|
|
36
35
|
});
|
|
37
36
|
Object.defineProperty(exports, "createInlineAdapter", {
|
|
38
37
|
enumerable: true,
|
|
39
|
-
get: function () { return
|
|
38
|
+
get: function () { return chunkBNF352SA_cjs.createInlineAdapter; }
|
|
40
39
|
});
|
|
41
40
|
Object.defineProperty(exports, "createMcpAppsAdapter", {
|
|
42
41
|
enumerable: true,
|
|
43
|
-
get: function () { return
|
|
42
|
+
get: function () { return chunkBNF352SA_cjs.createMcpAppsAdapter; }
|
|
44
43
|
});
|
|
45
44
|
Object.defineProperty(exports, "detectHostKind", {
|
|
46
45
|
enumerable: true,
|
|
47
|
-
get: function () { return
|
|
46
|
+
get: function () { return chunkBNF352SA_cjs.detectHostKind; }
|
|
48
47
|
});
|
|
49
48
|
Object.defineProperty(exports, "preferredMode", {
|
|
50
49
|
enumerable: true,
|
|
51
|
-
get: function () { return
|
|
50
|
+
get: function () { return chunkBNF352SA_cjs.preferredMode; }
|
|
52
51
|
});
|
|
53
52
|
Object.defineProperty(exports, "selectAdapter", {
|
|
54
53
|
enumerable: true,
|
|
55
|
-
get: function () { return
|
|
54
|
+
get: function () { return chunkBNF352SA_cjs.selectAdapter; }
|
|
56
55
|
});
|
|
57
56
|
//# sourceMappingURL=index.cjs.map
|
|
58
57
|
//# sourceMappingURL=index.cjs.map
|
package/dist/host/index.d.cts
CHANGED
|
@@ -1,18 +1,5 @@
|
|
|
1
|
-
import { C as ConnectUIOptions, H as HostAdapter, S as SynapseUITheme } from '../detect-
|
|
2
|
-
export { a as HostCapabilities, b as HostKind, c as HostUnsupportedError, d as SYNAPSE_DATA_ELEMENT_ID, e as SynapseUIClient, f as adapterForKind, g as connectUI, h as detectHostKind, s as selectAdapter } from '../detect-
|
|
3
|
-
import '../types-CG08aO82.cjs';
|
|
4
|
-
import '@modelcontextprotocol/ext-apps';
|
|
5
|
-
import '@modelcontextprotocol/sdk/types.js';
|
|
6
|
-
|
|
7
|
-
/**
|
|
8
|
-
* ChatGPT (OpenAI Apps SDK) adapter.
|
|
9
|
-
*
|
|
10
|
-
* Data arrives on `window.openai.toolOutput` (available synchronously before the
|
|
11
|
-
* widget script runs) and updates via the `openai:set_globals` event. Theme is a
|
|
12
|
-
* mode string on the same surface. The host auto-sizes the iframe, so `resize()`
|
|
13
|
-
* is a no-op. `callTool` is available when the host exposes `window.openai.callTool`.
|
|
14
|
-
*/
|
|
15
|
-
declare function createChatGPTAdapter(win: Window & typeof globalThis, _options: ConnectUIOptions): HostAdapter;
|
|
1
|
+
import { C as ConnectUIOptions, H as HostAdapter, S as SynapseUITheme } from '../detect-DVGaL2bH.cjs';
|
|
2
|
+
export { a as HostCapabilities, b as HostKind, c as HostUnsupportedError, d as SYNAPSE_DATA_ELEMENT_ID, e as SynapseUIClient, T as ToolCallError, f as adapterForKind, g as connectUI, h as detectHostKind, s as selectAdapter } from '../detect-DVGaL2bH.cjs';
|
|
16
3
|
|
|
17
4
|
/**
|
|
18
5
|
* Inline / standalone fallback adapter.
|
|
@@ -26,8 +13,8 @@ declare function createChatGPTAdapter(win: Window & typeof globalThis, _options:
|
|
|
26
13
|
declare function createInlineAdapter(win: Window & typeof globalThis, options: ConnectUIOptions): HostAdapter;
|
|
27
14
|
|
|
28
15
|
/**
|
|
29
|
-
* MCP Apps standard (SEP-1865) adapter — the
|
|
30
|
-
*
|
|
16
|
+
* MCP Apps standard (SEP-1865) adapter — the bridge for every framed host.
|
|
17
|
+
* ChatGPT, Claude and NimbleBrain all implement the standard, so there is one.
|
|
31
18
|
*
|
|
32
19
|
* The View iframe is an MCP client speaking JSON-RPC 2.0 to `window.parent`:
|
|
33
20
|
*
|
|
@@ -39,9 +26,7 @@ declare function createInlineAdapter(win: Window & typeof globalThis, options: C
|
|
|
39
26
|
* `ui/notifications/host-context-changed`.
|
|
40
27
|
*
|
|
41
28
|
* Actions go up as requests: `ui/open-link`, `ui/message` (follow-up), and
|
|
42
|
-
* `tools/call` (pull).
|
|
43
|
-
* accepted alongside so a pre-standard host still renders — a standard host drops
|
|
44
|
-
* the non-JSON-RPC frames, and a legacy host ignores the JSON-RPC ones.
|
|
29
|
+
* `tools/call` (pull).
|
|
45
30
|
*/
|
|
46
31
|
declare function createMcpAppsAdapter(win: Window & typeof globalThis, options: ConnectUIOptions): HostAdapter;
|
|
47
32
|
|
|
@@ -57,19 +42,18 @@ declare function createMcpAppsAdapter(win: Window & typeof globalThis, options:
|
|
|
57
42
|
* `@nimblebrain/synapse/ui` token components consume theme, backed by the
|
|
58
43
|
* SDK's neutral defaults so every referenced var resolves in both modes.
|
|
59
44
|
*
|
|
60
|
-
* Setting both means an app can use either convention (
|
|
61
|
-
* only a mode string
|
|
45
|
+
* Setting both means an app can use either convention (and a host that supplies
|
|
46
|
+
* only a mode string still themes correctly). SSR-safe.
|
|
62
47
|
*
|
|
63
|
-
*
|
|
64
|
-
*
|
|
65
|
-
* leaves the web-safe fallbacks in force.
|
|
48
|
+
* Fonts travel separately, as the host's `@font-face` CSS: see
|
|
49
|
+
* {@link injectHostFonts}.
|
|
66
50
|
*/
|
|
67
51
|
declare function applyHostTheme(theme: SynapseUITheme): void;
|
|
68
52
|
/** Read the OS-level color scheme as a sane default for hosts that don't push a
|
|
69
|
-
* theme until
|
|
53
|
+
* theme until the handshake completes, or ever (standalone). */
|
|
70
54
|
declare function preferredMode(win: Window | undefined): "light" | "dark";
|
|
71
55
|
/** Coerce an arbitrary host-supplied theme signal to a mode. Accepts the string
|
|
72
56
|
* form (`"dark"`) both hosts use; anything else falls back. */
|
|
73
57
|
declare function coerceMode(value: unknown, fallback: "light" | "dark"): "light" | "dark";
|
|
74
58
|
|
|
75
|
-
export { ConnectUIOptions, HostAdapter, SynapseUITheme, applyHostTheme, coerceMode,
|
|
59
|
+
export { ConnectUIOptions, HostAdapter, SynapseUITheme, applyHostTheme, coerceMode, createInlineAdapter, createMcpAppsAdapter, preferredMode };
|
package/dist/host/index.d.ts
CHANGED
|
@@ -1,18 +1,5 @@
|
|
|
1
|
-
import { C as ConnectUIOptions, H as HostAdapter, S as SynapseUITheme } from '../detect-
|
|
2
|
-
export { a as HostCapabilities, b as HostKind, c as HostUnsupportedError, d as SYNAPSE_DATA_ELEMENT_ID, e as SynapseUIClient, f as adapterForKind, g as connectUI, h as detectHostKind, s as selectAdapter } from '../detect-
|
|
3
|
-
import '../types-CG08aO82.js';
|
|
4
|
-
import '@modelcontextprotocol/ext-apps';
|
|
5
|
-
import '@modelcontextprotocol/sdk/types.js';
|
|
6
|
-
|
|
7
|
-
/**
|
|
8
|
-
* ChatGPT (OpenAI Apps SDK) adapter.
|
|
9
|
-
*
|
|
10
|
-
* Data arrives on `window.openai.toolOutput` (available synchronously before the
|
|
11
|
-
* widget script runs) and updates via the `openai:set_globals` event. Theme is a
|
|
12
|
-
* mode string on the same surface. The host auto-sizes the iframe, so `resize()`
|
|
13
|
-
* is a no-op. `callTool` is available when the host exposes `window.openai.callTool`.
|
|
14
|
-
*/
|
|
15
|
-
declare function createChatGPTAdapter(win: Window & typeof globalThis, _options: ConnectUIOptions): HostAdapter;
|
|
1
|
+
import { C as ConnectUIOptions, H as HostAdapter, S as SynapseUITheme } from '../detect-DVGaL2bH.js';
|
|
2
|
+
export { a as HostCapabilities, b as HostKind, c as HostUnsupportedError, d as SYNAPSE_DATA_ELEMENT_ID, e as SynapseUIClient, T as ToolCallError, f as adapterForKind, g as connectUI, h as detectHostKind, s as selectAdapter } from '../detect-DVGaL2bH.js';
|
|
16
3
|
|
|
17
4
|
/**
|
|
18
5
|
* Inline / standalone fallback adapter.
|
|
@@ -26,8 +13,8 @@ declare function createChatGPTAdapter(win: Window & typeof globalThis, _options:
|
|
|
26
13
|
declare function createInlineAdapter(win: Window & typeof globalThis, options: ConnectUIOptions): HostAdapter;
|
|
27
14
|
|
|
28
15
|
/**
|
|
29
|
-
* MCP Apps standard (SEP-1865) adapter — the
|
|
30
|
-
*
|
|
16
|
+
* MCP Apps standard (SEP-1865) adapter — the bridge for every framed host.
|
|
17
|
+
* ChatGPT, Claude and NimbleBrain all implement the standard, so there is one.
|
|
31
18
|
*
|
|
32
19
|
* The View iframe is an MCP client speaking JSON-RPC 2.0 to `window.parent`:
|
|
33
20
|
*
|
|
@@ -39,9 +26,7 @@ declare function createInlineAdapter(win: Window & typeof globalThis, options: C
|
|
|
39
26
|
* `ui/notifications/host-context-changed`.
|
|
40
27
|
*
|
|
41
28
|
* Actions go up as requests: `ui/open-link`, `ui/message` (follow-up), and
|
|
42
|
-
* `tools/call` (pull).
|
|
43
|
-
* accepted alongside so a pre-standard host still renders — a standard host drops
|
|
44
|
-
* the non-JSON-RPC frames, and a legacy host ignores the JSON-RPC ones.
|
|
29
|
+
* `tools/call` (pull).
|
|
45
30
|
*/
|
|
46
31
|
declare function createMcpAppsAdapter(win: Window & typeof globalThis, options: ConnectUIOptions): HostAdapter;
|
|
47
32
|
|
|
@@ -57,19 +42,18 @@ declare function createMcpAppsAdapter(win: Window & typeof globalThis, options:
|
|
|
57
42
|
* `@nimblebrain/synapse/ui` token components consume theme, backed by the
|
|
58
43
|
* SDK's neutral defaults so every referenced var resolves in both modes.
|
|
59
44
|
*
|
|
60
|
-
* Setting both means an app can use either convention (
|
|
61
|
-
* only a mode string
|
|
45
|
+
* Setting both means an app can use either convention (and a host that supplies
|
|
46
|
+
* only a mode string still themes correctly). SSR-safe.
|
|
62
47
|
*
|
|
63
|
-
*
|
|
64
|
-
*
|
|
65
|
-
* leaves the web-safe fallbacks in force.
|
|
48
|
+
* Fonts travel separately, as the host's `@font-face` CSS: see
|
|
49
|
+
* {@link injectHostFonts}.
|
|
66
50
|
*/
|
|
67
51
|
declare function applyHostTheme(theme: SynapseUITheme): void;
|
|
68
52
|
/** Read the OS-level color scheme as a sane default for hosts that don't push a
|
|
69
|
-
* theme until
|
|
53
|
+
* theme until the handshake completes, or ever (standalone). */
|
|
70
54
|
declare function preferredMode(win: Window | undefined): "light" | "dark";
|
|
71
55
|
/** Coerce an arbitrary host-supplied theme signal to a mode. Accepts the string
|
|
72
56
|
* form (`"dark"`) both hosts use; anything else falls back. */
|
|
73
57
|
declare function coerceMode(value: unknown, fallback: "light" | "dark"): "light" | "dark";
|
|
74
58
|
|
|
75
|
-
export { ConnectUIOptions, HostAdapter, SynapseUITheme, applyHostTheme, coerceMode,
|
|
59
|
+
export { ConnectUIOptions, HostAdapter, SynapseUITheme, applyHostTheme, coerceMode, createInlineAdapter, createMcpAppsAdapter, preferredMode };
|
package/dist/host/index.js
CHANGED
|
@@ -1,5 +1,4 @@
|
|
|
1
|
-
export { HostUnsupportedError, SYNAPSE_DATA_ELEMENT_ID, adapterForKind, applyHostTheme, coerceMode, connectUI,
|
|
2
|
-
import '../chunk-
|
|
3
|
-
import '../chunk-PZ5AY32C.js';
|
|
1
|
+
export { HostUnsupportedError, SYNAPSE_DATA_ELEMENT_ID, ToolCallError, adapterForKind, applyHostTheme, coerceMode, connectUI, createInlineAdapter, createMcpAppsAdapter, detectHostKind, preferredMode, selectAdapter } from '../chunk-UKP4W6DI.js';
|
|
2
|
+
import '../chunk-DJS2FKBN.js';
|
|
4
3
|
//# sourceMappingURL=index.js.map
|
|
5
4
|
//# sourceMappingURL=index.js.map
|
package/dist/index.cjs
CHANGED
|
@@ -1,18 +1,17 @@
|
|
|
1
1
|
'use strict';
|
|
2
2
|
|
|
3
|
-
var
|
|
4
|
-
var
|
|
5
|
-
|
|
6
|
-
require('./chunk-
|
|
7
|
-
require('./chunk-Q7SFCCGT.cjs');
|
|
3
|
+
var chunkBNF352SA_cjs = require('./chunk-BNF352SA.cjs');
|
|
4
|
+
var chunkHQLSVUOR_cjs = require('./chunk-HQLSVUOR.cjs');
|
|
5
|
+
require('./chunk-YSL7KJNU.cjs');
|
|
6
|
+
var chunkISV6HFQE_cjs = require('./chunk-ISV6HFQE.cjs');
|
|
8
7
|
var extApps = require('@modelcontextprotocol/ext-apps');
|
|
9
8
|
|
|
10
9
|
var BASE64_CHUNK = 32768;
|
|
11
10
|
async function downloadFile(app, filename, content, mimeType) {
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
throw new Error("downloadFile is not supported in this host");
|
|
11
|
+
if (!app.hostCapabilities.downloadFile) {
|
|
12
|
+
throw new chunkHQLSVUOR_cjs.HostCapabilityError("downloadFile", "downloadFile");
|
|
15
13
|
}
|
|
14
|
+
const internals = chunkHQLSVUOR_cjs.internalsFor(app);
|
|
16
15
|
const resolvedMime = mimeType || (content instanceof Blob ? content.type : "") || "application/octet-stream";
|
|
17
16
|
const uri = `file:///${filename}`;
|
|
18
17
|
const resource = typeof content === "string" ? { uri, mimeType: resolvedMime, text: content } : { uri, mimeType: resolvedMime, blob: await toBase64(content) };
|
|
@@ -35,43 +34,55 @@ async function toBase64(blob) {
|
|
|
35
34
|
|
|
36
35
|
Object.defineProperty(exports, "HostUnsupportedError", {
|
|
37
36
|
enumerable: true,
|
|
38
|
-
get: function () { return
|
|
37
|
+
get: function () { return chunkBNF352SA_cjs.HostUnsupportedError; }
|
|
39
38
|
});
|
|
40
39
|
Object.defineProperty(exports, "SYNAPSE_DATA_ELEMENT_ID", {
|
|
41
40
|
enumerable: true,
|
|
42
|
-
get: function () { return
|
|
41
|
+
get: function () { return chunkBNF352SA_cjs.SYNAPSE_DATA_ELEMENT_ID; }
|
|
42
|
+
});
|
|
43
|
+
Object.defineProperty(exports, "ToolCallError", {
|
|
44
|
+
enumerable: true,
|
|
45
|
+
get: function () { return chunkBNF352SA_cjs.ToolCallError; }
|
|
43
46
|
});
|
|
44
47
|
Object.defineProperty(exports, "connectUI", {
|
|
45
48
|
enumerable: true,
|
|
46
|
-
get: function () { return
|
|
49
|
+
get: function () { return chunkBNF352SA_cjs.connectUI; }
|
|
47
50
|
});
|
|
48
51
|
Object.defineProperty(exports, "detectHostKind", {
|
|
49
52
|
enumerable: true,
|
|
50
|
-
get: function () { return
|
|
53
|
+
get: function () { return chunkBNF352SA_cjs.detectHostKind; }
|
|
54
|
+
});
|
|
55
|
+
Object.defineProperty(exports, "HostCapabilityError", {
|
|
56
|
+
enumerable: true,
|
|
57
|
+
get: function () { return chunkHQLSVUOR_cjs.HostCapabilityError; }
|
|
51
58
|
});
|
|
52
59
|
Object.defineProperty(exports, "action", {
|
|
53
60
|
enumerable: true,
|
|
54
|
-
get: function () { return
|
|
61
|
+
get: function () { return chunkHQLSVUOR_cjs.action; }
|
|
55
62
|
});
|
|
56
63
|
Object.defineProperty(exports, "callToolAsTask", {
|
|
57
64
|
enumerable: true,
|
|
58
|
-
get: function () { return
|
|
65
|
+
get: function () { return chunkHQLSVUOR_cjs.callToolAsTask; }
|
|
59
66
|
});
|
|
60
67
|
Object.defineProperty(exports, "connect", {
|
|
61
68
|
enumerable: true,
|
|
62
|
-
get: function () { return
|
|
69
|
+
get: function () { return chunkHQLSVUOR_cjs.connect; }
|
|
70
|
+
});
|
|
71
|
+
Object.defineProperty(exports, "hostSupports", {
|
|
72
|
+
enumerable: true,
|
|
73
|
+
get: function () { return chunkHQLSVUOR_cjs.hostSupports; }
|
|
63
74
|
});
|
|
64
75
|
Object.defineProperty(exports, "pickFile", {
|
|
65
76
|
enumerable: true,
|
|
66
|
-
get: function () { return
|
|
77
|
+
get: function () { return chunkHQLSVUOR_cjs.pickFile; }
|
|
67
78
|
});
|
|
68
79
|
Object.defineProperty(exports, "pickFiles", {
|
|
69
80
|
enumerable: true,
|
|
70
|
-
get: function () { return
|
|
81
|
+
get: function () { return chunkHQLSVUOR_cjs.pickFiles; }
|
|
71
82
|
});
|
|
72
|
-
Object.defineProperty(exports, "
|
|
83
|
+
Object.defineProperty(exports, "NIMBLEBRAIN_EXTENSIONS", {
|
|
73
84
|
enumerable: true,
|
|
74
|
-
get: function () { return
|
|
85
|
+
get: function () { return chunkISV6HFQE_cjs.NIMBLEBRAIN_EXTENSIONS; }
|
|
75
86
|
});
|
|
76
87
|
exports.downloadFile = downloadFile;
|
|
77
88
|
//# sourceMappingURL=index.cjs.map
|
package/dist/index.cjs.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/download-file.ts"],"names":["internalsFor","DOWNLOAD_FILE_METHOD"],"mappings":"
|
|
1
|
+
{"version":3,"sources":["../src/download-file.ts"],"names":["HostCapabilityError","internalsFor","DOWNLOAD_FILE_METHOD"],"mappings":";;;;;;;;AAsBA,IAAM,YAAA,GAAe,KAAA;AAqBrB,eAAsB,YAAA,CACpB,GAAA,EACA,QAAA,EACA,OAAA,EACA,QAAA,EACkC;AAClC,EAAA,IAAI,CAAC,GAAA,CAAI,gBAAA,CAAiB,YAAA,EAAc;AACtC,IAAA,MAAM,IAAIA,qCAAA,CAAoB,cAAA,EAAgB,cAAc,CAAA;AAAA,EAC9D;AACA,EAAA,MAAM,SAAA,GAAYC,+BAAa,GAAG,CAAA;AAClC,EAAA,MAAM,eACJ,QAAA,KAAa,OAAA,YAAmB,IAAA,GAAO,OAAA,CAAQ,OAAO,EAAA,CAAA,IAAO,0BAAA;AAC/D,EAAA,MAAM,GAAA,GAAM,WAAW,QAAQ,CAAA,CAAA;AAC/B,EAAA,MAAM,WACJ,OAAO,OAAA,KAAY,WACf,EAAE,GAAA,EAAK,UAAU,YAAA,EAAc,IAAA,EAAM,SAAQ,GAC7C,EAAE,KAAK,QAAA,EAAU,YAAA,EAAc,MAAM,MAAM,QAAA,CAAS,OAAO,CAAA,EAAE;AACnE,EAAA,MAAM,MAAA,GAA6C;AAAA,IACjD,UAAU,CAAC,EAAE,IAAA,EAAM,UAAA,EAAY,UAAU;AAAA,GAC3C;AACA,EAAA,OAAQ,MAAM,SAAA,CAAU,OAAA;AAAA,IACtBC,4BAAA;AAAA,IACA;AAAA,GACF;AACF;AAEA,eAAe,SAAS,IAAA,EAA6B;AACnD,EAAA,MAAM,QAAQ,IAAI,UAAA,CAAW,MAAM,IAAA,CAAK,aAAa,CAAA;AACrD,EAAA,IAAI,MAAA,GAAS,EAAA;AACb,EAAA,KAAA,IAAS,IAAI,CAAA,EAAG,CAAA,GAAI,KAAA,CAAM,MAAA,EAAQ,KAAK,YAAA,EAAc;AACnD,IAAA,MAAA,IAAU,MAAA,CAAO,aAAa,GAAG,KAAA,CAAM,SAAS,CAAA,EAAG,CAAA,GAAI,YAAY,CAAC,CAAA;AAAA,EACtE;AACA,EAAA,OAAO,KAAK,MAAM,CAAA;AACpB","file":"index.cjs","sourcesContent":["/**\n * Hand the user a file to save, over the ext-apps `ui/download-file` request.\n *\n * A function over {@link App} rather than a method on it, like the helpers in\n * `extensions.ts` — but unlike them this is spec surface, so it is not gated on\n * the host identity. Any host that advertises `downloadFile` can answer it.\n *\n * The bytes always travel embedded. The spec also allows a `ResourceLink`, which\n * asks the host to fetch a URI the app names; a host holding the user's session\n * has every reason to refuse that, and the NimbleBrain host does.\n */\nimport {\n DOWNLOAD_FILE_METHOD,\n type McpUiDownloadFileRequest,\n type McpUiDownloadFileResult,\n} from \"@modelcontextprotocol/ext-apps\";\nimport type { EmbeddedResource } from \"@modelcontextprotocol/sdk/types.js\";\nimport { HostCapabilityError } from \"./errors.js\";\nimport { internalsFor } from \"./internals.js\";\nimport type { App } from \"./types.js\";\n\n/** Bytes per `String.fromCharCode` spread — well under any engine's argument limit. */\nconst BASE64_CHUNK = 0x8000;\n\n/**\n * Hand the user a file to save.\n *\n * A string is sent as the resource's `text`; a `Blob` is read and sent as\n * base64 `blob`. Reading a `Blob` is asynchronous, which is why this returns a\n * promise.\n *\n * Precedence for the MIME type: the explicit argument, then the Blob's own\n * type, then `application/octet-stream`. An empty-string argument falls\n * through — a `\"\"` MIME is effectively \"no type\".\n *\n * The filename is the last segment of the resource's `file:///` URI, because an\n * embedded resource has no name field of its own.\n *\n * Resolves with the host's result: `{ isError: true }` when the host declined\n * or the user cancelled. Rejects with `HostCapabilityError`, without sending,\n * when the host did not declare `downloadFile` — a host that does not implement\n * the request may never answer it, and a request has no deadline.\n */\nexport async function downloadFile(\n app: App,\n filename: string,\n content: string | Blob,\n mimeType?: string,\n): Promise<McpUiDownloadFileResult> {\n if (!app.hostCapabilities.downloadFile) {\n throw new HostCapabilityError(\"downloadFile\", \"downloadFile\");\n }\n const internals = internalsFor(app);\n const resolvedMime =\n mimeType || (content instanceof Blob ? content.type : \"\") || \"application/octet-stream\";\n const uri = `file:///${filename}`;\n const resource: EmbeddedResource[\"resource\"] =\n typeof content === \"string\"\n ? { uri, mimeType: resolvedMime, text: content }\n : { uri, mimeType: resolvedMime, blob: await toBase64(content) };\n const params: McpUiDownloadFileRequest[\"params\"] = {\n contents: [{ type: \"resource\", resource }],\n };\n return (await internals.request(\n DOWNLOAD_FILE_METHOD,\n params as unknown as Record<string, unknown>,\n )) as McpUiDownloadFileResult;\n}\n\nasync function toBase64(blob: Blob): Promise<string> {\n const bytes = new Uint8Array(await blob.arrayBuffer());\n let binary = \"\";\n for (let i = 0; i < bytes.length; i += BASE64_CHUNK) {\n binary += String.fromCharCode(...bytes.subarray(i, i + BASE64_CHUNK));\n }\n return btoa(binary);\n}\n"]}
|