@agent-native/core 0.103.1 → 0.104.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 (565) hide show
  1. package/corpus/README.md +2 -2
  2. package/corpus/core/CHANGELOG.md +30 -0
  3. package/corpus/core/package.json +9 -2
  4. package/corpus/core/src/agent/engine/credential-errors.ts +2 -2
  5. package/corpus/core/src/agent/production-agent.ts +30 -0
  6. package/corpus/core/src/agent/run-store.ts +12 -2
  7. package/corpus/core/src/cli/create.ts +1 -0
  8. package/corpus/core/src/cli/skills-content/visual-plan-skill.ts +30 -11
  9. package/corpus/core/src/cli/templates-meta.ts +4 -3
  10. package/corpus/core/src/client/AgentAskPopover.tsx +89 -0
  11. package/corpus/core/src/client/AgentChatHome.tsx +4 -0
  12. package/corpus/core/src/client/AgentPanel.tsx +321 -223
  13. package/corpus/core/src/client/AssistantChat.tsx +6 -10
  14. package/corpus/core/src/client/MultiTabAssistantChat.tsx +53 -372
  15. package/corpus/core/src/client/agent-chat-adapter.ts +13 -1
  16. package/corpus/core/src/client/agent-page/AgentContextTab.tsx +133 -149
  17. package/corpus/core/src/client/agent-page/AgentEmptyState.tsx +44 -0
  18. package/corpus/core/src/client/agent-page/AgentJobsTab.tsx +153 -82
  19. package/corpus/core/src/client/agent-page/AgentTabFrame.tsx +39 -0
  20. package/corpus/core/src/client/agent-page/AgentTabsPage.tsx +368 -356
  21. package/corpus/core/src/client/agent-page/types.ts +1 -1
  22. package/corpus/core/src/client/analytics.ts +51 -5
  23. package/corpus/core/src/client/chat/run-recovery.tsx +12 -4
  24. package/corpus/core/src/client/composer/PromptComposer.tsx +5 -15
  25. package/corpus/core/src/client/composer/TiptapComposer.tsx +32 -3
  26. package/corpus/core/src/client/dynamic-suggestions.ts +3 -3
  27. package/corpus/core/src/client/index.ts +16 -1
  28. package/corpus/core/src/client/resources/ResourceTree.tsx +249 -38
  29. package/corpus/core/src/client/resources/ResourcesPanel.tsx +307 -140
  30. package/corpus/core/src/client/session-replay.ts +158 -5
  31. package/corpus/core/src/client/settings/AutomationsSection.tsx +30 -10
  32. package/corpus/core/src/client/settings/SettingsPanel.tsx +3 -2
  33. package/corpus/core/src/client/settings/SettingsTabsPage.tsx +2 -0
  34. package/corpus/core/src/client/settings/agent-settings-search.ts +2 -2
  35. package/corpus/core/src/client/use-chat-threads.ts +2 -0
  36. package/corpus/core/src/connections/catalog.ts +49 -7
  37. package/corpus/core/src/db/index.ts +6 -1
  38. package/corpus/core/src/extensions/actions.ts +106 -16
  39. package/corpus/core/src/extensions/content-patch.ts +22 -0
  40. package/corpus/core/src/extensions/routes.ts +18 -0
  41. package/corpus/core/src/extensions/store.ts +8 -0
  42. package/corpus/core/src/index.ts +3 -0
  43. package/corpus/core/src/ingestion/docx.ts +158 -0
  44. package/corpus/core/src/ingestion/figma-node-to-html.ts +1860 -0
  45. package/corpus/core/src/ingestion/figma.ts +548 -0
  46. package/corpus/core/src/ingestion/index.ts +107 -0
  47. package/corpus/core/src/ingestion/media.ts +264 -0
  48. package/corpus/core/src/ingestion/notion.ts +121 -0
  49. package/corpus/core/src/ingestion/office.ts +214 -0
  50. package/corpus/core/src/ingestion/orchestration.ts +160 -0
  51. package/corpus/core/src/ingestion/pptx.ts +333 -0
  52. package/corpus/core/src/ingestion/selection.ts +81 -0
  53. package/corpus/core/src/ingestion/website.ts +151 -0
  54. package/corpus/core/src/integrations/plugin.ts +45 -37
  55. package/corpus/core/src/localization/default-messages.ts +35 -12
  56. package/corpus/core/src/observability/hosted-model-experiment.ts +118 -0
  57. package/corpus/core/src/observability/traces.ts +5 -3
  58. package/corpus/core/src/provider-api/index.ts +452 -8
  59. package/corpus/core/src/scripts/agent-engines/list-agent-engines.ts +18 -1
  60. package/corpus/core/src/search-utils/index.ts +112 -0
  61. package/corpus/core/src/secrets/register-framework-secrets.ts +61 -0
  62. package/corpus/core/src/server/action-discovery.ts +33 -8
  63. package/corpus/core/src/server/agent-chat/framework-prompts.ts +2 -2
  64. package/corpus/core/src/server/agent-chat/prompt-resources.ts +144 -0
  65. package/corpus/core/src/server/agent-chat-plugin.ts +6 -0
  66. package/corpus/core/src/server/core-routes-plugin.ts +12 -0
  67. package/corpus/core/src/server/index.ts +30 -0
  68. package/corpus/core/src/server/workspace-provider-oauth.ts +583 -0
  69. package/corpus/core/src/styles/agent-native.css +9 -0
  70. package/corpus/core/src/templates/default/app/i18n/en-US.ts +3 -3
  71. package/corpus/core/src/templates/workspace-core/.agents/skills/extensions/SKILL.md +14 -5
  72. package/corpus/core/src/templates/workspace-root/.env.example +12 -0
  73. package/corpus/core/src/workspace-connections/index.ts +6 -0
  74. package/corpus/core/src/workspace-connections/lifecycle.ts +43 -0
  75. package/corpus/core/src/workspace-connections/store.ts +16 -0
  76. package/corpus/templates/analytics/.agents/skills/dashboard-management/SKILL.md +46 -3
  77. package/corpus/templates/analytics/AGENTS.md +9 -0
  78. package/corpus/templates/analytics/actions/dashboard-mutation-api.ts +120 -6
  79. package/corpus/templates/analytics/actions/mutate-dashboard.ts +92 -30
  80. package/corpus/templates/analytics/actions/update-dashboard.ts +5 -5
  81. package/corpus/templates/analytics/app/components/dashboard/SqlChart.tsx +313 -220
  82. package/corpus/templates/analytics/app/components/layout/CommandPalette.tsx +2 -2
  83. package/corpus/templates/analytics/app/components/layout/Layout.tsx +9 -6
  84. package/corpus/templates/analytics/app/components/layout/Sidebar.tsx +90 -64
  85. package/corpus/templates/analytics/app/i18n-data.ts +3 -3
  86. package/corpus/templates/analytics/app/lib/dashboard-list-loading.ts +25 -0
  87. package/corpus/templates/analytics/app/lib/item-popularity.ts +13 -4
  88. package/corpus/templates/analytics/app/pages/adhoc/sql-dashboard/DashboardFilterBar.tsx +1 -1
  89. package/corpus/templates/analytics/app/pages/adhoc/sql-dashboard/pivot.ts +8 -3
  90. package/corpus/templates/analytics/app/pages/adhoc/sql-dashboard/types.ts +1 -0
  91. package/corpus/templates/analytics/app/pages/sessions/SessionDetailPage.tsx +15 -3
  92. package/corpus/templates/analytics/changelog/2026-07-16-dashboard-filter-defaults-can-now-be-changed-reliably-withou.md +6 -0
  93. package/corpus/templates/analytics/changelog/2026-07-16-dashboard-lists-load-in-one-stable-order-without-popping-bet.md +6 -0
  94. package/corpus/templates/analytics/changelog/2026-07-16-fixed-dashboard-filter-dropdown-text-alignment.md +6 -0
  95. package/corpus/templates/analytics/changelog/2026-07-16-recurring-signed-in-users-can-now-be-viewed-as-weekly-bars-b.md +6 -0
  96. package/corpus/templates/analytics/changelog/2026-07-16-the-analytics-agent-can-now-duplicate-a-chart-and-place-the-.md +6 -0
  97. package/corpus/templates/analytics/seeds/dashboards/agent-native-templates-first-party.json +41 -1
  98. package/corpus/templates/analytics/server/lib/dashboard-catalog.ts +1 -1
  99. package/corpus/templates/analytics/server/lib/first-party-metric-catalog.ts +47 -1
  100. package/corpus/templates/analytics/server/lib/session-replay.ts +68 -0
  101. package/corpus/templates/analytics/server/plugins/agent-chat.ts +1 -0
  102. package/corpus/templates/analytics/server/routes/sessions/lookup.get.ts +47 -0
  103. package/corpus/templates/assets/.agents/skills/asset-generation/SKILL.md +16 -9
  104. package/corpus/templates/assets/.agents/skills/creative-context/SKILL.md +86 -0
  105. package/corpus/templates/assets/AGENTS.md +10 -0
  106. package/corpus/templates/assets/actions/create-generation-session.ts +59 -1
  107. package/corpus/templates/assets/actions/edit-image.ts +2 -0
  108. package/corpus/templates/assets/actions/generate-asset.ts +52 -0
  109. package/corpus/templates/assets/actions/generate-image-batch.ts +55 -0
  110. package/corpus/templates/assets/actions/generate-image.ts +219 -1
  111. package/corpus/templates/assets/actions/open-asset-picker.ts +14 -0
  112. package/corpus/templates/assets/actions/refine-image.ts +3 -0
  113. package/corpus/templates/assets/actions/restyle-image.ts +2 -0
  114. package/corpus/templates/assets/agent-native.app-skill.json +4 -0
  115. package/corpus/templates/assets/app/components/layout/Layout.tsx +2 -0
  116. package/corpus/templates/assets/app/i18n/zh-TW.ts +3 -0
  117. package/corpus/templates/assets/app/i18n-data.ts +29 -13
  118. package/corpus/templates/assets/app/routes/agent.tsx +7 -1
  119. package/corpus/templates/assets/app/routes/library.tsx +9 -0
  120. package/corpus/templates/assets/app/routes/settings.tsx +3 -0
  121. package/corpus/templates/assets/changelog/2026-07-16-creative-context-library.md +6 -0
  122. package/corpus/templates/assets/package.json +1 -0
  123. package/corpus/templates/assets/server/lib/image-processing.ts +1 -22
  124. package/corpus/templates/assets/server/plugins/creative-context.ts +205 -0
  125. package/corpus/templates/brain/app/i18n-data.ts +3 -3
  126. package/corpus/templates/brain/app/lib/brain.ts +1 -1
  127. package/corpus/templates/brain/server/lib/search.ts +17 -67
  128. package/corpus/templates/calendar/app/i18n-data.ts +3 -3
  129. package/corpus/templates/calendar/app/pages/BookingLinksPage.tsx +19 -18
  130. package/corpus/templates/chat/app/i18n/en-US.ts +3 -3
  131. package/corpus/templates/chat/app/lib/agent-page.tsx +10 -1
  132. package/corpus/templates/clips/.agents/skills/meetings/SKILL.md +1 -1
  133. package/corpus/templates/clips/AGENTS.md +4 -0
  134. package/corpus/templates/clips/actions/cleanup-transcript.ts +35 -4
  135. package/corpus/templates/clips/actions/create-meeting.ts +6 -2
  136. package/corpus/templates/clips/actions/create-organization.ts +3 -2
  137. package/corpus/templates/clips/actions/create-recording.ts +4 -1
  138. package/corpus/templates/clips/actions/finalize-recording.ts +44 -7
  139. package/corpus/templates/clips/actions/import-loom-recording.ts +4 -1
  140. package/corpus/templates/clips/actions/lib/create-recording-schema.ts +2 -2
  141. package/corpus/templates/clips/actions/list-meetings.ts +23 -5
  142. package/corpus/templates/clips/actions/list-organization-state.ts +1 -1
  143. package/corpus/templates/clips/actions/remove-silences.ts +10 -1
  144. package/corpus/templates/clips/actions/request-transcript.ts +53 -11
  145. package/corpus/templates/clips/actions/search-recordings-utils.ts +7 -0
  146. package/corpus/templates/clips/actions/search-recordings.ts +5 -8
  147. package/corpus/templates/clips/actions/set-organization-branding.ts +2 -2
  148. package/corpus/templates/clips/actions/stitch-recordings.ts +10 -5
  149. package/corpus/templates/clips/actions/update-ai-request-status.ts +38 -0
  150. package/corpus/templates/clips/app/components/editor/editor-layout.tsx +3 -4
  151. package/corpus/templates/clips/app/components/editor/editor-selection.ts +19 -0
  152. package/corpus/templates/clips/app/components/editor/stitch-manager.tsx +10 -10
  153. package/corpus/templates/clips/app/components/library/bulk-action-toolbar.tsx +1 -2
  154. package/corpus/templates/clips/app/components/library/library-grid.tsx +101 -93
  155. package/corpus/templates/clips/app/components/player/video-player.tsx +11 -0
  156. package/corpus/templates/clips/app/components/workspace/branding-editor.tsx +53 -1
  157. package/corpus/templates/clips/app/i18n/ar-SA.ts +7 -1
  158. package/corpus/templates/clips/app/i18n/de-DE.ts +7 -1
  159. package/corpus/templates/clips/app/i18n/en-US.ts +10 -4
  160. package/corpus/templates/clips/app/i18n/es-ES.ts +7 -1
  161. package/corpus/templates/clips/app/i18n/fr-FR.ts +7 -1
  162. package/corpus/templates/clips/app/i18n/hi-IN.ts +7 -1
  163. package/corpus/templates/clips/app/i18n/ja-JP.ts +7 -1
  164. package/corpus/templates/clips/app/i18n/ko-KR.ts +7 -1
  165. package/corpus/templates/clips/app/i18n/pt-BR.ts +7 -1
  166. package/corpus/templates/clips/app/i18n/zh-CN.ts +6 -1
  167. package/corpus/templates/clips/app/i18n/zh-TW.ts +6 -1
  168. package/corpus/templates/clips/app/routes/_app.settings._index.tsx +5 -9
  169. package/corpus/templates/clips/app/routes/_app.settings.organization.tsx +6 -2
  170. package/corpus/templates/clips/app/routes/r.$recordingId.tsx +129 -27
  171. package/corpus/templates/clips/app/routes/record.tsx +23 -2
  172. package/corpus/templates/clips/app/routes/share.$shareId.tsx +6 -2
  173. package/corpus/templates/clips/changelog/2026-07-16-authorized-viewers-can-open-shared-private-clips-without-a-m.md +6 -0
  174. package/corpus/templates/clips/changelog/2026-07-16-camera-bubble-hover-controls-appear-above-the-face.md +6 -0
  175. package/corpus/templates/clips/changelog/2026-07-16-chrome-extension-recovers-stale-recorder-state.md +6 -0
  176. package/corpus/templates/clips/changelog/2026-07-16-clips-agent-chat-no-longer-shows-a-separate-workspace-header.md +6 -0
  177. package/corpus/templates/clips/changelog/2026-07-16-clips-search-now-matches-recording-content-without-requiring.md +6 -0
  178. package/corpus/templates/clips/changelog/2026-07-16-declined-meetings-no-longer-show-desktop-reminders.md +6 -0
  179. package/corpus/templates/clips/changelog/2026-07-16-failed-desktop-saves-now-show-their-local-recovery-copy.md +6 -0
  180. package/corpus/templates/clips/changelog/2026-07-16-long-desktop-clips-now-preserve-complete-playback-synced-aud.md +6 -0
  181. package/corpus/templates/clips/changelog/2026-07-16-long-recording-lists-keep-stitch-and-library-actions-visible.md +6 -0
  182. package/corpus/templates/clips/changelog/2026-07-16-organization-admins-can-choose-new-recording-visibility.md +6 -0
  183. package/corpus/templates/clips/changelog/2026-07-16-remove-silences-now-shows-queued-active-completed-and-failed.md +6 -0
  184. package/corpus/templates/clips/changelog/2026-07-16-settings-no-longer-repeats-the-builder-connection-status-in-.md +6 -0
  185. package/corpus/templates/clips/changelog/2026-07-16-transcripts-now-appear-from-native-browser-speech-sooner-wit.md +6 -0
  186. package/corpus/templates/clips/chrome-extension/public/manifest.json +1 -1
  187. package/corpus/templates/clips/chrome-extension/src/background.ts +73 -1
  188. package/corpus/templates/clips/chrome-extension/src/native-recording-state.ts +32 -0
  189. package/corpus/templates/clips/chrome-extension/src/native-transcription.ts +248 -0
  190. package/corpus/templates/clips/chrome-extension/src/offscreen.ts +106 -0
  191. package/corpus/templates/clips/desktop/src/app.tsx +66 -28
  192. package/corpus/templates/clips/desktop/src/lib/recorder.ts +335 -285
  193. package/corpus/templates/clips/desktop/src/lib/single-flight.ts +7 -0
  194. package/corpus/templates/clips/desktop/src/lib/upload-verification.ts +51 -0
  195. package/corpus/templates/clips/desktop/src/overlays/bubble.tsx +2 -2
  196. package/corpus/templates/clips/desktop/src/overlays/finalizing.tsx +10 -2
  197. package/corpus/templates/clips/desktop/src/styles.css +13 -11
  198. package/corpus/templates/clips/desktop/src-tauri/src/clips/mod.rs +8 -9
  199. package/corpus/templates/clips/desktop/src-tauri/src/meetings_watcher.rs +1 -0
  200. package/corpus/templates/clips/desktop/src-tauri/src/native_screen/custom_capture.rs +88 -13
  201. package/corpus/templates/clips/desktop/src-tauri/src/native_screen/live_upload.rs +13 -2
  202. package/corpus/templates/clips/desktop/src-tauri/src/native_screen.rs +241 -6
  203. package/corpus/templates/clips/server/db/schema.ts +2 -2
  204. package/corpus/templates/clips/server/lib/builder-media-compression.ts +64 -67
  205. package/corpus/templates/clips/server/lib/calendar-event-classification.ts +19 -0
  206. package/corpus/templates/clips/server/lib/google-calendar-client.ts +1 -0
  207. package/corpus/templates/clips/server/lib/recordings.ts +40 -1
  208. package/corpus/templates/clips/server/plugins/agent-chat.ts +1 -0
  209. package/corpus/templates/clips/server/plugins/db.ts +2 -2
  210. package/corpus/templates/clips/server/routes/api/auth/google-calendar.get.ts +1 -1
  211. package/corpus/templates/clips/server/routes/api/public-recording.get.ts +14 -5
  212. package/corpus/templates/clips/server/routes/api/uploads/[recordingId]/chunk.post.ts +51 -1
  213. package/corpus/templates/clips/server/routes/api/video/[recordingId].get.ts +1 -64
  214. package/corpus/templates/clips/shared/media-worker-contract.ts +32 -15
  215. package/corpus/templates/content/.agents/skills/content/SKILL.md +16 -0
  216. package/corpus/templates/content/.agents/skills/creative-context/SKILL.md +85 -0
  217. package/corpus/templates/content/.agents/skills/notion-integration/SKILL.md +8 -0
  218. package/corpus/templates/content/AGENTS.md +9 -0
  219. package/corpus/templates/content/actions/create-document.ts +94 -0
  220. package/corpus/templates/content/actions/edit-document.ts +144 -4
  221. package/corpus/templates/content/actions/update-document.ts +138 -0
  222. package/corpus/templates/content/agent-native.app-skill.json +4 -0
  223. package/corpus/templates/content/app/components/layout/Layout.tsx +2 -0
  224. package/corpus/templates/content/app/i18n/zh-TW.ts +3 -0
  225. package/corpus/templates/content/app/i18n-data.ts +13 -4
  226. package/corpus/templates/content/app/routes/_app.agent.tsx +2 -1
  227. package/corpus/templates/content/app/routes/_app.settings.tsx +3 -0
  228. package/corpus/templates/content/changelog/2026-07-16-creative-context-library.md +6 -0
  229. package/corpus/templates/content/package.json +1 -0
  230. package/corpus/templates/content/server/plugins/creative-context.ts +31 -0
  231. package/corpus/templates/design/.agents/skills/creative-context/SKILL.md +116 -0
  232. package/corpus/templates/design/.agents/skills/design-generation/SKILL.md +16 -0
  233. package/corpus/templates/design/.agents/skills/design-systems/SKILL.md +8 -0
  234. package/corpus/templates/design/AGENTS.md +6 -0
  235. package/corpus/templates/design/actions/clone-creative-context-design.ts +176 -0
  236. package/corpus/templates/design/actions/edit-design.ts +128 -0
  237. package/corpus/templates/design/actions/generate-design.ts +278 -14
  238. package/corpus/templates/design/actions/generate-screens.ts +42 -1
  239. package/corpus/templates/design/agent-native.app-skill.json +4 -0
  240. package/corpus/templates/design/app/components/layout/Layout.tsx +7 -3
  241. package/corpus/templates/design/app/i18n/zh-TW.ts +3 -0
  242. package/corpus/templates/design/app/i18n-data.ts +10 -4
  243. package/corpus/templates/design/app/routes/agent.tsx +2 -1
  244. package/corpus/templates/design/app/routes/settings.tsx +3 -0
  245. package/corpus/templates/design/changelog/2026-07-16-creative-context-library.md +6 -0
  246. package/corpus/templates/design/changelog/2026-07-16-design-agent-chat-no-longer-shows-a-separate-workspace-header.md +6 -0
  247. package/corpus/templates/design/package.json +1 -0
  248. package/corpus/templates/design/server/lib/figma-design-context.ts +5 -335
  249. package/corpus/templates/design/server/lib/figma-node-to-html.ts +1 -1859
  250. package/corpus/templates/design/server/lib/import-design-files.ts +6 -8
  251. package/corpus/templates/design/server/plugins/creative-context.ts +31 -0
  252. package/corpus/templates/design/shared/generation-session.ts +7 -0
  253. package/corpus/templates/dispatch/app/i18n-data.ts +3 -3
  254. package/corpus/templates/forms/app/i18n/en-US.ts +3 -3
  255. package/corpus/templates/macros/app/i18n/en-US.ts +3 -3
  256. package/corpus/templates/mail/app/components/email/EmailThread.tsx +35 -5
  257. package/corpus/templates/mail/app/i18n/en-US.ts +3 -3
  258. package/corpus/templates/mail/changelog/2026-07-16-mail-previews-now-expand-to-show-the-full-message-without-an.md +6 -0
  259. package/corpus/templates/plan/.agents/skills/visual-plan/SKILL.md +30 -11
  260. package/corpus/templates/plan/AGENTS.md +21 -1
  261. package/corpus/templates/plan/actions/get-visual-plan.ts +1 -1
  262. package/corpus/templates/plan/actions/patch-visual-plan-source.ts +161 -0
  263. package/corpus/templates/plan/actions/read-visual-plan-source.ts +1 -1
  264. package/corpus/templates/plan/actions/update-visual-plan.ts +126 -10
  265. package/corpus/templates/plan/app/hooks/use-plans.ts +2 -0
  266. package/corpus/templates/plan/app/i18n/en-US.ts +3 -3
  267. package/corpus/templates/plan/app/pages/PlansPage.tsx +65 -62
  268. package/corpus/templates/plan/changelog/2026-07-16-local-plan-previews-now-load-annotations-containing-html-lik.md +6 -0
  269. package/corpus/templates/plan/changelog/2026-07-16-plan-agents-now-prevent-stale-edits-from-overwriting-newer-p.md +6 -0
  270. package/corpus/templates/plan/server/plan-mdx.ts +75 -2
  271. package/corpus/templates/slides/.agents/skills/create-deck/SKILL.md +21 -4
  272. package/corpus/templates/slides/.agents/skills/creative-context/SKILL.md +122 -0
  273. package/corpus/templates/slides/.agents/skills/design-systems/SKILL.md +11 -0
  274. package/corpus/templates/slides/.agents/skills/slide-editing/SKILL.md +12 -3
  275. package/corpus/templates/slides/AGENTS.md +6 -0
  276. package/corpus/templates/slides/actions/add-slide.ts +230 -14
  277. package/corpus/templates/slides/actions/clone-context-slide.ts +302 -0
  278. package/corpus/templates/slides/actions/create-deck.ts +130 -0
  279. package/corpus/templates/slides/actions/extract-pdf.ts +6 -2
  280. package/corpus/templates/slides/actions/import-file.ts +5 -4
  281. package/corpus/templates/slides/actions/patch-deck.ts +200 -10
  282. package/corpus/templates/slides/actions/update-slide.ts +208 -15
  283. package/corpus/templates/slides/app/components/layout/Layout.tsx +2 -0
  284. package/corpus/templates/slides/app/components/visual-editor/CanvasCommentPins.tsx +16 -1
  285. package/corpus/templates/slides/app/i18n/ar-SA.ts +3 -0
  286. package/corpus/templates/slides/app/i18n/de-DE.ts +3 -0
  287. package/corpus/templates/slides/app/i18n/en-US.ts +6 -3
  288. package/corpus/templates/slides/app/i18n/es-ES.ts +3 -0
  289. package/corpus/templates/slides/app/i18n/fr-FR.ts +3 -0
  290. package/corpus/templates/slides/app/i18n/hi-IN.ts +3 -0
  291. package/corpus/templates/slides/app/i18n/ja-JP.ts +3 -0
  292. package/corpus/templates/slides/app/i18n/ko-KR.ts +3 -0
  293. package/corpus/templates/slides/app/i18n/pt-BR.ts +3 -0
  294. package/corpus/templates/slides/app/i18n/zh-CN.ts +3 -0
  295. package/corpus/templates/slides/app/i18n/zh-TW.ts +3 -0
  296. package/corpus/templates/slides/app/lib/validate-native-slide-html.ts +176 -0
  297. package/corpus/templates/slides/app/routes/agent.tsx +7 -1
  298. package/corpus/templates/slides/app/routes/settings.tsx +3 -0
  299. package/corpus/templates/slides/changelog/2026-07-16-creative-context-library.md +6 -0
  300. package/corpus/templates/slides/changelog/2026-07-16-google-slides-native-cloning.md +6 -0
  301. package/corpus/templates/slides/package.json +1 -0
  302. package/corpus/templates/slides/server/handlers/import/docx-parser.ts +4 -85
  303. package/corpus/templates/slides/server/handlers/import/pptx-parser.ts +7 -421
  304. package/corpus/templates/slides/server/plugins/creative-context.ts +166 -0
  305. package/dist/agent/engine/credential-errors.d.ts +1 -1
  306. package/dist/agent/engine/credential-errors.d.ts.map +1 -1
  307. package/dist/agent/engine/credential-errors.js +2 -2
  308. package/dist/agent/engine/credential-errors.js.map +1 -1
  309. package/dist/agent/production-agent.d.ts.map +1 -1
  310. package/dist/agent/production-agent.js +25 -0
  311. package/dist/agent/production-agent.js.map +1 -1
  312. package/dist/agent/run-store.d.ts.map +1 -1
  313. package/dist/agent/run-store.js +12 -2
  314. package/dist/agent/run-store.js.map +1 -1
  315. package/dist/cli/create.d.ts.map +1 -1
  316. package/dist/cli/create.js +1 -0
  317. package/dist/cli/create.js.map +1 -1
  318. package/dist/cli/skills-content/visual-plan-skill.d.ts +1 -1
  319. package/dist/cli/skills-content/visual-plan-skill.d.ts.map +1 -1
  320. package/dist/cli/skills-content/visual-plan-skill.js +30 -11
  321. package/dist/cli/skills-content/visual-plan-skill.js.map +1 -1
  322. package/dist/cli/templates-meta.d.ts.map +1 -1
  323. package/dist/cli/templates-meta.js +4 -3
  324. package/dist/cli/templates-meta.js.map +1 -1
  325. package/dist/client/AgentAskPopover.d.ts +11 -0
  326. package/dist/client/AgentAskPopover.d.ts.map +1 -0
  327. package/dist/client/AgentAskPopover.js +30 -0
  328. package/dist/client/AgentAskPopover.js.map +1 -0
  329. package/dist/client/AgentChatHome.d.ts +1 -1
  330. package/dist/client/AgentChatHome.d.ts.map +1 -1
  331. package/dist/client/AgentChatHome.js +2 -2
  332. package/dist/client/AgentChatHome.js.map +1 -1
  333. package/dist/client/AgentPanel.d.ts +9 -19
  334. package/dist/client/AgentPanel.d.ts.map +1 -1
  335. package/dist/client/AgentPanel.js +119 -80
  336. package/dist/client/AgentPanel.js.map +1 -1
  337. package/dist/client/AssistantChat.d.ts.map +1 -1
  338. package/dist/client/AssistantChat.js +4 -4
  339. package/dist/client/AssistantChat.js.map +1 -1
  340. package/dist/client/MultiTabAssistantChat.d.ts +3 -9
  341. package/dist/client/MultiTabAssistantChat.d.ts.map +1 -1
  342. package/dist/client/MultiTabAssistantChat.js +49 -189
  343. package/dist/client/MultiTabAssistantChat.js.map +1 -1
  344. package/dist/client/agent-chat-adapter.d.ts.map +1 -1
  345. package/dist/client/agent-chat-adapter.js +12 -1
  346. package/dist/client/agent-chat-adapter.js.map +1 -1
  347. package/dist/client/agent-page/AgentContextTab.d.ts.map +1 -1
  348. package/dist/client/agent-page/AgentContextTab.js +26 -28
  349. package/dist/client/agent-page/AgentContextTab.js.map +1 -1
  350. package/dist/client/agent-page/AgentEmptyState.d.ts +13 -0
  351. package/dist/client/agent-page/AgentEmptyState.d.ts.map +1 -0
  352. package/dist/client/agent-page/AgentEmptyState.js +6 -0
  353. package/dist/client/agent-page/AgentEmptyState.js.map +1 -0
  354. package/dist/client/agent-page/AgentJobsTab.d.ts +1 -1
  355. package/dist/client/agent-page/AgentJobsTab.d.ts.map +1 -1
  356. package/dist/client/agent-page/AgentJobsTab.js +90 -58
  357. package/dist/client/agent-page/AgentJobsTab.js.map +1 -1
  358. package/dist/client/agent-page/AgentTabFrame.d.ts +12 -0
  359. package/dist/client/agent-page/AgentTabFrame.d.ts.map +1 -0
  360. package/dist/client/agent-page/AgentTabFrame.js +7 -0
  361. package/dist/client/agent-page/AgentTabFrame.js.map +1 -0
  362. package/dist/client/agent-page/AgentTabsPage.d.ts +9 -1
  363. package/dist/client/agent-page/AgentTabsPage.d.ts.map +1 -1
  364. package/dist/client/agent-page/AgentTabsPage.js +135 -99
  365. package/dist/client/agent-page/AgentTabsPage.js.map +1 -1
  366. package/dist/client/agent-page/types.d.ts +1 -1
  367. package/dist/client/agent-page/types.d.ts.map +1 -1
  368. package/dist/client/agent-page/types.js.map +1 -1
  369. package/dist/client/analytics.d.ts +10 -3
  370. package/dist/client/analytics.d.ts.map +1 -1
  371. package/dist/client/analytics.js +37 -2
  372. package/dist/client/analytics.js.map +1 -1
  373. package/dist/client/chat/run-recovery.d.ts.map +1 -1
  374. package/dist/client/chat/run-recovery.js +10 -3
  375. package/dist/client/chat/run-recovery.js.map +1 -1
  376. package/dist/client/composer/PromptComposer.d.ts.map +1 -1
  377. package/dist/client/composer/PromptComposer.js +2 -2
  378. package/dist/client/composer/PromptComposer.js.map +1 -1
  379. package/dist/client/composer/TiptapComposer.d.ts.map +1 -1
  380. package/dist/client/composer/TiptapComposer.js +15 -3
  381. package/dist/client/composer/TiptapComposer.js.map +1 -1
  382. package/dist/client/dynamic-suggestions.js +3 -3
  383. package/dist/client/dynamic-suggestions.js.map +1 -1
  384. package/dist/client/index.d.ts +4 -3
  385. package/dist/client/index.d.ts.map +1 -1
  386. package/dist/client/index.js +3 -2
  387. package/dist/client/index.js.map +1 -1
  388. package/dist/client/resources/ResourceTree.d.ts +5 -1
  389. package/dist/client/resources/ResourceTree.d.ts.map +1 -1
  390. package/dist/client/resources/ResourceTree.js +74 -5
  391. package/dist/client/resources/ResourceTree.js.map +1 -1
  392. package/dist/client/resources/ResourcesPanel.d.ts +11 -2
  393. package/dist/client/resources/ResourcesPanel.d.ts.map +1 -1
  394. package/dist/client/resources/ResourcesPanel.js +105 -31
  395. package/dist/client/resources/ResourcesPanel.js.map +1 -1
  396. package/dist/client/session-replay.d.ts +28 -0
  397. package/dist/client/session-replay.d.ts.map +1 -1
  398. package/dist/client/session-replay.js +122 -8
  399. package/dist/client/session-replay.js.map +1 -1
  400. package/dist/client/settings/AutomationsSection.d.ts +3 -1
  401. package/dist/client/settings/AutomationsSection.d.ts.map +1 -1
  402. package/dist/client/settings/AutomationsSection.js +16 -6
  403. package/dist/client/settings/AutomationsSection.js.map +1 -1
  404. package/dist/client/settings/SettingsPanel.d.ts.map +1 -1
  405. package/dist/client/settings/SettingsPanel.js +3 -3
  406. package/dist/client/settings/SettingsPanel.js.map +1 -1
  407. package/dist/client/settings/SettingsTabsPage.d.ts +2 -0
  408. package/dist/client/settings/SettingsTabsPage.d.ts.map +1 -1
  409. package/dist/client/settings/SettingsTabsPage.js.map +1 -1
  410. package/dist/client/settings/agent-settings-search.js +2 -2
  411. package/dist/client/settings/agent-settings-search.js.map +1 -1
  412. package/dist/client/use-chat-threads.d.ts +2 -0
  413. package/dist/client/use-chat-threads.d.ts.map +1 -1
  414. package/dist/client/use-chat-threads.js.map +1 -1
  415. package/dist/collab/routes.d.ts +1 -1
  416. package/dist/connections/catalog.d.ts +41 -7
  417. package/dist/connections/catalog.d.ts.map +1 -1
  418. package/dist/connections/catalog.js +40 -7
  419. package/dist/connections/catalog.js.map +1 -1
  420. package/dist/db/index.d.ts +2 -2
  421. package/dist/db/index.d.ts.map +1 -1
  422. package/dist/db/index.js +2 -2
  423. package/dist/db/index.js.map +1 -1
  424. package/dist/extensions/actions.d.ts.map +1 -1
  425. package/dist/extensions/actions.js +85 -15
  426. package/dist/extensions/actions.js.map +1 -1
  427. package/dist/extensions/content-patch.d.ts +4 -0
  428. package/dist/extensions/content-patch.d.ts.map +1 -1
  429. package/dist/extensions/content-patch.js +18 -0
  430. package/dist/extensions/content-patch.js.map +1 -1
  431. package/dist/extensions/routes.d.ts.map +1 -1
  432. package/dist/extensions/routes.js +14 -0
  433. package/dist/extensions/routes.js.map +1 -1
  434. package/dist/extensions/store.d.ts +1 -0
  435. package/dist/extensions/store.d.ts.map +1 -1
  436. package/dist/extensions/store.js +4 -1
  437. package/dist/extensions/store.js.map +1 -1
  438. package/dist/file-upload/actions/upload-image.d.ts +1 -1
  439. package/dist/index.d.ts +1 -1
  440. package/dist/index.d.ts.map +1 -1
  441. package/dist/index.js +1 -1
  442. package/dist/index.js.map +1 -1
  443. package/dist/ingestion/docx.d.ts +16 -0
  444. package/dist/ingestion/docx.d.ts.map +1 -0
  445. package/dist/ingestion/docx.js +129 -0
  446. package/dist/ingestion/docx.js.map +1 -0
  447. package/dist/ingestion/figma-node-to-html.d.ts +304 -0
  448. package/dist/ingestion/figma-node-to-html.d.ts.map +1 -0
  449. package/dist/ingestion/figma-node-to-html.js +1292 -0
  450. package/dist/ingestion/figma-node-to-html.js.map +1 -0
  451. package/dist/ingestion/figma.d.ts +115 -0
  452. package/dist/ingestion/figma.d.ts.map +1 -0
  453. package/dist/ingestion/figma.js +399 -0
  454. package/dist/ingestion/figma.js.map +1 -0
  455. package/dist/ingestion/index.d.ts +11 -0
  456. package/dist/ingestion/index.d.ts.map +1 -0
  457. package/dist/ingestion/index.js +11 -0
  458. package/dist/ingestion/index.js.map +1 -0
  459. package/dist/ingestion/media.d.ts +36 -0
  460. package/dist/ingestion/media.d.ts.map +1 -0
  461. package/dist/ingestion/media.js +178 -0
  462. package/dist/ingestion/media.js.map +1 -0
  463. package/dist/ingestion/notion.d.ts +12 -0
  464. package/dist/ingestion/notion.d.ts.map +1 -0
  465. package/dist/ingestion/notion.js +104 -0
  466. package/dist/ingestion/notion.js.map +1 -0
  467. package/dist/ingestion/office.d.ts +45 -0
  468. package/dist/ingestion/office.d.ts.map +1 -0
  469. package/dist/ingestion/office.js +141 -0
  470. package/dist/ingestion/office.js.map +1 -0
  471. package/dist/ingestion/orchestration.d.ts +52 -0
  472. package/dist/ingestion/orchestration.d.ts.map +1 -0
  473. package/dist/ingestion/orchestration.js +89 -0
  474. package/dist/ingestion/orchestration.js.map +1 -0
  475. package/dist/ingestion/pptx.d.ts +28 -0
  476. package/dist/ingestion/pptx.d.ts.map +1 -0
  477. package/dist/ingestion/pptx.js +255 -0
  478. package/dist/ingestion/pptx.js.map +1 -0
  479. package/dist/ingestion/selection.d.ts +20 -0
  480. package/dist/ingestion/selection.d.ts.map +1 -0
  481. package/dist/ingestion/selection.js +52 -0
  482. package/dist/ingestion/selection.js.map +1 -0
  483. package/dist/ingestion/website.d.ts +27 -0
  484. package/dist/ingestion/website.d.ts.map +1 -0
  485. package/dist/ingestion/website.js +100 -0
  486. package/dist/ingestion/website.js.map +1 -0
  487. package/dist/integrations/plugin.d.ts.map +1 -1
  488. package/dist/integrations/plugin.js +32 -27
  489. package/dist/integrations/plugin.js.map +1 -1
  490. package/dist/localization/default-messages.d.ts +22 -0
  491. package/dist/localization/default-messages.d.ts.map +1 -1
  492. package/dist/localization/default-messages.js +31 -9
  493. package/dist/localization/default-messages.js.map +1 -1
  494. package/dist/notifications/routes.d.ts +1 -1
  495. package/dist/observability/hosted-model-experiment.d.ts +39 -0
  496. package/dist/observability/hosted-model-experiment.d.ts.map +1 -0
  497. package/dist/observability/hosted-model-experiment.js +90 -0
  498. package/dist/observability/hosted-model-experiment.js.map +1 -0
  499. package/dist/observability/traces.d.ts.map +1 -1
  500. package/dist/observability/traces.js +5 -3
  501. package/dist/observability/traces.js.map +1 -1
  502. package/dist/progress/routes.d.ts +1 -1
  503. package/dist/provider-api/index.d.ts +35 -4
  504. package/dist/provider-api/index.d.ts.map +1 -1
  505. package/dist/provider-api/index.js +339 -8
  506. package/dist/provider-api/index.js.map +1 -1
  507. package/dist/scripts/agent-engines/list-agent-engines.d.ts.map +1 -1
  508. package/dist/scripts/agent-engines/list-agent-engines.js +18 -1
  509. package/dist/scripts/agent-engines/list-agent-engines.js.map +1 -1
  510. package/dist/search-utils/index.d.ts +12 -0
  511. package/dist/search-utils/index.d.ts.map +1 -0
  512. package/dist/search-utils/index.js +95 -0
  513. package/dist/search-utils/index.js.map +1 -0
  514. package/dist/secrets/register-framework-secrets.d.ts.map +1 -1
  515. package/dist/secrets/register-framework-secrets.js +57 -0
  516. package/dist/secrets/register-framework-secrets.js.map +1 -1
  517. package/dist/server/action-discovery.d.ts +8 -0
  518. package/dist/server/action-discovery.d.ts.map +1 -1
  519. package/dist/server/action-discovery.js +26 -9
  520. package/dist/server/action-discovery.js.map +1 -1
  521. package/dist/server/agent-chat/framework-prompts.js +2 -2
  522. package/dist/server/agent-chat/framework-prompts.js.map +1 -1
  523. package/dist/server/agent-chat/prompt-resources.d.ts +19 -0
  524. package/dist/server/agent-chat/prompt-resources.d.ts.map +1 -1
  525. package/dist/server/agent-chat/prompt-resources.js +95 -0
  526. package/dist/server/agent-chat/prompt-resources.js.map +1 -1
  527. package/dist/server/agent-chat-plugin.d.ts.map +1 -1
  528. package/dist/server/agent-chat-plugin.js +7 -0
  529. package/dist/server/agent-chat-plugin.js.map +1 -1
  530. package/dist/server/agent-engine-api-key-route.d.ts +1 -1
  531. package/dist/server/core-routes-plugin.d.ts.map +1 -1
  532. package/dist/server/core-routes-plugin.js +5 -0
  533. package/dist/server/core-routes-plugin.js.map +1 -1
  534. package/dist/server/index.d.ts +5 -1
  535. package/dist/server/index.d.ts.map +1 -1
  536. package/dist/server/index.js +5 -1
  537. package/dist/server/index.js.map +1 -1
  538. package/dist/server/workspace-provider-oauth.d.ts +48 -0
  539. package/dist/server/workspace-provider-oauth.d.ts.map +1 -0
  540. package/dist/server/workspace-provider-oauth.js +415 -0
  541. package/dist/server/workspace-provider-oauth.js.map +1 -0
  542. package/dist/styles/agent-native.css +9 -0
  543. package/dist/templates/chat/app/i18n/en-US.ts +3 -3
  544. package/dist/templates/chat/app/lib/agent-page.tsx +10 -1
  545. package/dist/templates/default/app/i18n/en-US.ts +3 -3
  546. package/dist/templates/workspace-core/.agents/skills/extensions/SKILL.md +14 -5
  547. package/dist/templates/workspace-root/.env.example +12 -0
  548. package/dist/workspace-connections/index.d.ts +1 -0
  549. package/dist/workspace-connections/index.d.ts.map +1 -1
  550. package/dist/workspace-connections/index.js +1 -0
  551. package/dist/workspace-connections/index.js.map +1 -1
  552. package/dist/workspace-connections/lifecycle.d.ts +16 -0
  553. package/dist/workspace-connections/lifecycle.d.ts.map +1 -0
  554. package/dist/workspace-connections/lifecycle.js +14 -0
  555. package/dist/workspace-connections/lifecycle.js.map +1 -0
  556. package/dist/workspace-connections/store.d.ts.map +1 -1
  557. package/dist/workspace-connections/store.js +16 -0
  558. package/dist/workspace-connections/store.js.map +1 -1
  559. package/package.json +10 -3
  560. package/src/templates/chat/app/i18n/en-US.ts +3 -3
  561. package/src/templates/chat/app/lib/agent-page.spec.tsx +10 -1
  562. package/src/templates/chat/app/lib/agent-page.tsx +10 -1
  563. package/src/templates/default/app/i18n/en-US.ts +3 -3
  564. package/src/templates/workspace-core/.agents/skills/extensions/SKILL.md +14 -5
  565. package/src/templates/workspace-root/.env.example +12 -0
