@agent-native/core 0.22.13 → 0.22.15

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 (61) hide show
  1. package/dist/agent/engine/registry.d.ts.map +1 -1
  2. package/dist/agent/engine/registry.js +13 -1
  3. package/dist/agent/engine/registry.js.map +1 -1
  4. package/dist/client/MultiTabAssistantChat.d.ts.map +1 -1
  5. package/dist/client/MultiTabAssistantChat.js +5 -6
  6. package/dist/client/MultiTabAssistantChat.js.map +1 -1
  7. package/dist/client/agent-chat.d.ts.map +1 -1
  8. package/dist/client/agent-chat.js +13 -0
  9. package/dist/client/agent-chat.js.map +1 -1
  10. package/dist/client/index.d.ts +1 -0
  11. package/dist/client/index.d.ts.map +1 -1
  12. package/dist/client/index.js +1 -0
  13. package/dist/client/index.js.map +1 -1
  14. package/dist/client/mcp-app-host.d.ts +40 -0
  15. package/dist/client/mcp-app-host.d.ts.map +1 -0
  16. package/dist/client/mcp-app-host.js +165 -0
  17. package/dist/client/mcp-app-host.js.map +1 -0
  18. package/dist/client/sharing/ShareButton.d.ts +9 -0
  19. package/dist/client/sharing/ShareButton.d.ts.map +1 -1
  20. package/dist/client/sharing/ShareButton.js +19 -2
  21. package/dist/client/sharing/ShareButton.js.map +1 -1
  22. package/dist/client/use-chat-models.d.ts.map +1 -1
  23. package/dist/client/use-chat-models.js +4 -5
  24. package/dist/client/use-chat-models.js.map +1 -1
  25. package/dist/index.browser.d.ts +2 -1
  26. package/dist/index.browser.d.ts.map +1 -1
  27. package/dist/index.browser.js +2 -1
  28. package/dist/index.browser.js.map +1 -1
  29. package/dist/index.d.ts +2 -1
  30. package/dist/index.d.ts.map +1 -1
  31. package/dist/index.js +2 -1
  32. package/dist/index.js.map +1 -1
  33. package/dist/mcp/embed-app.d.ts.map +1 -1
  34. package/dist/mcp/embed-app.js +167 -1
  35. package/dist/mcp/embed-app.js.map +1 -1
  36. package/dist/mcp/embed-route.d.ts +26 -0
  37. package/dist/mcp/embed-route.d.ts.map +1 -0
  38. package/dist/mcp/embed-route.js +38 -0
  39. package/dist/mcp/embed-route.js.map +1 -0
  40. package/dist/mcp/index.d.ts +1 -0
  41. package/dist/mcp/index.d.ts.map +1 -1
  42. package/dist/mcp/index.js +1 -0
  43. package/dist/mcp/index.js.map +1 -1
  44. package/dist/scripts/agent-engines/list-agent-engines.d.ts.map +1 -1
  45. package/dist/scripts/agent-engines/list-agent-engines.js +18 -12
  46. package/dist/scripts/agent-engines/list-agent-engines.js.map +1 -1
  47. package/dist/server/core-routes-plugin.d.ts.map +1 -1
  48. package/dist/server/core-routes-plugin.js +22 -1
  49. package/dist/server/core-routes-plugin.js.map +1 -1
  50. package/dist/server/embed-route.d.ts.map +1 -1
  51. package/dist/server/embed-route.js +7 -1
  52. package/dist/server/embed-route.js.map +1 -1
  53. package/dist/shared/embed-auth.d.ts +1 -0
  54. package/dist/shared/embed-auth.d.ts.map +1 -1
  55. package/dist/shared/embed-auth.js +1 -0
  56. package/dist/shared/embed-auth.js.map +1 -1
  57. package/docs/content/actions.md +22 -7
  58. package/docs/content/client.md +43 -0
  59. package/docs/content/external-agents.md +40 -1
  60. package/docs/content/mcp-protocol.md +25 -0
  61. package/package.json +1 -1
@@ -1 +1 @@
1
- {"version":3,"file":"embed-route.d.ts","sourceRoot":"","sources":["../../src/server/embed-route.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,OAAO,EAAE,MAAM,IAAI,CAAC;AAQlC,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,WAAW,CAAC;AA0C7C,wBAAgB,mBAAmB,CAAC,MAAM,EAAE,MAAM,GAAG,MAAM,CAG1D;AAED,MAAM,WAAW,sBAAsB;IACrC,kBAAkB,CAAC,EAAE,CAAC,KAAK,EAAE,OAAO,KAAK,OAAO,CAAC,WAAW,GAAG,IAAI,CAAC,CAAC;CACtE;AAED,wBAAgB,4BAA4B,CAC1C,OAAO,GAAE,sBAA2B,2FAuCrC"}
1
+ {"version":3,"file":"embed-route.d.ts","sourceRoot":"","sources":["../../src/server/embed-route.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,OAAO,EAAE,MAAM,IAAI,CAAC;AAQlC,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,WAAW,CAAC;AA0C7C,wBAAgB,mBAAmB,CAAC,MAAM,EAAE,MAAM,GAAG,MAAM,CAG1D;AAED,MAAM,WAAW,sBAAsB;IACrC,kBAAkB,CAAC,EAAE,CAAC,KAAK,EAAE,OAAO,KAAK,OAAO,CAAC,WAAW,GAAG,IAAI,CAAC,CAAC;CACtE;AAED,wBAAgB,4BAA4B,CAC1C,OAAO,GAAE,sBAA2B,2FA8CrC"}
@@ -38,7 +38,13 @@ export function buildEmbedStartPath(ticket) {
38
38
  export function createEmbedStartRouteHandler(options = {}) {
39
39
  return defineEventHandler(async (event) => {
40
40
  const method = getMethod(event);
41
- if (method !== "GET" && method !== "HEAD") {
41
+ if (method === "HEAD") {
42
+ return new Response(null, {
43
+ status: 204,
44
+ headers: { "Cache-Control": "no-store" },
45
+ });
46
+ }
47
+ if (method !== "GET") {
42
48
  return textResponse("Method not allowed", 405);
43
49
  }
44
50
  const rawTicket = getQuery(event)?.ticket;
@@ -1 +1 @@
1
- {"version":3,"file":"embed-route.js","sourceRoot":"","sources":["../../src/server/embed-route.ts"],"names":[],"mappings":"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","sourcesContent":["import type { H3Event } from \"h3\";\nimport { defineEventHandler, getMethod, getQuery, setResponseHeader } from \"h3\";\nimport {\n consumeEmbedSessionTicket,\n normalizeEmbedTargetPath,\n setEmbedSessionCookie,\n signEmbedSessionToken,\n} from \"./embed-session.js\";\nimport type { AuthSession } from \"./auth.js\";\nimport { getConfiguredAppBasePath } from \"./app-base-path.js\";\nimport {\n EMBED_MODE_QUERY_PARAM,\n EMBED_START_PATH,\n EMBED_TOKEN_QUERY_PARAM,\n} from \"../shared/embed-auth.js\";\nimport { withCollapsedAgentSidebarParam } from \"../shared/agent-sidebar-url.js\";\n\nfunction withConfiguredBasePath(path: string): string {\n const base = getConfiguredAppBasePath();\n if (!base) return path;\n if (path === base || path.startsWith(`${base}/`)) return path;\n return `${base}${path}`;\n}\n\nfunction appendEmbedParams(target: string, token: string): string {\n const url = new URL(target, \"http://agent-native.invalid\");\n url.searchParams.set(EMBED_MODE_QUERY_PARAM, \"1\");\n url.searchParams.set(EMBED_TOKEN_QUERY_PARAM, token);\n return `${url.pathname}${url.search}${url.hash}`;\n}\n\nfunction redirectWithStagedCookies(\n event: H3Event,\n location: string,\n status = 302,\n): Response {\n const headers = new Headers({ Location: location });\n const staged = event.res?.headers?.getSetCookie?.() ?? [];\n for (const cookie of staged) headers.append(\"set-cookie\", cookie);\n headers.set(\"Referrer-Policy\", \"no-referrer\");\n return new Response(\"\", { status, headers });\n}\n\nfunction textResponse(message: string, status: number): Response {\n return new Response(message, {\n status,\n headers: { \"Content-Type\": \"text/plain; charset=utf-8\" },\n });\n}\n\nexport function buildEmbedStartPath(ticket: string): string {\n const qs = new URLSearchParams({ ticket });\n return `${getConfiguredAppBasePath()}${EMBED_START_PATH}?${qs}`;\n}\n\nexport interface EmbedStartRouteOptions {\n getExistingSession?: (event: H3Event) => Promise<AuthSession | null>;\n}\n\nexport function createEmbedStartRouteHandler(\n options: EmbedStartRouteOptions = {},\n) {\n return defineEventHandler(async (event: H3Event) => {\n const method = getMethod(event);\n if (method !== \"GET\" && method !== \"HEAD\") {\n return textResponse(\"Method not allowed\", 405);\n }\n\n const rawTicket = getQuery(event)?.ticket;\n const ticket = Array.isArray(rawTicket) ? rawTicket[0] : rawTicket;\n const existingSession = await options\n .getExistingSession?.(event)\n .catch(() => null);\n const consumed = await consumeEmbedSessionTicket(ticket, {\n expectedOrgId: existingSession?.orgId ?? null,\n });\n if (!consumed) {\n return textResponse(\"Invalid or expired embed session.\", 401);\n }\n\n const target = normalizeEmbedTargetPath(consumed.targetPath);\n if (!target) {\n return textResponse(\"Invalid embed target.\", 400);\n }\n\n const token = signEmbedSessionToken({\n ownerEmail: consumed.ownerEmail,\n orgId: consumed.orgId,\n targetPath: target,\n scope: consumed.scope,\n });\n setEmbedSessionCookie(event, token);\n setResponseHeader(event, \"Referrer-Policy\", \"no-referrer\");\n\n const location = withConfiguredBasePath(\n withCollapsedAgentSidebarParam(appendEmbedParams(target, token)),\n );\n return redirectWithStagedCookies(event, location);\n });\n}\n"]}
1
+ {"version":3,"file":"embed-route.js","sourceRoot":"","sources":["../../src/server/embed-route.ts"],"names":[],"mappings":"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","sourcesContent":["import type { H3Event } from \"h3\";\nimport { defineEventHandler, getMethod, getQuery, setResponseHeader } from \"h3\";\nimport {\n consumeEmbedSessionTicket,\n normalizeEmbedTargetPath,\n setEmbedSessionCookie,\n signEmbedSessionToken,\n} from \"./embed-session.js\";\nimport type { AuthSession } from \"./auth.js\";\nimport { getConfiguredAppBasePath } from \"./app-base-path.js\";\nimport {\n EMBED_MODE_QUERY_PARAM,\n EMBED_START_PATH,\n EMBED_TOKEN_QUERY_PARAM,\n} from \"../shared/embed-auth.js\";\nimport { withCollapsedAgentSidebarParam } from \"../shared/agent-sidebar-url.js\";\n\nfunction withConfiguredBasePath(path: string): string {\n const base = getConfiguredAppBasePath();\n if (!base) return path;\n if (path === base || path.startsWith(`${base}/`)) return path;\n return `${base}${path}`;\n}\n\nfunction appendEmbedParams(target: string, token: string): string {\n const url = new URL(target, \"http://agent-native.invalid\");\n url.searchParams.set(EMBED_MODE_QUERY_PARAM, \"1\");\n url.searchParams.set(EMBED_TOKEN_QUERY_PARAM, token);\n return `${url.pathname}${url.search}${url.hash}`;\n}\n\nfunction redirectWithStagedCookies(\n event: H3Event,\n location: string,\n status = 302,\n): Response {\n const headers = new Headers({ Location: location });\n const staged = event.res?.headers?.getSetCookie?.() ?? [];\n for (const cookie of staged) headers.append(\"set-cookie\", cookie);\n headers.set(\"Referrer-Policy\", \"no-referrer\");\n return new Response(\"\", { status, headers });\n}\n\nfunction textResponse(message: string, status: number): Response {\n return new Response(message, {\n status,\n headers: { \"Content-Type\": \"text/plain; charset=utf-8\" },\n });\n}\n\nexport function buildEmbedStartPath(ticket: string): string {\n const qs = new URLSearchParams({ ticket });\n return `${getConfiguredAppBasePath()}${EMBED_START_PATH}?${qs}`;\n}\n\nexport interface EmbedStartRouteOptions {\n getExistingSession?: (event: H3Event) => Promise<AuthSession | null>;\n}\n\nexport function createEmbedStartRouteHandler(\n options: EmbedStartRouteOptions = {},\n) {\n return defineEventHandler(async (event: H3Event) => {\n const method = getMethod(event);\n if (method === \"HEAD\") {\n return new Response(null, {\n status: 204,\n headers: { \"Cache-Control\": \"no-store\" },\n });\n }\n\n if (method !== \"GET\") {\n return textResponse(\"Method not allowed\", 405);\n }\n\n const rawTicket = getQuery(event)?.ticket;\n const ticket = Array.isArray(rawTicket) ? rawTicket[0] : rawTicket;\n const existingSession = await options\n .getExistingSession?.(event)\n .catch(() => null);\n const consumed = await consumeEmbedSessionTicket(ticket, {\n expectedOrgId: existingSession?.orgId ?? null,\n });\n if (!consumed) {\n return textResponse(\"Invalid or expired embed session.\", 401);\n }\n\n const target = normalizeEmbedTargetPath(consumed.targetPath);\n if (!target) {\n return textResponse(\"Invalid embed target.\", 400);\n }\n\n const token = signEmbedSessionToken({\n ownerEmail: consumed.ownerEmail,\n orgId: consumed.orgId,\n targetPath: target,\n scope: consumed.scope,\n });\n setEmbedSessionCookie(event, token);\n setResponseHeader(event, \"Referrer-Policy\", \"no-referrer\");\n\n const location = withConfiguredBasePath(\n withCollapsedAgentSidebarParam(appendEmbedParams(target, token)),\n );\n return redirectWithStagedCookies(event, location);\n });\n}\n"]}
@@ -1,6 +1,7 @@
1
1
  export declare const EMBED_START_PATH = "/_agent-native/embed/start";
2
2
  export declare const EMBED_TOKEN_QUERY_PARAM = "__an_embed_token";
3
3
  export declare const EMBED_MODE_QUERY_PARAM = "embedded";
4
+ export declare const MCP_APP_CHAT_BRIDGE_QUERY_PARAM = "__an_mcp_chat_bridge";
4
5
  export declare const EMBED_SESSION_COOKIE = "an_embed_session";
5
6
  export declare const EMBED_TARGET_HEADER = "x-agent-native-embed-target";
6
7
  //# sourceMappingURL=embed-auth.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"embed-auth.d.ts","sourceRoot":"","sources":["../../src/shared/embed-auth.ts"],"names":[],"mappings":"AAAA,eAAO,MAAM,gBAAgB,+BAA+B,CAAC;AAC7D,eAAO,MAAM,uBAAuB,qBAAqB,CAAC;AAC1D,eAAO,MAAM,sBAAsB,aAAa,CAAC;AACjD,eAAO,MAAM,oBAAoB,qBAAqB,CAAC;AACvD,eAAO,MAAM,mBAAmB,gCAAgC,CAAC"}
1
+ {"version":3,"file":"embed-auth.d.ts","sourceRoot":"","sources":["../../src/shared/embed-auth.ts"],"names":[],"mappings":"AAAA,eAAO,MAAM,gBAAgB,+BAA+B,CAAC;AAC7D,eAAO,MAAM,uBAAuB,qBAAqB,CAAC;AAC1D,eAAO,MAAM,sBAAsB,aAAa,CAAC;AACjD,eAAO,MAAM,+BAA+B,yBAAyB,CAAC;AACtE,eAAO,MAAM,oBAAoB,qBAAqB,CAAC;AACvD,eAAO,MAAM,mBAAmB,gCAAgC,CAAC"}
@@ -1,6 +1,7 @@
1
1
  export const EMBED_START_PATH = "/_agent-native/embed/start";
2
2
  export const EMBED_TOKEN_QUERY_PARAM = "__an_embed_token";
3
3
  export const EMBED_MODE_QUERY_PARAM = "embedded";
4
+ export const MCP_APP_CHAT_BRIDGE_QUERY_PARAM = "__an_mcp_chat_bridge";
4
5
  export const EMBED_SESSION_COOKIE = "an_embed_session";
5
6
  export const EMBED_TARGET_HEADER = "x-agent-native-embed-target";
6
7
  //# sourceMappingURL=embed-auth.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"embed-auth.js","sourceRoot":"","sources":["../../src/shared/embed-auth.ts"],"names":[],"mappings":"AAAA,MAAM,CAAC,MAAM,gBAAgB,GAAG,4BAA4B,CAAC;AAC7D,MAAM,CAAC,MAAM,uBAAuB,GAAG,kBAAkB,CAAC;AAC1D,MAAM,CAAC,MAAM,sBAAsB,GAAG,UAAU,CAAC;AACjD,MAAM,CAAC,MAAM,oBAAoB,GAAG,kBAAkB,CAAC;AACvD,MAAM,CAAC,MAAM,mBAAmB,GAAG,6BAA6B,CAAC","sourcesContent":["export const EMBED_START_PATH = \"/_agent-native/embed/start\";\nexport const EMBED_TOKEN_QUERY_PARAM = \"__an_embed_token\";\nexport const EMBED_MODE_QUERY_PARAM = \"embedded\";\nexport const EMBED_SESSION_COOKIE = \"an_embed_session\";\nexport const EMBED_TARGET_HEADER = \"x-agent-native-embed-target\";\n"]}
1
+ {"version":3,"file":"embed-auth.js","sourceRoot":"","sources":["../../src/shared/embed-auth.ts"],"names":[],"mappings":"AAAA,MAAM,CAAC,MAAM,gBAAgB,GAAG,4BAA4B,CAAC;AAC7D,MAAM,CAAC,MAAM,uBAAuB,GAAG,kBAAkB,CAAC;AAC1D,MAAM,CAAC,MAAM,sBAAsB,GAAG,UAAU,CAAC;AACjD,MAAM,CAAC,MAAM,+BAA+B,GAAG,sBAAsB,CAAC;AACtE,MAAM,CAAC,MAAM,oBAAoB,GAAG,kBAAkB,CAAC;AACvD,MAAM,CAAC,MAAM,mBAAmB,GAAG,6BAA6B,CAAC","sourcesContent":["export const EMBED_START_PATH = \"/_agent-native/embed/start\";\nexport const EMBED_TOKEN_QUERY_PARAM = \"__an_embed_token\";\nexport const EMBED_MODE_QUERY_PARAM = \"embedded\";\nexport const MCP_APP_CHAT_BRIDGE_QUERY_PARAM = \"__an_mcp_chat_bridge\";\nexport const EMBED_SESSION_COOKIE = \"an_embed_session\";\nexport const EMBED_TARGET_HEADER = \"x-agent-native-embed-target\";\n"]}
@@ -166,25 +166,33 @@ This works for draft emails, filtered inboxes, calendar event drafts, full
166
166
  dashboards, saved analyses, extension routes, decks, design editors, and any
167
167
  other state the app can load from a route.
168
168
 
169
+ Keep MCP Apps URL-first. Prefer a durable app route such as
170
+ `/dashboards/:id`, `/compose?draft=...`, or `/chart?payload=...` over passing
171
+ large opaque state through the bridge. When an action's `link` and `mcpApp`
172
+ should point at the same route, use `embedRoute()` to create both from one pure
173
+ path builder. The host bridge is for host-owned capabilities: model context
174
+ updates, host-mediated links, host context, and display-mode requests.
175
+
169
176
  When a whole app surface is too much, embed a narrow route that renders a real
170
177
  shared React component instead. For example, Analytics can render `/chart` with
171
178
  a compact `SqlPanel` URL payload so the MCP host shows one live chart while the
172
179
  implementation still reuses the dashboard chart component.
173
180
 
174
181
  ```ts
175
- import { embedApp } from "@agent-native/core";
182
+ import { embedRoute } from "@agent-native/core";
176
183
 
177
184
  export default defineAction({
178
185
  description: "Create an email draft for review.",
179
186
  schema: z.object({ body: z.string() }),
180
187
  run: async ({ body }) => ({ body }),
181
- link: ({ result }) => ({
182
- label: "Open draft in Mail",
183
- url: "/_agent-native/open?app=mail&view=inbox",
188
+ ...embedRoute({
189
+ title: "Review draft",
190
+ openLabel: "Open in Mail",
191
+ path: ({ result }) => ({
192
+ label: "Open draft in Mail",
193
+ url: "/_agent-native/open?app=mail&view=inbox",
194
+ }),
184
195
  }),
185
- mcpApp: {
186
- resource: embedApp({ title: "Review draft", openLabel: "Open in Mail" }),
187
- },
188
196
  });
189
197
  ```
190
198
 
@@ -192,6 +200,13 @@ This advertises the MCP Apps extension (`io.modelcontextprotocol/ui`), exposes t
192
200
 
193
201
  The helper launches the action's `link` target through `/_agent-native/embed/start` with a short-lived browser session, so routes such as full dashboards, filtered inboxes, drafts, and extension pages can reuse the app's React components directly.
194
202
 
203
+ Embedded routes can use the exported client helpers for the MCP App host
204
+ bridge. Under the hood, routes receive `agentNative.mcpHostContext` and may
205
+ post `agentNative.mcpHost.updateModelContext`,
206
+ `agentNative.mcpHost.openLink`, or
207
+ `agentNative.mcpHost.requestDisplayMode`; the wrapper replies with
208
+ `agentNative.mcpHost.response`.
209
+
195
210
  ## Standard actions {#standard-actions}
196
211
 
197
212
  Every template should include these two for [context awareness](/docs/context-awareness):
@@ -73,6 +73,14 @@ navigate(`/inbox/${threadId}`);
73
73
 
74
74
  Send a message to the agent chat via postMessage. Used to delegate AI tasks from UI interactions.
75
75
 
76
+ When the app route is running inside an MCP App embed created with `embedApp()`,
77
+ auto-submitted messages (`submit` omitted or `true`) are forwarded to the MCP
78
+ App wrapper, which asks the containing host to add hidden context and send the
79
+ visible user turn. `context` is sent as model context before the visible
80
+ message, so it stays model-visible without being posted as user-facing chat.
81
+ `submit: false` keeps the local prefill/review behavior because MCP Apps do not
82
+ define a standard draft-prefill API.
83
+
76
84
  ```ts
77
85
  import { sendToAgentChat } from "@agent-native/core";
78
86
 
@@ -102,6 +110,41 @@ sendToAgentChat({
102
110
  | `preset` | `string?` | Optional preset name for downstream consumers |
103
111
  | `referenceImagePaths` | `string[]?` | Optional reference image paths |
104
112
 
113
+ ## MCP App Host Bridge {#mcp-app-host-bridge}
114
+
115
+ Routes embedded by `embedApp()` should be URL-first: load the current artifact
116
+ from path/query params, render the real React route or a focused shared
117
+ component, and use host bridge messages only for host-owned behavior.
118
+
119
+ The wire contract is:
120
+
121
+ | Direction | Message type | Purpose |
122
+ | --------------- | ---------------------------------------- | ------------------------------------------------- |
123
+ | wrapper → route | `agentNative.mcpHostContext` | Push host context such as theme/display mode |
124
+ | route → wrapper | `agentNative.mcpHost.updateModelContext` | Add hidden model context |
125
+ | route → wrapper | `agentNative.mcpHost.openLink` | Ask the host to open a URL |
126
+ | route → wrapper | `agentNative.mcpHost.requestDisplayMode` | Ask for `inline`, `fullscreen`, or `pip` |
127
+ | wrapper → route | `agentNative.mcpHost.response` | Resolve or reject a request by matching requestId |
128
+
129
+ Use the exported helpers from `@agent-native/core/client` inside embedded
130
+ routes:
131
+
132
+ ```ts
133
+ import {
134
+ getMcpAppHostContext,
135
+ openMcpAppHostLink,
136
+ requestMcpAppDisplayMode,
137
+ updateMcpAppModelContext,
138
+ useMcpAppHostContext,
139
+ } from "@agent-native/core/client";
140
+ ```
141
+
142
+ `getMcpAppHostContext()` reads the latest pushed host context snapshot;
143
+ `useMcpAppHostContext()` subscribes React components to changes. The request
144
+ helpers return `false` outside an embedded MCP App frame, or
145
+ `Promise<boolean>` inside a frame. `sendToAgentChat()` uses the same bridge for
146
+ auto-submitted prompts from embedded routes.
147
+
105
148
  ## Dynamic Suggestions {#dynamic-suggestions}
106
149
 
107
150
  `<AgentSidebar>`, `<AgentPanel>`, and `<AssistantChat>` merge static `suggestions` with context-aware suggestions by default. The framework reads `navigation`, `selection`, `pending-selection-context`, and the current URL from application state while an empty chat is visible, then offers prompt chips that match the current screen.
@@ -215,6 +215,34 @@ That makes the same app surface available to every compatible host rather than b
215
215
 
216
216
  Claude Code and other CLI-first clients still receive the same resources and metadata when they support MCP Apps, but the deep link remains the reliable fallback when a host chooses not to render an iframe. In practice, every agent-native app should be authored with both: MCP Apps for inline review/edit in capable hosts, and `link` for universal round-tripping back to the full app.
217
217
 
218
+ ### First-class MCP App bridge {#mcp-app-bridge}
219
+
220
+ MCP App embeds are route embeds, not separate mini-products. `embedApp()`
221
+ starts from the action's `link` target, creates a short-lived embed session,
222
+ and loads that URL in an iframe. Design embedded routes so a reload with the
223
+ same URL reconstructs the same view.
224
+
225
+ The host bridge is deliberately small:
226
+
227
+ | Direction | Message type | Use it for |
228
+ | --------------- | ---------------------------------------- | ---------------------------------------- |
229
+ | wrapper → route | `agentNative.mcpHostContext` | Theme, locale, host platform, dimensions |
230
+ | route → wrapper | `agentNative.mcpHost.updateModelContext` | Hidden context for the host model |
231
+ | route → wrapper | `agentNative.mcpHost.openLink` | Open an external or app URL via the host |
232
+ | route → wrapper | `agentNative.mcpHost.requestDisplayMode` | Request `inline`, `fullscreen`, or `pip` |
233
+ | wrapper → route | `agentNative.mcpHost.response` | Correlate async request results |
234
+
235
+ Embedded routes can use `updateMcpAppModelContext()`,
236
+ `openMcpAppHostLink()`, `requestMcpAppDisplayMode()`,
237
+ `getMcpAppHostContext()`, and `useMcpAppHostContext()` from
238
+ `@agent-native/core/client`. `sendToAgentChat()` uses the same path from
239
+ full-app embeds for auto-submitted prompts.
240
+
241
+ Display mode is best-effort. The in-app `McpAppRenderer` currently reports an
242
+ inline web host context and an inline-only display mode; external hosts may
243
+ honor larger display requests, ignore them, or reply with an unsupported-mode
244
+ error. Always keep the inline route usable.
245
+
218
246
  ### Generic cross-app verbs {#cross-app}
219
247
 
220
248
  On top of the per-action tools the MCP server exposes a stable verb set, so an external agent has a predictable surface without guessing per-app action names:
@@ -231,6 +259,8 @@ On top of the per-action tools the MCP server exposes a stable verb set, so an e
231
259
 
232
260
  For OAuth callers that request `mcp:apps`, the server intentionally advertises a compact `tools/list` catalog so app hosts do not ingest every internal action schema. The model sees app-facing builtins (`list_apps`, `open_app`, app-only `create_embed_session`) and actions with `mcpApp`. Stdio/static-token developer clients still get the full connected action surface, and `publicAgent.expose` remains the opt-in for safe read/ingest tools outside the compact app catalog. If a UI-capable host should be able to call a new action from an MCP App conversation, mark it with `mcpApp`; use `publicAgent` for non-UI read/ingest handoff tools.
233
261
 
262
+ For fast ChatGPT/Claude handoffs, the ideal path is direct: call the action that creates or opens the artifact, then let the MCP App widget launch the iframe. A Mail request should call `manage_draft` and render the real compose route. A dashboard request should call `open_app({ path, embed: true })` or a dashboard action with `mcpApp` and render the full Analytics route. Calendar, Forms, Content, Slides, Design, and Clips should follow the same pattern with their draft/create/search actions. `list_apps` is useful when the model must choose among granted apps; broad `resources/list`, full-catalog discovery, or `ask_app` delegation should not be the normal route for an obvious UI handoff.
263
+
234
264
  ### Per-app tour {#tour}
235
265
 
236
266
  Every allow-listed template that produces or lists a navigable resource ships a `link` builder, and the ingest-heavy ones ship a GET + `publicAgent` action so a connected agent can pull live state:
@@ -283,7 +313,7 @@ List/search actions point at a record-focused view the same way — e.g. calenda
283
313
 
284
314
  For hosts that support the MCP Apps extension, an action can also advertise an inline UI resource with `mcpApp`. This is a progressive enhancement for flows where the external agent should hand the user an interactive surface instead of only text — for example reviewing an email draft, editing a calendar invite, or choosing between generated dashboard variants.
285
315
 
286
- Use the real React app with `embedApp()` whenever the user needs UI. The mental model is simple: the action's `link` target is also the MCP App embed target. Expose the operation as a normal action/tool, return a focused deep link with `link`, and add `mcpApp.resource = embedApp(...)` so capable hosts load that same route inline instead of opening a new tab.
316
+ Use the real React app with `embedRoute()` or `embedApp()` whenever the user needs UI. The mental model is simple: the action's `link` target is also the MCP App embed target. Expose the operation as a normal action/tool, return a focused deep link with `link`, and add `mcpApp.resource = embedApp(...)` so capable hosts load that same route inline instead of opening a new tab. When both should be built from the same route, prefer `embedRoute({ title, openLabel, path })`; it returns matching `link` and `mcpApp` action fields.
287
317
 
288
318
  That means full-app embeds can do anything the route can do once opened: review or edit an email draft, show a filtered inbox/search, open a calendar event or event draft, load an extension page, inspect a full analytics dashboard or saved analysis, continue a deck in the Slides editor, or open a Design project/editor. Prefer URL/deep-link params and the existing `/_agent-native/open` navigation/app-state bridge over inventing a second state protocol for MCP Apps.
289
319
 
@@ -312,6 +342,12 @@ The MCP server advertises extension `io.modelcontextprotocol/ui`, adds `_meta.ui
312
342
 
313
343
  Keep the existing `link` builder even when adding `mcpApp`. CLI-only clients, older hosts, and any host that does not render MCP Apps will ignore the UI metadata and still need the `"Open in … →"` link. `embedApp()` uses that link as its launch target, calls the app-only `create_embed_session` helper, exchanges a one-time SQL ticket at `/_agent-native/embed/start`, and loads the target route in an iframe with a short-lived browser session plus a bearer fallback for same-origin fetches. `open_app({ app, path, embed: true })` is the generic escape hatch for routes such as full dashboards, filtered inboxes, calendar draft views, analyses, and extension pages, and should be used liberally when the full app is the clearest review/edit surface.
314
344
 
345
+ Inside those `embedApp()` full-app iframes, `sendToAgentChat()` is host-aware:
346
+ auto-submitted prompts are relayed to the wrapper, which uses the host's model
347
+ context and message APIs for hidden context plus the visible user turn. Hosts
348
+ without MCP Apps messaging support simply ignore the bridge, and
349
+ `submit: false` remains a local review/prefill path.
350
+
315
351
  ### The `link` contract {#link-contract}
316
352
 
317
353
  The `link` builder is **pure and synchronous — no I/O, no awaits**. It runs best-effort: a throw, `null`, or `undefined` is swallowed and **never** fails the tool call. It only reads the call's `args` and `result`; it must not query the DB, read app-state, or call other actions. Return `null` when there's nothing to open.
@@ -452,6 +488,9 @@ The fallback hosted `connect` flow never copies the deployment's shared secret.
452
488
  - Make external-agent ingest actions GET + `readOnly` + `publicAgent`, and read live (Yjs) state, not the stale DB column.
453
489
  - Let the open route resolve the browser session; pass record ids as deep-link params and let the UI focus them via the polled `navigate` command.
454
490
  - Revoke a minted connect token by `jti` when an agent client is decommissioned.
491
+ - Test MCP Apps with the lightweight fixtures around `embedApp()` and
492
+ `McpAppRenderer`; they cover CSP, host context, app launch, and bridge
493
+ message behavior without needing a real external host.
455
494
 
456
495
  **Don't**
457
496
 
@@ -74,6 +74,31 @@ The server supports the standard MCP handshake: `initialize` → `initialized`
74
74
 
75
75
  If an action declares `mcpApp`, the server also advertises the official MCP Apps extension (`io.modelcontextprotocol/ui`) and supports `resources/list`, `resources/templates/list`, and `resources/read` for the app resource. Hosts that render MCP Apps can show the UI inline; hosts that do not can still call the tool and use the deep-link fallback. Product UIs should use `embedApp()` so the inline surface is the real React app route, or a focused route that renders a shared React component such as an Analytics chart, not a separate plain HTML implementation. The server emits both standard MCP Apps metadata and ChatGPT Apps SDK compatibility metadata so app-capable hosts can find the same `ui://` resource. The current official extension matrix includes Claude, Claude Desktop, VS Code GitHub Copilot, Goose, Postman, MCPJam, ChatGPT, and Cursor; host support varies by version and plan, so use the [External Agents MCP Apps notes](/docs/external-agents#mcp-apps-compatibility) for the user-facing guidance.
76
76
 
77
+ ### MCP App embed bridge {#mcp-app-embed-bridge}
78
+
79
+ `embedApp()` is the low-level URL-first MCP App helper. It reads the action
80
+ result's open link, asks the app-only `create_embed_session` tool to mint a
81
+ route-scoped session, then loads the resulting route in an iframe. For normal
82
+ action authoring, use `embedRoute()` when the action's `link` and `mcpApp`
83
+ should come from the same pure route builder. The route itself should derive
84
+ state from the URL and normal app data fetching.
85
+
86
+ The bridge between the wrapper and the embedded route uses Agent-Native
87
+ postMessage types:
88
+
89
+ | Direction | Type | Payload shape |
90
+ | --------------- | ---------------------------------------- | --------------------------------------------- |
91
+ | wrapper → route | `agentNative.mcpHostContext` | `{ context, capabilities, version }` |
92
+ | route → wrapper | `agentNative.mcpHost.updateModelContext` | `{ requestId, content?, structuredContent? }` |
93
+ | route → wrapper | `agentNative.mcpHost.openLink` | `{ requestId, url }` |
94
+ | route → wrapper | `agentNative.mcpHost.requestDisplayMode` | `{ requestId, mode }` |
95
+ | wrapper → route | `agentNative.mcpHost.response` | `{ requestId, ok, result?, error? }` |
96
+
97
+ Host-mediated open links keep the iframe from choosing its own browser target.
98
+ Model context updates are opt-in and hidden from the user-facing transcript.
99
+ Display mode requests are best-effort: a host can honor, ignore, or reject the
100
+ request. Embedded routes must remain functional in the default inline mode.
101
+
77
102
  ## Tools {#tools}
78
103
 
79
104
  Stdio/static-token developer clients see all connected app actions as MCP tools. OAuth callers that request `mcp:apps` get a compact app-host catalog: app-facing builtins and actions with `mcpApp`. `publicAgent.expose` remains the opt-in for safe read/ingest tools outside that compact app catalog. This keeps ChatGPT/Claude app-host discovery small while preserving the full developer surface for local agents.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@agent-native/core",
3
- "version": "0.22.13",
3
+ "version": "0.22.15",
4
4
  "type": "module",
5
5
  "description": "Framework for agent-native application development — where AI agents and UI share state via files",
6
6
  "license": "MIT",