@@ -20,9 +20,11 @@ import {
20
20
  listOAuthAccountsByOwner,
21
21
  saveOAuthTokens,
22
22
  } from "../oauth-tokens/index.js";
23
+ import { resolveSecret } from "../server/credential-provider.js";
23
24
  import { resolveGoogleProviderCredentialCandidates } from "../server/google-oauth-credentials.js";
24
25
  import { getCredentialContext } from "../server/request-context.js";
25
26
  import { resolveWorkspaceConnectionCredentialForApp } from "../workspace-connections/credentials.js";
27
+ import { resolveWorkspaceConnectionForApp } from "../workspace-connections/store.js";
26
28
  import type {
27
29
  CustomProviderConfig,
28
30
  CustomProviderAuthKind,
@@ -66,6 +68,7 @@ export const PROVIDER_API_IDS = [
66
68
  "gong",
67
69
  "google_calendar",
68
70
  "google_drive",
71
+ "google_slides",
69
72
  "granola",
70
73
  "grafana",
71
74
  "hubspot",
@@ -345,6 +348,22 @@ export type ProviderApiAuthKind =
345
348
  type: "oauth-bearer";
346
349
  oauthProvider: string;
347
350
  tokenLabel: string;
351
+ workspaceProvider?: string;
352
+ }
353
+ | {
354
+ type: "oauth-bearer-or-api-key-header";
355
+ oauthProvider: string;
356
+ tokenLabel: string;
357
+ key: string;
358
+ header: string;
359
+ workspaceProvider: string;
360
+ }
361
+ | {
362
+ type: "oauth-bearer-or-bearer-key";
363
+ oauthProvider: string;
364
+ tokenLabel: string;
365
+ key: string;
366
+ workspaceProvider: string;
348
367
  }
349
368
  | {
350
369
  type: "prometheus";
@@ -486,6 +505,14 @@ export interface ProviderApiRuntime {
486
505
  ): Promise<GitHubRepositoryFileDeleteResult>;
487
506
  }
488
507
 
508
+ export interface ProviderApiOAuthAccessToken {
509
+ accessToken: string;
510
+ accountId: string | null;
511
+ accountLabel: string | null;
512
+ connectionId: string | null;
513
+ connectionLabel: string | null;
514
+ }
515
+
489
516
  interface ResolvedAuth {
490
517
  headers: Record<string, string>;
491
518
  credentialSources: Array<Omit<ProviderApiResolvedCredential, "value">>;
@@ -837,9 +864,12 @@ const PROVIDER_CONFIGS: Record<ProviderApiId, ProviderApiConfig> = {
837
864
  label: "Figma REST API",
838
865
  defaultBaseUrl: "https://api.figma.com/v1",
839
866
  auth: {
840
- type: "api-key-header",
867
+ type: "oauth-bearer-or-api-key-header",
868
+ oauthProvider: "figma",
869
+ tokenLabel: "Figma OAuth token",
841
870
  key: "FIGMA_ACCESS_TOKEN",
842
871
  header: "X-Figma-Token",
872
+ workspaceProvider: "figma",
843
873
  },
844
874
  credentialKeys: ["FIGMA_ACCESS_TOKEN"],
845
875
  docsUrls: [
@@ -1042,6 +1072,7 @@ const PROVIDER_CONFIGS: Record<ProviderApiId, ProviderApiConfig> = {
1042
1072
  type: "oauth-bearer",
1043
1073
  oauthProvider: "google",
1044
1074
  tokenLabel: "Google OAuth token",
1075
+ workspaceProvider: "google_drive",
1045
1076
  },
1046
1077
  credentialKeys: ["GOOGLE_OAUTH_ACCOUNT"],
1047
1078
  docsUrls: ["https://developers.google.com/drive/api/reference/rest/v3"],
@@ -1056,6 +1087,35 @@ const PROVIDER_CONFIGS: Record<ProviderApiId, ProviderApiConfig> = {
1056
1087
  "Uses the current user's stored Google OAuth account. Pass accountId when the user has multiple Google accounts connected.",
1057
1088
  ],
1058
1089
  },
1090
+ google_slides: {
1091
+ id: "google_slides",
1092
+ label: "Google Slides API",
1093
+ defaultBaseUrl: "https://slides.googleapis.com/v1",
1094
+ auth: {
1095
+ type: "oauth-bearer",
1096
+ oauthProvider: "google",
1097
+ tokenLabel: "Google OAuth token",
1098
+ workspaceProvider: "google_drive",
1099
+ },
1100
+ credentialKeys: ["GOOGLE_OAUTH_ACCOUNT"],
1101
+ docsUrls: [
1102
+ "https://developers.google.com/workspace/slides/api/reference/rest",
1103
+ ],
1104
+ specUrls: ["https://slides.googleapis.com/$discovery/rest?version=v1"],
1105
+ allowedHostSuffixes: ["googleapis.com"],
1106
+ templateUses: ["brain", "content", "slides", "dispatch"],
1107
+ examples: [
1108
+ {
1109
+ label: "Get presentation with slides and speaker notes",
1110
+ method: "GET",
1111
+ path: "/presentations/{presentationId}",
1112
+ },
1113
+ ],
1114
+ notes: [
1115
+ "Creative context imports use the non-sensitive drive.file scope. A user must choose each presentation through Google Picker before the Slides API can read it; unrestricted Drive-wide discovery is intentionally unavailable.",
1116
+ "Uses the current user's stored Google OAuth account. Pass accountId when the user has multiple Google accounts connected.",
1117
+ ],
1118
+ },
1059
1119
  granola: {
1060
1120
  id: "granola",
1061
1121
  label: "Granola Public API",
@@ -1190,13 +1250,15 @@ const PROVIDER_CONFIGS: Record<ProviderApiId, ProviderApiConfig> = {
1190
1250
  label: "Notion",
1191
1251
  defaultBaseUrl: "https://api.notion.com/v1",
1192
1252
  auth: {
1193
- type: "bearer",
1194
- keys: ["NOTION_API_KEY"],
1253
+ type: "oauth-bearer-or-bearer-key",
1254
+ oauthProvider: "notion",
1255
+ tokenLabel: "Notion OAuth token",
1256
+ key: "NOTION_API_KEY",
1195
1257
  workspaceProvider: "notion",
1196
1258
  },
1197
1259
  credentialKeys: ["NOTION_API_KEY"],
1198
1260
  docsUrls: ["https://developers.notion.com/reference/intro"],
1199
- defaultHeaders: { "Notion-Version": "2022-06-28" },
1261
+ defaultHeaders: { "Notion-Version": "2026-03-11" },
1200
1262
  templateUses: ["analytics", "brain", "content", "dispatch"],
1201
1263
  examples: [{ label: "Search", method: "POST", path: "/search", body: {} }],
1202
1264
  },
@@ -1748,6 +1810,55 @@ export async function executeProviderApiRequest(
1748
1810
  };
1749
1811
  }
1750
1812
 
1813
+ /**
1814
+ * Resolve a provider OAuth token for a trusted server-side UI bridge such as
1815
+ * Google Picker. Callers must keep the result out of agent, MCP, A2A, logs,
1816
+ * persistence, and extension/tool surfaces.
1817
+ */
1818
+ export async function resolveProviderApiOAuthAccessToken(
1819
+ args: {
1820
+ provider: ProviderApiId;
1821
+ connectionId?: string | null;
1822
+ accountId?: string | null;
1823
+ },
1824
+ runtime: ProviderApiRuntimeOptions,
1825
+ ): Promise<ProviderApiOAuthAccessToken> {
1826
+ await assertProviderAllowedAsync(args.provider, runtime);
1827
+ const config = getProviderApiConfig(args.provider);
1828
+ const auth = config.auth;
1829
+ if (auth.type !== "oauth-bearer") {
1830
+ throw new Error(
1831
+ `Provider API ${args.provider} does not use a direct OAuth bearer token.`,
1832
+ );
1833
+ }
1834
+ const ctx = requireRuntimeCredentialContext(
1835
+ runtime,
1836
+ config.credentialKeys[0] ?? config.id,
1837
+ );
1838
+ const credential =
1839
+ auth.workspaceProvider && args.connectionId
1840
+ ? await resolveConnectionBoundOAuthBearerToken({
1841
+ auth,
1842
+ runtime,
1843
+ ctx,
1844
+ workspaceProvider: auth.workspaceProvider,
1845
+ connectionId: args.connectionId,
1846
+ accountId: args.accountId,
1847
+ })
1848
+ : await resolveOAuthBearerToken({
1849
+ auth,
1850
+ ctx,
1851
+ accountId: args.accountId,
1852
+ });
1853
+ return {
1854
+ accessToken: credential.value,
1855
+ accountId: credential.accountId ?? null,
1856
+ accountLabel: credential.accountLabel ?? null,
1857
+ connectionId: credential.connectionId ?? null,
1858
+ connectionLabel: credential.connectionLabel ?? null,
1859
+ };
1860
+ }
1861
+
1751
1862
  const GITHUB_REPO_FILES_DEFAULT_MAX = 1_000;
1752
1863
  const GITHUB_REPO_FILES_MAX = 10_000;
1753
1864
  const GITHUB_CODE_SEARCH_DEFAULT_PER_PAGE = 30;
@@ -2949,6 +3060,12 @@ function describeAuth(auth: ProviderApiAuthKind): string {
2949
3060
  if (auth.type === "api-key-header") return `api-key-header:${auth.header}`;
2950
3061
  if (auth.type === "google-service-account") return "google-service-account";
2951
3062
  if (auth.type === "oauth-bearer") return `oauth-bearer:${auth.oauthProvider}`;
3063
+ if (auth.type === "oauth-bearer-or-api-key-header") {
3064
+ return `oauth-bearer:${auth.oauthProvider}-or-api-key-header:${auth.header}`;
3065
+ }
3066
+ if (auth.type === "oauth-bearer-or-bearer-key") {
3067
+ return `oauth-bearer:${auth.oauthProvider}-or-bearer-key:${auth.key}`;
3068
+ }
2952
3069
  return "prometheus-basic-or-bearer";
2953
3070
  }
2954
3071
 
@@ -3234,10 +3351,86 @@ async function resolveAuth(
3234
3351
  if (auth.type === "oauth-bearer") {
3235
3352
  const oauthProvider =
3236
3353
  runtime.oauthProviderOverrides?.[config.id] ?? auth.oauthProvider;
3237
- const credential = await resolveOAuthBearerToken({
3238
- auth: { ...auth, oauthProvider },
3354
+ const credential =
3355
+ auth.workspaceProvider && args.connectionId
3356
+ ? await resolveConnectionBoundOAuthBearerToken({
3357
+ auth: { ...auth, oauthProvider },
3358
+ runtime,
3359
+ ctx,
3360
+ workspaceProvider: auth.workspaceProvider,
3361
+ connectionId: args.connectionId,
3362
+ accountId: args.accountId,
3363
+ })
3364
+ : await resolveOAuthBearerToken({
3365
+ auth: { ...auth, oauthProvider },
3366
+ ctx,
3367
+ accountId: args.accountId,
3368
+ });
3369
+ return {
3370
+ headers: { Authorization: `Bearer ${credential.value}` },
3371
+ credentialSources: [omitCredentialValue(credential)],
3372
+ secretValues: [credential.value],
3373
+ };
3374
+ }
3375
+ if (auth.type === "oauth-bearer-or-api-key-header") {
3376
+ if (args.connectionId) {
3377
+ const credential = await resolveConnectionBoundOAuthBearerToken({
3378
+ auth: {
3379
+ type: "oauth-bearer",
3380
+ oauthProvider: auth.oauthProvider,
3381
+ tokenLabel: auth.tokenLabel,
3382
+ },
3383
+ runtime,
3384
+ ctx,
3385
+ connectionId: args.connectionId,
3386
+ accountId: args.accountId,
3387
+ workspaceProvider: auth.workspaceProvider,
3388
+ });
3389
+ return {
3390
+ headers: { Authorization: `Bearer ${credential.value}` },
3391
+ credentialSources: [omitCredentialValue(credential)],
3392
+ secretValues: [credential.value],
3393
+ };
3394
+ }
3395
+ const credential = await resolveRequiredCredential({
3396
+ provider: config.id,
3397
+ workspaceProvider: auth.workspaceProvider,
3398
+ key: auth.key,
3399
+ ctx,
3400
+ runtime,
3401
+ });
3402
+ return {
3403
+ headers: { [auth.header]: credential.value },
3404
+ credentialSources: [omitCredentialValue(credential)],
3405
+ secretValues: [credential.value],
3406
+ };
3407
+ }
3408
+ if (auth.type === "oauth-bearer-or-bearer-key") {
3409
+ if (args.connectionId) {
3410
+ const credential = await resolveConnectionBoundOAuthBearerToken({
3411
+ auth: {
3412
+ type: "oauth-bearer",
3413
+ oauthProvider: auth.oauthProvider,
3414
+ tokenLabel: auth.tokenLabel,
3415
+ },
3416
+ runtime,
3417
+ ctx,
3418
+ connectionId: args.connectionId,
3419
+ accountId: args.accountId,
3420
+ workspaceProvider: auth.workspaceProvider,
3421
+ });
3422
+ return {
3423
+ headers: { Authorization: `Bearer ${credential.value}` },
3424
+ credentialSources: [omitCredentialValue(credential)],
3425
+ secretValues: [credential.value],
3426
+ };
3427
+ }
3428
+ const credential = await resolveRequiredCredential({
3429
+ provider: config.id,
3430
+ workspaceProvider: auth.workspaceProvider,
3431
+ key: auth.key,
3239
3432
  ctx,
3240
- accountId: args.accountId,
3433
+ runtime,
3241
3434
  });
3242
3435
  return {
3243
3436
  headers: { Authorization: `Bearer ${credential.value}` },
@@ -3491,6 +3684,53 @@ async function resolveOAuthBearerToken(options: {
3491
3684
  };
3492
3685
  }
3493
3686
 
3687
+ async function resolveConnectionBoundOAuthBearerToken(options: {
3688
+ auth: Extract<ProviderApiAuthKind, { type: "oauth-bearer" }>;
3689
+ runtime: ProviderApiRuntimeOptions;
3690
+ ctx: CredentialContext;
3691
+ workspaceProvider: string;
3692
+ connectionId?: string | null;
3693
+ accountId?: string | null;
3694
+ }): Promise<ProviderApiResolvedCredential> {
3695
+ const requestedConnectionId = options.connectionId?.trim();
3696
+ if (!requestedConnectionId) {
3697
+ throw new Error(
3698
+ `${options.auth.tokenLabel} requires an explicit workspace connection selection.`,
3699
+ );
3700
+ }
3701
+ const resolved = await resolveWorkspaceConnectionForApp({
3702
+ appId: options.runtime.appId,
3703
+ provider: options.workspaceProvider,
3704
+ connectionId: requestedConnectionId,
3705
+ requireConnected: true,
3706
+ });
3707
+ if (!resolved.available || !resolved.connection) {
3708
+ throw new Error(resolved.reason);
3709
+ }
3710
+ const connectionAccountId = resolved.connection.accountId?.trim();
3711
+ if (!connectionAccountId) {
3712
+ throw new Error(
3713
+ `${options.auth.tokenLabel} workspace connection ${requestedConnectionId} is missing its OAuth account binding.`,
3714
+ );
3715
+ }
3716
+ const requestedAccountId = options.accountId?.trim();
3717
+ if (requestedAccountId && requestedAccountId !== connectionAccountId) {
3718
+ throw new Error(
3719
+ `${options.auth.tokenLabel} account ${requestedAccountId} does not match workspace connection ${requestedConnectionId}.`,
3720
+ );
3721
+ }
3722
+ const credential = await resolveOAuthBearerToken({
3723
+ auth: options.auth,
3724
+ ctx: options.ctx,
3725
+ accountId: connectionAccountId,
3726
+ });
3727
+ return {
3728
+ ...credential,
3729
+ connectionId: resolved.connection.id,
3730
+ connectionLabel: resolved.connection.label,
3731
+ };
3732
+ }
3733
+
3494
3734
  async function getValidOAuthAccessToken(options: {
3495
3735
  oauthProvider: string;
3496
3736
  accountId: string;
@@ -3522,11 +3762,195 @@ async function getValidOAuthAccessToken(options: {
3522
3762
  ) {
3523
3763
  return refreshGoogleOAuthToken(options, refreshToken);
3524
3764
  }
3765
+ if (options.oauthProvider === "figma") {
3766
+ return refreshFigmaOAuthToken(options, refreshToken);
3767
+ }
3768
+ if (options.oauthProvider === "notion") {
3769
+ return refreshNotionOAuthToken(options, refreshToken);
3770
+ }
3525
3771
  throw new Error(
3526
3772
  `${options.oauthProvider} OAuth token is expired and automatic refresh is not configured for provider-api.`,
3527
3773
  );
3528
3774
  }
3529
3775
 
3776
+ async function refreshFigmaOAuthToken(
3777
+ options: {
3778
+ oauthProvider: string;
3779
+ accountId: string;
3780
+ ownerEmail: string;
3781
+ tokens: OAuthTokens;
3782
+ },
3783
+ refreshToken: string,
3784
+ ): Promise<string> {
3785
+ const [clientId, clientSecret] = await Promise.all([
3786
+ resolveSecret("FIGMA_CLIENT_ID"),
3787
+ resolveSecret("FIGMA_CLIENT_SECRET"),
3788
+ ]);
3789
+ if (!clientId || !clientSecret) {
3790
+ throw new Error(
3791
+ "FIGMA_CLIENT_ID and FIGMA_CLIENT_SECRET are required to refresh Figma OAuth tokens.",
3792
+ );
3793
+ }
3794
+ const { response, data } = await fetchBoundedOAuthRefreshJson<{
3795
+ access_token?: string;
3796
+ refresh_token?: string;
3797
+ expires_in?: number;
3798
+ token_type?: string;
3799
+ }>(
3800
+ "https://api.figma.com/v1/oauth/token",
3801
+ {
3802
+ method: "POST",
3803
+ headers: {
3804
+ Authorization: `Basic ${Buffer.from(`${clientId}:${clientSecret}`).toString("base64")}`,
3805
+ "Content-Type": "application/x-www-form-urlencoded",
3806
+ },
3807
+ body: new URLSearchParams({
3808
+ grant_type: "refresh_token",
3809
+ refresh_token: refreshToken,
3810
+ }),
3811
+ },
3812
+ "Figma",
3813
+ );
3814
+ if (!response.ok || !data.access_token) {
3815
+ throw new Error(`Figma OAuth refresh failed (${response.status}).`);
3816
+ }
3817
+ const updated = {
3818
+ ...options.tokens,
3819
+ access_token: data.access_token,
3820
+ token_type: data.token_type ?? "bearer",
3821
+ expiry_date: Date.now() + (data.expires_in ?? 3600) * 1_000,
3822
+ refresh_token: data.refresh_token ?? refreshToken,
3823
+ };
3824
+ await saveOAuthTokens(
3825
+ options.oauthProvider,
3826
+ options.accountId,
3827
+ updated as unknown as Record<string, unknown>,
3828
+ options.ownerEmail,
3829
+ );
3830
+ return data.access_token;
3831
+ }
3832
+
3833
+ async function refreshNotionOAuthToken(
3834
+ options: {
3835
+ oauthProvider: string;
3836
+ accountId: string;
3837
+ ownerEmail: string;
3838
+ tokens: OAuthTokens;
3839
+ },
3840
+ refreshToken: string,
3841
+ ): Promise<string> {
3842
+ const [clientId, clientSecret] = await Promise.all([
3843
+ resolveSecret("NOTION_CLIENT_ID"),
3844
+ resolveSecret("NOTION_CLIENT_SECRET"),
3845
+ ]);
3846
+ if (!clientId || !clientSecret) {
3847
+ throw new Error(
3848
+ "NOTION_CLIENT_ID and NOTION_CLIENT_SECRET are required to refresh Notion OAuth tokens.",
3849
+ );
3850
+ }
3851
+ const { response, data } = await fetchBoundedOAuthRefreshJson<{
3852
+ access_token?: string;
3853
+ refresh_token?: string;
3854
+ expires_in?: number;
3855
+ token_type?: string;
3856
+ }>(
3857
+ "https://api.notion.com/v1/oauth/token",
3858
+ {
3859
+ method: "POST",
3860
+ headers: {
3861
+ Authorization: `Basic ${Buffer.from(`${clientId}:${clientSecret}`).toString("base64")}`,
3862
+ "Content-Type": "application/json",
3863
+ "Notion-Version": "2026-03-11",
3864
+ },
3865
+ body: JSON.stringify({
3866
+ grant_type: "refresh_token",
3867
+ refresh_token: refreshToken,
3868
+ }),
3869
+ },
3870
+ "Notion",
3871
+ );
3872
+ if (!response.ok || !data.access_token) {
3873
+ throw new Error(`Notion OAuth refresh failed (${response.status}).`);
3874
+ }
3875
+ const updated = {
3876
+ ...options.tokens,
3877
+ access_token: data.access_token,
3878
+ token_type: data.token_type ?? "bearer",
3879
+ expiry_date: Date.now() + (data.expires_in ?? 3600) * 1_000,
3880
+ refresh_token: data.refresh_token ?? refreshToken,
3881
+ };
3882
+ await saveOAuthTokens(
3883
+ options.oauthProvider,
3884
+ options.accountId,
3885
+ updated as unknown as Record<string, unknown>,
3886
+ options.ownerEmail,
3887
+ );
3888
+ return data.access_token;
3889
+ }
3890
+
3891
+ const OAUTH_REFRESH_TIMEOUT_MS = 10_000;
3892
+ const OAUTH_REFRESH_MAX_BYTES = 256 * 1024;
3893
+
3894
+ async function fetchBoundedOAuthRefreshJson<T extends Record<string, unknown>>(
3895
+ url: string,
3896
+ init: RequestInit,
3897
+ providerLabel: string,
3898
+ ): Promise<{ response: Response; data: T }> {
3899
+ let response: Response;
3900
+ try {
3901
+ response = await fetch(url, {
3902
+ ...init,
3903
+ signal: AbortSignal.timeout(OAUTH_REFRESH_TIMEOUT_MS),
3904
+ });
3905
+ } catch {
3906
+ throw new Error(`${providerLabel} OAuth refresh request failed.`);
3907
+ }
3908
+ const declaredLength = Number(response.headers.get("content-length"));
3909
+ if (
3910
+ Number.isFinite(declaredLength) &&
3911
+ declaredLength > OAUTH_REFRESH_MAX_BYTES
3912
+ ) {
3913
+ throw new Error(
3914
+ `${providerLabel} OAuth refresh response exceeded the size limit.`,
3915
+ );
3916
+ }
3917
+ if (!response.body) return { response, data: {} as T };
3918
+ const reader = response.body.getReader();
3919
+ const chunks: Uint8Array[] = [];
3920
+ let length = 0;
3921
+ try {
3922
+ while (true) {
3923
+ const chunk = await reader.read();
3924
+ if (chunk.done) break;
3925
+ length += chunk.value.byteLength;
3926
+ if (length > OAUTH_REFRESH_MAX_BYTES) {
3927
+ await reader.cancel();
3928
+ break;
3929
+ }
3930
+ chunks.push(chunk.value);
3931
+ }
3932
+ } catch {
3933
+ throw new Error(`${providerLabel} OAuth refresh request failed.`);
3934
+ }
3935
+ if (length > OAUTH_REFRESH_MAX_BYTES) {
3936
+ throw new Error(
3937
+ `${providerLabel} OAuth refresh response exceeded the size limit.`,
3938
+ );
3939
+ }
3940
+ try {
3941
+ const parsed = JSON.parse(Buffer.concat(chunks).toString("utf8"));
3942
+ return {
3943
+ response,
3944
+ data:
3945
+ parsed && typeof parsed === "object" && !Array.isArray(parsed)
3946
+ ? (parsed as T)
3947
+ : ({} as T),
3948
+ };
3949
+ } catch {
3950
+ return { response, data: {} as T };
3951
+ }
3952
+ }
3953
+
3530
3954
  async function refreshGoogleOAuthToken(
3531
3955
  options: {
3532
3956
  oauthProvider: string;
@@ -3536,7 +3960,16 @@ async function refreshGoogleOAuthToken(
3536
3960
  },
3537
3961
  refreshToken: string,
3538
3962
  ): Promise<string> {
3539
- const credentialCandidates = resolveGoogleProviderCredentialCandidates();
3963
+ const [scopedClientId, scopedClientSecret] = await Promise.all([
3964
+ resolveSecret("GOOGLE_CLIENT_ID"),
3965
+ resolveSecret("GOOGLE_CLIENT_SECRET"),
3966
+ ]);
3967
+ const credentialCandidates = dedupeGoogleOAuthCredentials([
3968
+ ...(scopedClientId && scopedClientSecret
3969
+ ? [{ clientId: scopedClientId, clientSecret: scopedClientSecret }]
3970
+ : []),
3971
+ ...resolveGoogleProviderCredentialCandidates(),
3972
+ ]);
3540
3973
  if (!credentialCandidates.length) {
3541
3974
  throw new Error(
3542
3975
  "GOOGLE_CLIENT_ID/SECRET not set for Google OAuth refresh.",
@@ -3603,6 +4036,17 @@ async function refreshGoogleOAuthToken(
3603
4036
  return data.access_token;
3604
4037
  }
3605
4038
 
4039
+ function dedupeGoogleOAuthCredentials(
4040
+ candidates: Array<{ clientId: string; clientSecret: string }>,
4041
+ ): Array<{ clientId: string; clientSecret: string }> {
4042
+ const seen = new Set<string>();
4043
+ return candidates.filter((candidate) => {
4044
+ if (seen.has(candidate.clientId)) return false;
4045
+ seen.add(candidate.clientId);
4046
+ return true;
4047
+ });
4048
+ }
4049
+
3606
4050
  function normalizeMethod(
3607
4051
  method: ProviderApiMethod | undefined,
3608
4052
  ): ProviderApiMethod {
@@ -15,6 +15,8 @@ import {
15
15
  normalizeModelForEngine,
16
16
  } from "../../agent/engine/index.js";
17
17
  import type { ActionTool } from "../../agent/types.js";
18
+ import { resolveHostedDefaultModelExperiment } from "../../observability/hosted-model-experiment.js";
19
+ import { getRequestUserEmail } from "../../server/request-context.js";
18
20
  import { getSetting } from "../../settings/index.js";
19
21
 
20
22
  export const tool: ActionTool = {
@@ -89,6 +91,15 @@ export async function run(args: Record<string, string> = {}): Promise<string> {
89
91
  currentModelCandidate ?? currentEntry.defaultModel,
90
92
  )
91
93
  : (currentModelCandidate ?? DEFAULT_MODEL);
94
+ const hostedExperiment = currentEntry
95
+ ? resolveHostedDefaultModelExperiment({
96
+ userId: getRequestUserEmail(),
97
+ engineName: currentEntry.name,
98
+ isDefaultModelSelection: currentModelCandidate == null,
99
+ supportedModels: currentEntry.supportedModels,
100
+ })
101
+ : null;
102
+ const effectiveCurrentModel = hostedExperiment?.model ?? currentModel;
92
103
  const result = {
93
104
  engines: engines.map((e) => ({
94
105
  name: e.name,
@@ -105,7 +116,13 @@ export async function run(args: Record<string, string> = {}): Promise<string> {
105
116
  ? null
106
117
  : {
107
118
  engine: currentEngineName,
108
- model: currentModel,
119
+ model: effectiveCurrentModel,
120
+ ...(hostedExperiment
121
+ ? {
122
+ modelSelectionSource: "experiment",
123
+ experimentAssignments: [hostedExperiment.assignment],
124
+ }
125
+ : {}),
109
126
  },
110
127
  };
111
128