@agent-native/core 0.99.3 → 0.100.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/corpus/README.md +2 -2
- package/corpus/core/CHANGELOG.md +21 -0
- package/corpus/core/docs/content/agent-surfaces.mdx +43 -0
- package/corpus/core/docs/content/external-agents.mdx +11 -0
- package/corpus/core/docs/content/locales/ar-SA/agent-surfaces.mdx +30 -0
- package/corpus/core/docs/content/locales/ar-SA/external-agents.mdx +9 -0
- package/corpus/core/docs/content/locales/de-DE/agent-surfaces.mdx +34 -0
- package/corpus/core/docs/content/locales/de-DE/external-agents.mdx +10 -0
- package/corpus/core/docs/content/locales/es-ES/agent-surfaces.mdx +34 -0
- package/corpus/core/docs/content/locales/es-ES/external-agents.mdx +10 -0
- package/corpus/core/docs/content/locales/fr-FR/agent-surfaces.mdx +34 -0
- package/corpus/core/docs/content/locales/fr-FR/external-agents.mdx +11 -0
- package/corpus/core/docs/content/locales/hi-IN/agent-surfaces.mdx +31 -0
- package/corpus/core/docs/content/locales/hi-IN/external-agents.mdx +9 -0
- package/corpus/core/docs/content/locales/ja-JP/agent-surfaces.mdx +32 -0
- package/corpus/core/docs/content/locales/ja-JP/external-agents.mdx +10 -0
- package/corpus/core/docs/content/locales/ko-KR/agent-surfaces.mdx +32 -0
- package/corpus/core/docs/content/locales/ko-KR/external-agents.mdx +9 -0
- package/corpus/core/docs/content/locales/pt-BR/agent-surfaces.mdx +33 -0
- package/corpus/core/docs/content/locales/pt-BR/external-agents.mdx +10 -0
- package/corpus/core/docs/content/locales/zh-CN/agent-surfaces.mdx +29 -0
- package/corpus/core/docs/content/locales/zh-CN/external-agents.mdx +8 -0
- package/corpus/core/docs/content/locales/zh-TW/agent-surfaces.mdx +29 -0
- package/corpus/core/docs/content/locales/zh-TW/external-agents.mdx +8 -0
- package/corpus/core/package.json +1 -1
- package/corpus/core/src/agent/context-xray/actions/context-evict.ts +11 -0
- package/corpus/core/src/agent/context-xray/actions/context-pin.ts +11 -0
- package/corpus/core/src/agent/context-xray/actions/context-preview-get.ts +134 -0
- package/corpus/core/src/agent/context-xray/actions/context-restore.ts +11 -0
- package/corpus/core/src/agent/context-xray/actions/errors.ts +20 -0
- package/corpus/core/src/agent/context-xray/manifest.ts +106 -7
- package/corpus/core/src/agent/engine/context-directives-transform.ts +5 -1
- package/corpus/core/src/agent/production-agent.ts +100 -38
- package/corpus/core/src/agent/run-loop-with-resume.ts +7 -2
- package/corpus/core/src/client/AgentPanel.tsx +35 -8
- package/corpus/core/src/client/agent-page/AgentContextTab.tsx +501 -0
- package/corpus/core/src/client/agent-page/AgentJobsTab.tsx +370 -0
- package/corpus/core/src/client/agent-page/AgentTabsPage.tsx +1084 -0
- package/corpus/core/src/client/agent-page/types.ts +18 -0
- package/corpus/core/src/client/agent-page/use-jobs.ts +150 -0
- package/corpus/core/src/client/context-xray/ContextMeter.tsx +22 -5
- package/corpus/core/src/client/context-xray/ContextTreemap.tsx +16 -1
- package/corpus/core/src/client/context-xray/ContextXRayPanel.tsx +168 -3
- package/corpus/core/src/client/context-xray/format.ts +6 -0
- package/corpus/core/src/client/index.ts +6 -0
- package/corpus/core/src/client/resources/ResourcesPanel.tsx +51 -23
- package/corpus/core/src/client/settings/AutomationsSection.tsx +407 -387
- package/corpus/core/src/jobs/actions/list-recurring-jobs.ts +105 -0
- package/corpus/core/src/jobs/actions/manage-recurring-job.ts +85 -0
- package/corpus/core/src/jobs/tools.ts +1 -1
- package/corpus/core/src/localization/default-messages.ts +110 -0
- package/corpus/core/src/mcp/build-server.ts +1 -0
- package/corpus/core/src/mcp/connect-route.ts +62 -65
- package/corpus/core/src/server/action-discovery.ts +23 -0
- package/corpus/core/src/server/agent-chat/prompt-resources.ts +174 -2
- package/corpus/core/src/server/agent-chat-plugin.ts +175 -2
- package/corpus/core/src/server/auth.ts +1 -7
- package/corpus/core/src/server/google-oauth.ts +1 -7
- package/corpus/core/src/server/workspace-oauth.ts +31 -0
- package/corpus/core/src/shared/context-xray.ts +84 -1
- package/corpus/core/src/shared/mcp-connect-content.ts +130 -0
- package/corpus/core/src/templates/default/app/routes/_index.tsx +11 -0
- package/corpus/core/src/templates/default/app/routes/agent.tsx +33 -0
- package/corpus/core/src/templates/workspace-core/.agents/skills/agent-native-toolkit/SKILL.md +6 -0
- package/corpus/core/src/templates/workspace-core/.agents/skills/agent-page/SKILL.md +59 -0
- package/corpus/core/src/templates/workspace-core/.agents/skills/context-xray/SKILL.md +25 -0
- package/corpus/core/src/templates/workspace-core/.agents/skills/external-agents/SKILL.md +7 -0
- package/corpus/core/src/templates/workspace-core/.agents/skills/recurring-jobs/SKILL.md +9 -0
- package/corpus/core/src/triggers/actions/list-automations.ts +99 -0
- package/corpus/core/src/triggers/actions/manage-automation.ts +78 -0
- package/corpus/templates/analytics/actions/data-source-status.ts +33 -15
- package/corpus/templates/analytics/actions/query-agent-native-analytics.ts +1 -1
- package/corpus/templates/analytics/app/components/dashboard/SqlChart.tsx +149 -24
- package/corpus/templates/analytics/app/components/layout/CommandPalette.tsx +17 -0
- package/corpus/templates/analytics/app/components/layout/Header.tsx +1 -0
- package/corpus/templates/analytics/app/components/layout/Layout.tsx +1 -0
- package/corpus/templates/analytics/app/components/layout/Sidebar.tsx +8 -0
- package/corpus/templates/analytics/app/i18n/zh-TW.ts +1 -0
- package/corpus/templates/analytics/app/i18n-data.ts +1 -0
- package/corpus/templates/analytics/app/routes/agent.tsx +5 -0
- package/corpus/templates/analytics/changelog/2026-07-13-a-full-agent-page-now-brings-context-files-connections-jobs-.md +6 -0
- package/corpus/templates/analytics/changelog/2026-07-13-analytics-answers-can-use-built-in-first-party-event-data.md +6 -0
- package/corpus/templates/analytics/changelog/2026-07-13-chart-legends-can-filter-to-one-series-or-hide-a-series-on-h.md +6 -0
- package/corpus/templates/analytics/changelog/2026-07-13-gpt-5-6-luna-answers-now-recover-normally-instead-of-showing.md +6 -0
- package/corpus/templates/analytics/server/plugins/agent-chat.ts +11 -2
- package/corpus/templates/assets/app/components/layout/Header.tsx +1 -0
- package/corpus/templates/assets/app/components/layout/Layout.tsx +1 -0
- package/corpus/templates/assets/app/components/layout/Sidebar.tsx +2 -0
- package/corpus/templates/assets/app/routes/agent.tsx +5 -0
- package/corpus/templates/assets/changelog/2026-07-13-a-full-agent-page-now-brings-context-files-connections-jobs-.md +6 -0
- package/corpus/templates/brain/app/components/layout/Layout.tsx +1 -0
- package/corpus/templates/brain/app/components/layout/Sidebar.tsx +4 -1
- package/corpus/templates/brain/app/lib/brain.ts +11 -0
- package/corpus/templates/brain/app/root.tsx +15 -1
- package/corpus/templates/brain/app/routes/agent.tsx +11 -0
- package/corpus/templates/brain/changelog/2026-07-13-a-full-agent-page-now-brings-context-files-connections-jobs-.md +6 -0
- package/corpus/templates/calendar/AGENTS.md +9 -0
- package/corpus/templates/calendar/actions/list-events.ts +659 -44
- package/corpus/templates/calendar/app/components/layout/AppLayout.tsx +1 -0
- package/corpus/templates/calendar/app/components/layout/Sidebar.tsx +2 -0
- package/corpus/templates/calendar/app/root.tsx +17 -1
- package/corpus/templates/calendar/app/routes/_app.agent.tsx +25 -0
- package/corpus/templates/calendar/changelog/2026-07-13-a-full-agent-page-now-brings-context-files-connections-jobs-.md +6 -0
- package/corpus/templates/calendar/changelog/2026-07-13-calendar-inventory-reads-report-source-coverage.md +6 -0
- package/corpus/templates/calendar/server/lib/calendar-connector-catalog.ts +8 -0
- package/corpus/templates/calendar/server/lib/google-calendar.ts +173 -51
- package/corpus/templates/calendar/server/lib/ical-fetcher.ts +13 -2
- package/corpus/templates/calendar/server/plugins/agent-chat.ts +5 -3
- package/corpus/templates/calendar/shared/api.ts +2 -0
- package/corpus/templates/chat/app/components/layout/Header.tsx +1 -0
- package/corpus/templates/chat/app/components/layout/Layout.tsx +1 -0
- package/corpus/templates/chat/app/components/layout/Sidebar.tsx +7 -0
- package/corpus/templates/chat/app/hooks/use-navigation-state.ts +3 -0
- package/corpus/templates/chat/app/root.tsx +24 -2
- package/corpus/templates/chat/app/routes/agent.tsx +15 -0
- package/corpus/templates/chat/changelog/2026-07-13-a-full-agent-page-now-brings-context-files-connections-jobs-.md +6 -0
- package/corpus/templates/clips/app/components/library/library-layout.tsx +8 -0
- package/corpus/templates/clips/app/i18n/ar-SA.ts +2 -0
- package/corpus/templates/clips/app/i18n/de-DE.ts +2 -0
- package/corpus/templates/clips/app/i18n/en-US.ts +2 -0
- package/corpus/templates/clips/app/i18n/es-ES.ts +2 -0
- package/corpus/templates/clips/app/i18n/fr-FR.ts +2 -0
- package/corpus/templates/clips/app/i18n/hi-IN.ts +2 -0
- package/corpus/templates/clips/app/i18n/ja-JP.ts +2 -0
- package/corpus/templates/clips/app/i18n/ko-KR.ts +2 -0
- package/corpus/templates/clips/app/i18n/pt-BR.ts +2 -0
- package/corpus/templates/clips/app/i18n/zh-CN.ts +2 -0
- package/corpus/templates/clips/app/i18n/zh-TW.ts +2 -0
- package/corpus/templates/clips/app/root.tsx +7 -1
- package/corpus/templates/clips/app/routes/_app.agent.tsx +15 -0
- package/corpus/templates/clips/changelog/2026-07-13-new-agent-page-see-and-manage-your-agent-s-context-files-con.md +6 -0
- package/corpus/templates/content/app/components/layout/Layout.tsx +1 -0
- package/corpus/templates/content/app/components/sidebar/DocumentSidebar.tsx +36 -0
- package/corpus/templates/content/app/i18n/zh-TW.ts +2 -0
- package/corpus/templates/content/app/i18n-data.ts +44 -6
- package/corpus/templates/content/app/root.tsx +8 -0
- package/corpus/templates/content/app/routes/_app.agent.tsx +15 -0
- package/corpus/templates/content/changelog/2026-07-13-new-agent-page-see-and-manage-your-agent-s-context-files-con.md +6 -0
- package/corpus/templates/design/app/components/layout/Layout.tsx +1 -0
- package/corpus/templates/design/app/components/layout/Sidebar.tsx +2 -0
- package/corpus/templates/design/app/i18n/zh-TW.ts +2 -0
- package/corpus/templates/design/app/i18n-data.ts +20 -0
- package/corpus/templates/design/app/root.tsx +7 -1
- package/corpus/templates/design/app/routes/agent.tsx +15 -0
- package/corpus/templates/design/changelog/2026-07-13-new-agent-page-see-and-manage-your-agent-s-context-files-con.md +6 -0
- package/corpus/templates/dispatch/app/dispatch-extensions.tsx +10 -1
- package/corpus/templates/dispatch/app/i18n/zh-TW.ts +2 -0
- package/corpus/templates/dispatch/app/i18n-data.ts +20 -0
- package/corpus/templates/dispatch/app/root.tsx +7 -2
- package/corpus/templates/dispatch/app/routes/agent.tsx +18 -0
- package/corpus/templates/dispatch/changelog/2026-07-13-new-agent-page-see-and-manage-your-agent-s-context-files-con.md +6 -0
- package/corpus/templates/forms/app/components/layout/Layout.tsx +1 -0
- package/corpus/templates/forms/app/components/layout/Sidebar.tsx +35 -0
- package/corpus/templates/forms/app/i18n/ar-SA.ts +2 -0
- package/corpus/templates/forms/app/i18n/de-DE.ts +2 -0
- package/corpus/templates/forms/app/i18n/en-US.ts +2 -0
- package/corpus/templates/forms/app/i18n/es-ES.ts +2 -0
- package/corpus/templates/forms/app/i18n/fr-FR.ts +2 -0
- package/corpus/templates/forms/app/i18n/hi-IN.ts +2 -0
- package/corpus/templates/forms/app/i18n/ja-JP.ts +2 -0
- package/corpus/templates/forms/app/i18n/ko-KR.ts +2 -0
- package/corpus/templates/forms/app/i18n/pt-BR.ts +2 -0
- package/corpus/templates/forms/app/i18n/zh-CN.ts +2 -0
- package/corpus/templates/forms/app/i18n/zh-TW.ts +2 -0
- package/corpus/templates/forms/app/root.tsx +6 -1
- package/corpus/templates/forms/app/routes/_app.agent.tsx +15 -0
- package/corpus/templates/forms/changelog/2026-07-13-new-agent-page-see-and-manage-your-agent-s-context-files-con.md +6 -0
- package/corpus/templates/macros/app/components/layout/AppLayout.tsx +14 -2
- package/corpus/templates/macros/app/components/layout/Header.tsx +1 -0
- package/corpus/templates/macros/app/root.tsx +17 -2
- package/corpus/templates/macros/app/routes/agent.tsx +15 -0
- package/corpus/templates/macros/changelog/2026-07-13-new-agent-page-see-and-manage-your-agent-s-context-files-con.md +6 -0
- package/corpus/templates/mail/AGENTS.md +12 -0
- package/corpus/templates/mail/actions/list-emails.ts +486 -4
- package/corpus/templates/mail/app/components/layout/AppLayout.tsx +42 -0
- package/corpus/templates/mail/app/components/layout/CommandPalette.tsx +6 -0
- package/corpus/templates/mail/app/routes/agent.tsx +15 -0
- package/corpus/templates/mail/changelog/2026-07-13-coverage-aware-connected-inbox-inventory.md +6 -0
- package/corpus/templates/mail/changelog/2026-07-13-new-agent-page-see-and-manage-your-agent-s-context-files-con.md +6 -0
- package/corpus/templates/mail/server/db/schema.ts +17 -0
- package/corpus/templates/mail/server/lib/google-auth.ts +33 -5
- package/corpus/templates/mail/server/lib/inventory-cursor.ts +406 -0
- package/corpus/templates/mail/server/lib/list-inbox-emails.ts +21 -2
- package/corpus/templates/mail/server/lib/mail-connector-catalog.ts +8 -0
- package/corpus/templates/mail/server/plugins/agent-chat.ts +4 -9
- package/corpus/templates/mail/server/plugins/db.ts +20 -0
- package/corpus/templates/plan/app/components/layout/Header.tsx +1 -0
- package/corpus/templates/plan/app/components/layout/Layout.tsx +1 -0
- package/corpus/templates/plan/app/components/layout/Sidebar.tsx +2 -0
- package/corpus/templates/plan/app/root.tsx +8 -0
- package/corpus/templates/plan/app/routes/agent.tsx +15 -0
- package/corpus/templates/plan/changelog/2026-07-13-new-agent-page-see-and-manage-your-agent-s-context-files-con.md +6 -0
- package/corpus/templates/slides/app/components/layout/Header.tsx +1 -0
- package/corpus/templates/slides/app/components/layout/Layout.tsx +1 -0
- package/corpus/templates/slides/app/components/layout/Sidebar.tsx +2 -0
- package/corpus/templates/slides/app/root.tsx +10 -1
- package/corpus/templates/slides/app/routes/agent.tsx +15 -0
- package/corpus/templates/slides/changelog/2026-07-13-new-agent-page-see-and-manage-your-agent-s-context-files-con.md +6 -0
- package/dist/agent/context-xray/actions/context-evict.js +5 -2
- package/dist/agent/context-xray/actions/context-evict.js.map +1 -1
- package/dist/agent/context-xray/actions/context-pin.js +5 -2
- package/dist/agent/context-xray/actions/context-pin.js.map +1 -1
- package/dist/agent/context-xray/actions/context-preview-get.d.ts +17 -0
- package/dist/agent/context-xray/actions/context-preview-get.d.ts.map +1 -0
- package/dist/agent/context-xray/actions/context-preview-get.js +94 -0
- package/dist/agent/context-xray/actions/context-preview-get.js.map +1 -0
- package/dist/agent/context-xray/actions/context-restore.js +5 -2
- package/dist/agent/context-xray/actions/context-restore.js.map +1 -1
- package/dist/agent/context-xray/actions/errors.d.ts +3 -0
- package/dist/agent/context-xray/actions/errors.d.ts.map +1 -1
- package/dist/agent/context-xray/actions/errors.js +6 -0
- package/dist/agent/context-xray/actions/errors.js.map +1 -1
- package/dist/agent/context-xray/manifest.d.ts +18 -1
- package/dist/agent/context-xray/manifest.d.ts.map +1 -1
- package/dist/agent/context-xray/manifest.js +68 -6
- package/dist/agent/context-xray/manifest.js.map +1 -1
- package/dist/agent/engine/context-directives-transform.d.ts +2 -0
- package/dist/agent/engine/context-directives-transform.d.ts.map +1 -1
- package/dist/agent/engine/context-directives-transform.js +2 -1
- package/dist/agent/engine/context-directives-transform.js.map +1 -1
- package/dist/agent/production-agent.d.ts +15 -0
- package/dist/agent/production-agent.d.ts.map +1 -1
- package/dist/agent/production-agent.js +74 -36
- package/dist/agent/production-agent.js.map +1 -1
- package/dist/agent/run-loop-with-resume.d.ts.map +1 -1
- package/dist/agent/run-loop-with-resume.js +6 -3
- package/dist/agent/run-loop-with-resume.js.map +1 -1
- package/dist/client/AgentPanel.d.ts +5 -1
- package/dist/client/AgentPanel.d.ts.map +1 -1
- package/dist/client/AgentPanel.js +9 -11
- package/dist/client/AgentPanel.js.map +1 -1
- package/dist/client/agent-page/AgentContextTab.d.ts +5 -0
- package/dist/client/agent-page/AgentContextTab.d.ts.map +1 -0
- package/dist/client/agent-page/AgentContextTab.js +202 -0
- package/dist/client/agent-page/AgentContextTab.js.map +1 -0
- package/dist/client/agent-page/AgentJobsTab.d.ts +3 -0
- package/dist/client/agent-page/AgentJobsTab.d.ts.map +1 -0
- package/dist/client/agent-page/AgentJobsTab.js +98 -0
- package/dist/client/agent-page/AgentJobsTab.js.map +1 -0
- package/dist/client/agent-page/AgentTabsPage.d.ts +20 -0
- package/dist/client/agent-page/AgentTabsPage.d.ts.map +1 -0
- package/dist/client/agent-page/AgentTabsPage.js +420 -0
- package/dist/client/agent-page/AgentTabsPage.js.map +1 -0
- package/dist/client/agent-page/types.d.ts +17 -0
- package/dist/client/agent-page/types.d.ts.map +1 -0
- package/dist/client/agent-page/types.js +9 -0
- package/dist/client/agent-page/types.js.map +1 -0
- package/dist/client/agent-page/use-jobs.d.ts +61 -0
- package/dist/client/agent-page/use-jobs.d.ts.map +1 -0
- package/dist/client/agent-page/use-jobs.js +71 -0
- package/dist/client/agent-page/use-jobs.js.map +1 -0
- package/dist/client/context-xray/ContextMeter.d.ts +3 -1
- package/dist/client/context-xray/ContextMeter.d.ts.map +1 -1
- package/dist/client/context-xray/ContextMeter.js +14 -5
- package/dist/client/context-xray/ContextMeter.js.map +1 -1
- package/dist/client/context-xray/ContextTreemap.d.ts +3 -2
- package/dist/client/context-xray/ContextTreemap.d.ts.map +1 -1
- package/dist/client/context-xray/ContextTreemap.js +9 -1
- package/dist/client/context-xray/ContextTreemap.js.map +1 -1
- package/dist/client/context-xray/ContextXRayPanel.d.ts.map +1 -1
- package/dist/client/context-xray/ContextXRayPanel.js +95 -20
- package/dist/client/context-xray/ContextXRayPanel.js.map +1 -1
- package/dist/client/context-xray/format.d.ts.map +1 -1
- package/dist/client/context-xray/format.js +12 -0
- package/dist/client/context-xray/format.js.map +1 -1
- package/dist/client/index.d.ts +3 -0
- package/dist/client/index.d.ts.map +1 -1
- package/dist/client/index.js +1 -0
- package/dist/client/index.js.map +1 -1
- package/dist/client/resources/ResourcesPanel.d.ts +9 -1
- package/dist/client/resources/ResourcesPanel.d.ts.map +1 -1
- package/dist/client/resources/ResourcesPanel.js +26 -10
- package/dist/client/resources/ResourcesPanel.js.map +1 -1
- package/dist/client/settings/AutomationsSection.d.ts +9 -0
- package/dist/client/settings/AutomationsSection.d.ts.map +1 -1
- package/dist/client/settings/AutomationsSection.js +128 -147
- package/dist/client/settings/AutomationsSection.js.map +1 -1
- package/dist/collab/routes.d.ts +1 -1
- package/dist/collab/struct-routes.d.ts +1 -1
- package/dist/file-upload/actions/upload-image.d.ts +1 -1
- package/dist/jobs/actions/list-recurring-jobs.d.ts +21 -0
- package/dist/jobs/actions/list-recurring-jobs.d.ts.map +1 -0
- package/dist/jobs/actions/list-recurring-jobs.js +74 -0
- package/dist/jobs/actions/list-recurring-jobs.js.map +1 -0
- package/dist/jobs/actions/manage-recurring-job.d.ts +18 -0
- package/dist/jobs/actions/manage-recurring-job.d.ts.map +1 -0
- package/dist/jobs/actions/manage-recurring-job.js +68 -0
- package/dist/jobs/actions/manage-recurring-job.js.map +1 -0
- package/dist/jobs/tools.d.ts +13 -0
- package/dist/jobs/tools.d.ts.map +1 -1
- package/dist/jobs/tools.js +1 -1
- package/dist/jobs/tools.js.map +1 -1
- package/dist/localization/default-messages.d.ts +96 -0
- package/dist/localization/default-messages.d.ts.map +1 -1
- package/dist/localization/default-messages.js +96 -0
- package/dist/localization/default-messages.js.map +1 -1
- package/dist/mcp/build-server.d.ts.map +1 -1
- package/dist/mcp/build-server.js +1 -0
- package/dist/mcp/build-server.js.map +1 -1
- package/dist/mcp/connect-route.d.ts.map +1 -1
- package/dist/mcp/connect-route.js +44 -59
- package/dist/mcp/connect-route.js.map +1 -1
- package/dist/notifications/routes.d.ts +1 -1
- package/dist/observability/routes.d.ts +5 -5
- package/dist/progress/routes.d.ts +1 -1
- package/dist/resources/handlers.d.ts +3 -3
- package/dist/secrets/routes.d.ts +9 -9
- package/dist/server/action-discovery.d.ts.map +1 -1
- package/dist/server/action-discovery.js +23 -0
- package/dist/server/action-discovery.js.map +1 -1
- package/dist/server/agent-chat/prompt-resources.d.ts +14 -0
- package/dist/server/agent-chat/prompt-resources.d.ts.map +1 -1
- package/dist/server/agent-chat/prompt-resources.js +139 -2
- package/dist/server/agent-chat/prompt-resources.js.map +1 -1
- package/dist/server/agent-chat-plugin.d.ts +1 -0
- package/dist/server/agent-chat-plugin.d.ts.map +1 -1
- package/dist/server/agent-chat-plugin.js +136 -3
- package/dist/server/agent-chat-plugin.js.map +1 -1
- package/dist/server/agent-engine-api-key-route.d.ts +1 -1
- package/dist/server/auth.d.ts.map +1 -1
- package/dist/server/auth.js +1 -4
- package/dist/server/auth.js.map +1 -1
- package/dist/server/google-oauth.d.ts.map +1 -1
- package/dist/server/google-oauth.js +1 -4
- package/dist/server/google-oauth.js.map +1 -1
- package/dist/server/workspace-oauth.d.ts +11 -0
- package/dist/server/workspace-oauth.d.ts.map +1 -0
- package/dist/server/workspace-oauth.js +25 -0
- package/dist/server/workspace-oauth.js.map +1 -0
- package/dist/shared/context-xray.d.ts +45 -1
- package/dist/shared/context-xray.d.ts.map +1 -1
- package/dist/shared/context-xray.js +12 -0
- package/dist/shared/context-xray.js.map +1 -1
- package/dist/shared/mcp-connect-content.d.ts +37 -0
- package/dist/shared/mcp-connect-content.d.ts.map +1 -0
- package/dist/shared/mcp-connect-content.js +92 -0
- package/dist/shared/mcp-connect-content.js.map +1 -0
- package/dist/templates/default/app/routes/_index.tsx +11 -0
- package/dist/templates/default/app/routes/agent.tsx +33 -0
- package/dist/templates/workspace-core/.agents/skills/agent-native-toolkit/SKILL.md +6 -0
- package/dist/templates/workspace-core/.agents/skills/agent-page/SKILL.md +59 -0
- package/dist/templates/workspace-core/.agents/skills/context-xray/SKILL.md +25 -0
- package/dist/templates/workspace-core/.agents/skills/external-agents/SKILL.md +7 -0
- package/dist/templates/workspace-core/.agents/skills/recurring-jobs/SKILL.md +9 -0
- package/dist/triggers/actions/list-automations.d.ts +24 -0
- package/dist/triggers/actions/list-automations.d.ts.map +1 -0
- package/dist/triggers/actions/list-automations.js +72 -0
- package/dist/triggers/actions/list-automations.js.map +1 -0
- package/dist/triggers/actions/manage-automation.d.ts +18 -0
- package/dist/triggers/actions/manage-automation.d.ts.map +1 -0
- package/dist/triggers/actions/manage-automation.js +60 -0
- package/dist/triggers/actions/manage-automation.js.map +1 -0
- package/docs/content/agent-surfaces.mdx +43 -0
- package/docs/content/external-agents.mdx +11 -0
- package/docs/content/locales/ar-SA/agent-surfaces.mdx +30 -0
- package/docs/content/locales/ar-SA/external-agents.mdx +9 -0
- package/docs/content/locales/de-DE/agent-surfaces.mdx +34 -0
- package/docs/content/locales/de-DE/external-agents.mdx +10 -0
- package/docs/content/locales/es-ES/agent-surfaces.mdx +34 -0
- package/docs/content/locales/es-ES/external-agents.mdx +10 -0
- package/docs/content/locales/fr-FR/agent-surfaces.mdx +34 -0
- package/docs/content/locales/fr-FR/external-agents.mdx +11 -0
- package/docs/content/locales/hi-IN/agent-surfaces.mdx +31 -0
- package/docs/content/locales/hi-IN/external-agents.mdx +9 -0
- package/docs/content/locales/ja-JP/agent-surfaces.mdx +32 -0
- package/docs/content/locales/ja-JP/external-agents.mdx +10 -0
- package/docs/content/locales/ko-KR/agent-surfaces.mdx +32 -0
- package/docs/content/locales/ko-KR/external-agents.mdx +9 -0
- package/docs/content/locales/pt-BR/agent-surfaces.mdx +33 -0
- package/docs/content/locales/pt-BR/external-agents.mdx +10 -0
- package/docs/content/locales/zh-CN/agent-surfaces.mdx +29 -0
- package/docs/content/locales/zh-CN/external-agents.mdx +8 -0
- package/docs/content/locales/zh-TW/agent-surfaces.mdx +29 -0
- package/docs/content/locales/zh-TW/external-agents.mdx +8 -0
- package/package.json +1 -1
- package/src/templates/default/app/routes/_index.tsx +11 -0
- package/src/templates/default/app/routes/agent.tsx +33 -0
- package/src/templates/workspace-core/.agents/skills/agent-native-toolkit/SKILL.md +6 -0
- package/src/templates/workspace-core/.agents/skills/agent-page/SKILL.md +59 -0
- package/src/templates/workspace-core/.agents/skills/context-xray/SKILL.md +25 -0
- package/src/templates/workspace-core/.agents/skills/external-agents/SKILL.md +7 -0
- package/src/templates/workspace-core/.agents/skills/recurring-jobs/SKILL.md +9 -0
|
@@ -1,129 +1,123 @@
|
|
|
1
|
-
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
2
|
-
import {
|
|
3
|
-
import {
|
|
1
|
+
import { Fragment as _Fragment, jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
2
|
+
import { Button } from "@agent-native/toolkit/ui/button";
|
|
3
|
+
import { IconBolt, IconClock, IconEye, IconLoader2, IconPlayerPause, IconPlayerPlay, IconPlus, IconTrash, } from "@tabler/icons-react";
|
|
4
|
+
import { useCallback, useState } from "react";
|
|
4
5
|
import { sendToAgentChat } from "../agent-chat.js";
|
|
6
|
+
import { useAutomations, useManageAutomation, } from "../agent-page/use-jobs.js";
|
|
5
7
|
import { agentNativePath } from "../api-path.js";
|
|
8
|
+
import { Dialog, DialogContent, DialogDescription, DialogFooter, DialogHeader, DialogTitle, } from "../components/ui/dialog.js";
|
|
6
9
|
import { Popover, PopoverContent, PopoverTrigger, } from "../components/ui/popover.js";
|
|
7
|
-
import { Tooltip, TooltipContent, TooltipTrigger, } from "../components/ui/tooltip.js";
|
|
8
10
|
import { PromptComposer } from "../composer/PromptComposer.js";
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
11
|
+
import { useFormatters, useT } from "../i18n.js";
|
|
12
|
+
export const AUTOMATION_CREATION_SCOPE = "personal";
|
|
13
|
+
export function automationCreationContext() {
|
|
14
|
+
return `The user wants to create a new ${AUTOMATION_CREATION_SCOPE} automation. Use manage-automations with action=define to create it. Ask clarifying questions if needed about what event to trigger on, conditions, and what actions to take.`;
|
|
15
|
+
}
|
|
16
|
+
export function AutomationsList({ scope = "user", compact = false, emptyMessage, }) {
|
|
17
|
+
const t = useT();
|
|
18
|
+
const { formatDate } = useFormatters();
|
|
19
|
+
const query = useAutomations(scope);
|
|
20
|
+
const mutation = useManageAutomation(scope);
|
|
21
|
+
const [deleteTarget, setDeleteTarget] = useState(null);
|
|
22
|
+
const [detailsTarget, setDetailsTarget] = useState(null);
|
|
23
|
+
const formatDateTime = (value) => {
|
|
24
|
+
if (!value || Number.isNaN(new Date(value).getTime()))
|
|
25
|
+
return null;
|
|
26
|
+
return formatDate(value, {
|
|
27
|
+
month: "short",
|
|
28
|
+
day: "numeric",
|
|
29
|
+
hour: "numeric",
|
|
30
|
+
minute: "2-digit",
|
|
31
|
+
});
|
|
32
|
+
};
|
|
33
|
+
if (query.isLoading) {
|
|
34
|
+
return (_jsxs("div", { className: "flex items-center gap-2 text-sm text-muted-foreground", "aria-busy": "true", children: [_jsx(IconLoader2, { className: "size-4 animate-spin" }), t("jobs.loading", { defaultValue: "Loading…" })] }));
|
|
35
|
+
}
|
|
36
|
+
if (query.error) {
|
|
37
|
+
return (_jsx("p", { className: "text-sm text-destructive", children: t("jobs.automationsLoadError", {
|
|
38
|
+
defaultValue: "Could not load automations.",
|
|
39
|
+
}) }));
|
|
32
40
|
}
|
|
33
|
-
|
|
41
|
+
const automations = query.data ?? [];
|
|
42
|
+
if (automations.length === 0) {
|
|
43
|
+
return (_jsx("p", { className: "text-sm text-muted-foreground", children: emptyMessage ??
|
|
44
|
+
t("jobs.automationsEmpty", {
|
|
45
|
+
defaultValue: "No automations yet. Ask the agent to set up an event-triggered or scheduled task.",
|
|
46
|
+
}) }));
|
|
47
|
+
}
|
|
48
|
+
return (_jsxs("div", { className: compact ? "space-y-2" : "space-y-3", children: [automations.map((automation) => {
|
|
49
|
+
const lastRun = formatDateTime(automation.lastRun);
|
|
50
|
+
const nextRun = formatDateTime(automation.nextRun);
|
|
51
|
+
const trigger = automation.triggerType === "event"
|
|
52
|
+
? t("jobs.automationEventTrigger", {
|
|
53
|
+
defaultValue: "On {{event}}",
|
|
54
|
+
event: automation.event ?? "event",
|
|
55
|
+
})
|
|
56
|
+
: (automation.scheduleDescription ??
|
|
57
|
+
automation.schedule ??
|
|
58
|
+
t("jobs.automationScheduleTrigger", {
|
|
59
|
+
defaultValue: "Scheduled task",
|
|
60
|
+
}));
|
|
61
|
+
return (_jsx("article", { className: "rounded-lg border border-border bg-card p-3", children: _jsxs("div", { className: "flex items-start gap-3", children: [_jsx("div", { className: "mt-0.5 text-muted-foreground", children: automation.triggerType === "event" ? (_jsx(IconBolt, { className: "size-4" })) : (_jsx(IconClock, { className: "size-4" })) }), _jsxs("div", { className: "min-w-0 flex-1", children: [_jsxs("div", { className: "flex flex-wrap items-center gap-2", children: [_jsx("h3", { className: "truncate text-sm font-medium text-foreground", children: automation.name.replace(/-/g, " ") }), _jsx("span", { className: automation.enabled
|
|
62
|
+
? "rounded-full bg-emerald-500/15 px-2 py-0.5 text-[10px] font-medium text-emerald-600 dark:text-emerald-400"
|
|
63
|
+
: "rounded-full bg-muted px-2 py-0.5 text-[10px] font-medium text-muted-foreground", children: automation.enabled
|
|
64
|
+
? t("jobs.enabled", { defaultValue: "Enabled" })
|
|
65
|
+
: t("jobs.disabled", { defaultValue: "Disabled" }) }), automation.lastStatus ? (_jsx("span", { className: "rounded-full bg-muted px-2 py-0.5 text-[10px] font-medium text-muted-foreground", children: automation.lastStatus })) : null] }), _jsx("p", { className: "mt-1 text-xs text-muted-foreground", children: trigger }), _jsx("p", { className: "mt-1 line-clamp-2 text-xs text-muted-foreground/80", children: automation.body }), lastRun || nextRun ? (_jsxs("div", { className: "mt-2 flex flex-wrap gap-x-4 gap-y-1 text-[11px] text-muted-foreground", children: [lastRun ? (_jsxs("span", { children: [t("jobs.lastRun", { defaultValue: "Last run" }), ":", " ", lastRun] })) : null, nextRun ? (_jsxs("span", { children: [t("jobs.nextRun", { defaultValue: "Next run" }), ":", " ", nextRun] })) : null] })) : null] }), _jsxs("div", { className: "flex shrink-0 items-center gap-1", children: [_jsxs(Button, { type: "button", variant: "ghost", size: "sm", className: "cursor-pointer px-2 text-xs", onClick: () => setDetailsTarget(automation), children: [_jsx(IconEye, { className: "size-3.5" }), t("jobs.details", { defaultValue: "Details" })] }), automation.canUpdate ? (_jsxs(_Fragment, { children: [_jsxs(Button, { type: "button", variant: "ghost", size: "sm", className: "cursor-pointer px-2 text-xs", disabled: mutation.isPending, onClick: () => mutation.mutate({
|
|
66
|
+
operation: "update",
|
|
67
|
+
name: automation.name,
|
|
68
|
+
scope: automation.scope,
|
|
69
|
+
enabled: !automation.enabled,
|
|
70
|
+
}), children: [automation.enabled ? (_jsx(IconPlayerPause, { className: "size-3.5" })) : (_jsx(IconPlayerPlay, { className: "size-3.5" })), automation.enabled
|
|
71
|
+
? t("jobs.pause", { defaultValue: "Pause" })
|
|
72
|
+
: t("jobs.resume", { defaultValue: "Resume" })] }), _jsx(Button, { type: "button", variant: "ghost", size: "icon", className: "size-8 cursor-pointer text-muted-foreground hover:text-destructive", "aria-label": t("jobs.delete", { defaultValue: "Delete" }), onClick: () => setDeleteTarget(automation), children: _jsx(IconTrash, { className: "size-3.5" }) })] })) : null] })] }) }, automation.id));
|
|
73
|
+
}), mutation.error ? (_jsx("p", { className: "text-sm text-destructive", children: mutation.error.message ||
|
|
74
|
+
t("jobs.automationUpdateError", {
|
|
75
|
+
defaultValue: "Could not update automation.",
|
|
76
|
+
}) })) : null, _jsx(Dialog, { open: deleteTarget !== null, onOpenChange: (open) => {
|
|
77
|
+
if (!open && !mutation.isPending)
|
|
78
|
+
setDeleteTarget(null);
|
|
79
|
+
}, children: _jsxs(DialogContent, { children: [_jsxs(DialogHeader, { children: [_jsx(DialogTitle, { children: t("jobs.deleteAutomationTitle", {
|
|
80
|
+
defaultValue: "Delete automation?",
|
|
81
|
+
}) }), _jsx(DialogDescription, { children: t("jobs.deleteAutomationDescription", {
|
|
82
|
+
defaultValue: "This permanently removes the automation and cannot be undone.",
|
|
83
|
+
}) })] }), _jsxs(DialogFooter, { children: [_jsx(Button, { type: "button", variant: "outline", className: "cursor-pointer", disabled: mutation.isPending, onClick: () => setDeleteTarget(null), children: t("jobs.cancel", { defaultValue: "Cancel" }) }), _jsxs(Button, { type: "button", variant: "destructive", className: "cursor-pointer", disabled: mutation.isPending, onClick: () => {
|
|
84
|
+
if (!deleteTarget)
|
|
85
|
+
return;
|
|
86
|
+
mutation.mutate({
|
|
87
|
+
operation: "delete",
|
|
88
|
+
name: deleteTarget.name,
|
|
89
|
+
scope: deleteTarget.scope,
|
|
90
|
+
}, { onSuccess: () => setDeleteTarget(null) });
|
|
91
|
+
}, children: [mutation.isPending ? (_jsx(IconLoader2, { className: "size-4 animate-spin" })) : null, t("jobs.delete", { defaultValue: "Delete" })] })] })] }) }), _jsx(Dialog, { open: detailsTarget !== null, onOpenChange: (open) => {
|
|
92
|
+
if (!open)
|
|
93
|
+
setDetailsTarget(null);
|
|
94
|
+
}, children: _jsxs(DialogContent, { className: "max-w-2xl", children: [_jsxs(DialogHeader, { children: [_jsx(DialogTitle, { children: detailsTarget?.name.replace(/-/g, " ") ??
|
|
95
|
+
t("jobs.automationDetails", {
|
|
96
|
+
defaultValue: "Automation details",
|
|
97
|
+
}) }), _jsx(DialogDescription, { children: detailsTarget
|
|
98
|
+
? detailsTarget.triggerType === "event"
|
|
99
|
+
? t("jobs.automationEventDetails", {
|
|
100
|
+
defaultValue: "Runs when {{event}}.",
|
|
101
|
+
event: detailsTarget.event ?? "an event fires",
|
|
102
|
+
})
|
|
103
|
+
: (detailsTarget.scheduleDescription ??
|
|
104
|
+
detailsTarget.schedule ??
|
|
105
|
+
t("jobs.automationScheduleTrigger", {
|
|
106
|
+
defaultValue: "Scheduled task",
|
|
107
|
+
}))
|
|
108
|
+
: null })] }), detailsTarget ? (_jsxs("div", { className: "space-y-3", children: [detailsTarget.condition ? (_jsxs("div", { children: [_jsx("p", { className: "text-xs font-medium text-foreground", children: t("jobs.condition", { defaultValue: "Condition" }) }), _jsx("p", { className: "mt-1 text-sm text-muted-foreground", children: detailsTarget.condition })] })) : null, _jsxs("div", { children: [_jsx("p", { className: "text-xs font-medium text-foreground", children: t("jobs.instructions", { defaultValue: "Instructions" }) }), _jsx("p", { className: "mt-1 whitespace-pre-wrap text-sm text-muted-foreground", children: detailsTarget.body })] })] })) : null] }) })] }));
|
|
34
109
|
}
|
|
35
110
|
export function AutomationsSection() {
|
|
36
|
-
const
|
|
37
|
-
const [
|
|
38
|
-
const [
|
|
39
|
-
const [togglingId, setTogglingId] = useState(null);
|
|
40
|
-
const [deletingId, setDeletingId] = useState(null);
|
|
41
|
-
const [confirmDeleteId, setConfirmDeleteId] = useState(null);
|
|
111
|
+
const t = useT();
|
|
112
|
+
const { data: automations = [] } = useAutomations("user");
|
|
113
|
+
const [newOpen, setNewOpen] = useState(false);
|
|
42
114
|
const [toast, setToast] = useState(null);
|
|
43
|
-
const [reloadToken, setReloadToken] = useState(0);
|
|
44
115
|
const showToast = useCallback((kind, text, ms = 2500) => {
|
|
45
116
|
setToast({ kind, text });
|
|
46
|
-
setTimeout(() => setToast(null), ms);
|
|
117
|
+
window.setTimeout(() => setToast(null), ms);
|
|
47
118
|
}, []);
|
|
48
|
-
useEffect(() => {
|
|
49
|
-
let cancelled = false;
|
|
50
|
-
setLoading(true);
|
|
51
|
-
fetch(agentNativePath("/_agent-native/resources/tree"))
|
|
52
|
-
.then(async (r) => {
|
|
53
|
-
if (!r.ok)
|
|
54
|
-
throw new Error(`Failed to load (${r.status})`);
|
|
55
|
-
return (await r.json());
|
|
56
|
-
})
|
|
57
|
-
.then(({ tree }) => {
|
|
58
|
-
if (cancelled)
|
|
59
|
-
return;
|
|
60
|
-
const jobsFolder = tree.find((n) => n.name === "jobs" && n.type === "folder");
|
|
61
|
-
const items = jobsFolder?.children
|
|
62
|
-
? flattenJobs(jobsFolder.children)
|
|
63
|
-
: [];
|
|
64
|
-
setAutomations(items);
|
|
65
|
-
setLoading(false);
|
|
66
|
-
})
|
|
67
|
-
.catch((err) => {
|
|
68
|
-
if (cancelled)
|
|
69
|
-
return;
|
|
70
|
-
setError(err?.message ?? "Failed to load");
|
|
71
|
-
setLoading(false);
|
|
72
|
-
});
|
|
73
|
-
return () => {
|
|
74
|
-
cancelled = true;
|
|
75
|
-
};
|
|
76
|
-
}, [reloadToken]);
|
|
77
|
-
const reload = useCallback(() => setReloadToken((t) => t + 1), []);
|
|
78
|
-
const handleToggle = useCallback(async (item) => {
|
|
79
|
-
setTogglingId(item.id);
|
|
80
|
-
try {
|
|
81
|
-
const res = await fetch(agentNativePath(`/_agent-native/resources/${encodeURIComponent(item.id)}`));
|
|
82
|
-
if (!res.ok) {
|
|
83
|
-
showToast("err", "Failed to read automation");
|
|
84
|
-
return;
|
|
85
|
-
}
|
|
86
|
-
const resource = await res.json();
|
|
87
|
-
const content = resource.content ?? "";
|
|
88
|
-
const newEnabled = !item.enabled;
|
|
89
|
-
const updated = content.replace(/^(enabled:\s*)(true|false)/m, `$1${newEnabled}`);
|
|
90
|
-
const putRes = await fetch(agentNativePath(`/_agent-native/resources/${encodeURIComponent(item.id)}`), {
|
|
91
|
-
method: "PUT",
|
|
92
|
-
headers: { "Content-Type": "application/json" },
|
|
93
|
-
body: JSON.stringify({ content: updated }),
|
|
94
|
-
});
|
|
95
|
-
if (!putRes.ok) {
|
|
96
|
-
showToast("err", "Failed to update automation");
|
|
97
|
-
return;
|
|
98
|
-
}
|
|
99
|
-
showToast("ok", newEnabled ? "Enabled" : "Disabled");
|
|
100
|
-
reload();
|
|
101
|
-
}
|
|
102
|
-
finally {
|
|
103
|
-
setTogglingId(null);
|
|
104
|
-
}
|
|
105
|
-
}, [reload, showToast]);
|
|
106
|
-
const handleDelete = useCallback(async (item) => {
|
|
107
|
-
setDeletingId(item.id);
|
|
108
|
-
try {
|
|
109
|
-
const res = await fetch(agentNativePath(`/_agent-native/resources/${encodeURIComponent(item.id)}`), {
|
|
110
|
-
method: "DELETE",
|
|
111
|
-
headers: { "Content-Type": "application/json" },
|
|
112
|
-
});
|
|
113
|
-
if (!res.ok) {
|
|
114
|
-
showToast("err", "Failed to delete automation");
|
|
115
|
-
return;
|
|
116
|
-
}
|
|
117
|
-
showToast("ok", "Deleted");
|
|
118
|
-
setConfirmDeleteId(null);
|
|
119
|
-
reload();
|
|
120
|
-
}
|
|
121
|
-
finally {
|
|
122
|
-
setDeletingId(null);
|
|
123
|
-
}
|
|
124
|
-
}, [reload, showToast]);
|
|
125
119
|
const handleFireTestEvent = useCallback(async () => {
|
|
126
|
-
showToast("ok", "Firing test event
|
|
120
|
+
showToast("ok", t("jobs.firingTestEvent", { defaultValue: "Firing test event…" }));
|
|
127
121
|
try {
|
|
128
122
|
const res = await fetch(agentNativePath("/_agent-native/automations/fire-test"), {
|
|
129
123
|
method: "POST",
|
|
@@ -131,17 +125,22 @@ export function AutomationsSection() {
|
|
|
131
125
|
body: JSON.stringify({ data: {} }),
|
|
132
126
|
});
|
|
133
127
|
if (!res.ok) {
|
|
134
|
-
showToast("err",
|
|
128
|
+
showToast("err", t("jobs.fireEventError", {
|
|
129
|
+
defaultValue: "Failed to fire event ({{status}})",
|
|
130
|
+
status: res.status,
|
|
131
|
+
}));
|
|
135
132
|
return;
|
|
136
133
|
}
|
|
137
|
-
showToast("ok", "Event fired");
|
|
134
|
+
showToast("ok", t("jobs.eventFired", { defaultValue: "Event fired" }));
|
|
138
135
|
}
|
|
139
136
|
catch (err) {
|
|
140
|
-
showToast("err", err
|
|
137
|
+
showToast("err", err instanceof Error
|
|
138
|
+
? err.message
|
|
139
|
+
: t("jobs.fireEventErrorGeneric", {
|
|
140
|
+
defaultValue: "Failed to fire event.",
|
|
141
|
+
}));
|
|
141
142
|
}
|
|
142
|
-
}, [showToast]);
|
|
143
|
-
const [newOpen, setNewOpen] = useState(false);
|
|
144
|
-
const [newScope, setNewScope] = useState("personal");
|
|
143
|
+
}, [showToast, t]);
|
|
145
144
|
const handleNewSubmit = useCallback((text) => {
|
|
146
145
|
const trimmed = text.trim();
|
|
147
146
|
if (!trimmed)
|
|
@@ -151,36 +150,18 @@ export function AutomationsSection() {
|
|
|
151
150
|
}));
|
|
152
151
|
sendToAgentChat({
|
|
153
152
|
message: trimmed,
|
|
154
|
-
context:
|
|
153
|
+
context: automationCreationContext(),
|
|
155
154
|
submit: true,
|
|
156
155
|
newTab: true,
|
|
157
156
|
});
|
|
158
157
|
setNewOpen(false);
|
|
159
|
-
}, [
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
? "bg-green-500/15 text-green-500"
|
|
168
|
-
: "bg-accent/60 text-muted-foreground"} hover:opacity-80 disabled:opacity-40`, children: togglingId === item.id ? (_jsx(IconLoader2, { size: 10, className: "animate-spin" })) : item.enabled ? ("On") : ("Off") }) }), _jsx(TooltipContent, { children: item.enabled ? "Disable" : "Enable" })] }), confirmDeleteId === item.id ? (_jsxs("div", { className: "flex items-center gap-1", children: [_jsx("button", { type: "button", onClick: () => handleDelete(item), disabled: deletingId === item.id, className: "rounded px-1.5 py-0.5 text-[9px] font-semibold uppercase tracking-wide bg-red-500/15 text-red-500 hover:bg-red-500/25 disabled:opacity-40", children: deletingId === item.id ? (_jsx(IconLoader2, { size: 10, className: "animate-spin" })) : ("Confirm") }), _jsx("button", { type: "button", onClick: () => setConfirmDeleteId(null), className: "rounded px-1.5 py-0.5 text-[9px] font-semibold uppercase tracking-wide bg-accent/60 text-muted-foreground hover:text-foreground", children: "Cancel" })] })) : (_jsxs(Tooltip, { children: [_jsx(TooltipTrigger, { asChild: true, children: _jsx("button", { type: "button", onClick: () => setConfirmDeleteId(item.id), className: "text-muted-foreground hover:text-red-500 disabled:opacity-40", children: _jsx(IconTrash, { size: 12 }) }) }), _jsx(TooltipContent, { children: "Delete" })] }))] })] }), item.lastRun && (_jsxs("p", { className: "text-[10px] text-muted-foreground mt-1 ms-[17px]", children: ["Last run:", " ", new Date(item.lastRun).toLocaleString(undefined, {
|
|
169
|
-
month: "short",
|
|
170
|
-
day: "numeric",
|
|
171
|
-
hour: "numeric",
|
|
172
|
-
minute: "2-digit",
|
|
173
|
-
})] }))] }, item.id)))), toast && (_jsx("p", { className: `text-[10px] ${toast.kind === "ok" ? "text-green-500" : "text-red-500"}`, children: toast.text }))] }));
|
|
174
|
-
}
|
|
175
|
-
function StatusBadge({ status }) {
|
|
176
|
-
if (!status)
|
|
177
|
-
return null;
|
|
178
|
-
const styles = {
|
|
179
|
-
success: "bg-green-500/15 text-green-500",
|
|
180
|
-
error: "bg-red-500/15 text-red-500",
|
|
181
|
-
running: "bg-blue-500/15 text-blue-500",
|
|
182
|
-
skipped: "bg-accent/60 text-muted-foreground",
|
|
183
|
-
};
|
|
184
|
-
return (_jsx("span", { className: `rounded-full px-1.5 py-0.5 text-[9px] font-semibold uppercase tracking-wide ${styles[status] ?? styles.skipped}`, children: status }));
|
|
158
|
+
}, []);
|
|
159
|
+
return (_jsxs("div", { className: "space-y-2", children: [_jsxs("div", { className: "flex items-center gap-1.5", children: [_jsxs(Popover, { open: newOpen, onOpenChange: setNewOpen, children: [_jsx(PopoverTrigger, { asChild: true, children: _jsxs(Button, { type: "button", variant: "outline", size: "sm", className: "cursor-pointer", children: [_jsx(IconPlus, { className: "size-3.5" }), t("jobs.newAutomation", { defaultValue: "New automation" })] }) }), _jsxs(PopoverContent, { align: "start", sideOffset: 6, collisionPadding: 8, className: "z-[260] w-[calc(100vw-24px)] max-w-[380px] p-3", children: [_jsx("p", { className: "px-1 pb-2 text-sm font-semibold text-foreground", children: t("jobs.newAutomation", { defaultValue: "New automation" }) }), _jsx(PromptComposer, { autoFocus: true, placeholder: t("jobs.automationPlaceholder", {
|
|
160
|
+
defaultValue: "Describe what you want to automate…",
|
|
161
|
+
}), draftScope: "automations:create", onSubmit: handleNewSubmit })] })] }), automations.length > 0 ? (_jsxs(Button, { type: "button", variant: "outline", size: "sm", className: "cursor-pointer", onClick: handleFireTestEvent, children: [_jsx(IconPlayerPlay, { className: "size-3.5" }), t("jobs.fireTestEvent", { defaultValue: "Fire test event" })] })) : null] }), toast ? (_jsx("p", { className: toast.kind === "ok"
|
|
162
|
+
? "text-xs text-emerald-600"
|
|
163
|
+
: "text-xs text-destructive", children: toast.text })) : null, _jsx(AutomationsList, { scope: "user", compact: true, emptyMessage: t("jobs.automationsEmptySettings", {
|
|
164
|
+
defaultValue: 'No automations yet. Click "New automation" or ask the agent to set one up.',
|
|
165
|
+
}) })] }));
|
|
185
166
|
}
|
|
186
167
|
//# sourceMappingURL=AutomationsSection.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"AutomationsSection.js","sourceRoot":"","sources":["../../../src/client/settings/AutomationsSection.tsx"],"names":[],"mappings":"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","sourcesContent":["import {\n IconBolt,\n IconClock,\n IconLoader2,\n IconPlayerPlay,\n IconPlus,\n IconTrash,\n} from \"@tabler/icons-react\";\nimport { useEffect, useState, useCallback } from \"react\";\n\nimport { sendToAgentChat } from \"../agent-chat.js\";\nimport { agentNativePath } from \"../api-path.js\";\nimport {\n Popover,\n PopoverContent,\n PopoverTrigger,\n} from \"../components/ui/popover.js\";\nimport {\n Tooltip,\n TooltipContent,\n TooltipTrigger,\n} from \"../components/ui/tooltip.js\";\nimport { PromptComposer } from \"../composer/PromptComposer.js\";\n\ninterface TreeNode {\n name: string;\n path: string;\n type: \"file\" | \"folder\";\n kind?: string;\n children?: TreeNode[];\n resource?: {\n id: string;\n path: string;\n owner: string;\n mimeType: string;\n size: number;\n createdAt: number;\n updatedAt: number;\n };\n jobMeta?: {\n schedule?: string;\n scheduleDescription?: string;\n enabled?: boolean;\n lastStatus?: string;\n lastRun?: string;\n nextRun?: string;\n };\n}\n\ninterface AutomationItem {\n id: string;\n name: string;\n path: string;\n schedule?: string;\n scheduleDescription?: string;\n enabled: boolean;\n lastStatus?: string;\n lastRun?: string;\n nextRun?: string;\n}\n\nfunction flattenJobs(nodes: TreeNode[]): AutomationItem[] {\n const items: AutomationItem[] = [];\n for (const node of nodes) {\n if (node.type === \"folder\" && node.children) {\n items.push(...flattenJobs(node.children));\n }\n if (\n node.type === \"file\" &&\n node.kind === \"job\" &&\n node.resource &&\n node.jobMeta\n ) {\n const name = node.name.replace(/\\.md$/, \"\").replace(/-/g, \" \");\n items.push({\n id: node.resource.id,\n name,\n path: node.resource.path,\n schedule: node.jobMeta.schedule,\n scheduleDescription: node.jobMeta.scheduleDescription,\n enabled: node.jobMeta.enabled ?? false,\n lastStatus: node.jobMeta.lastStatus,\n lastRun: node.jobMeta.lastRun,\n nextRun: node.jobMeta.nextRun,\n });\n }\n }\n return items;\n}\n\nexport function AutomationsSection() {\n const [automations, setAutomations] = useState<AutomationItem[]>([]);\n const [loading, setLoading] = useState(true);\n const [error, setError] = useState<string | null>(null);\n const [togglingId, setTogglingId] = useState<string | null>(null);\n const [deletingId, setDeletingId] = useState<string | null>(null);\n const [confirmDeleteId, setConfirmDeleteId] = useState<string | null>(null);\n const [toast, setToast] = useState<{\n kind: \"ok\" | \"err\";\n text: string;\n } | null>(null);\n const [reloadToken, setReloadToken] = useState(0);\n\n const showToast = useCallback(\n (kind: \"ok\" | \"err\", text: string, ms = 2500) => {\n setToast({ kind, text });\n setTimeout(() => setToast(null), ms);\n },\n [],\n );\n\n useEffect(() => {\n let cancelled = false;\n setLoading(true);\n fetch(agentNativePath(\"/_agent-native/resources/tree\"))\n .then(async (r) => {\n if (!r.ok) throw new Error(`Failed to load (${r.status})`);\n return (await r.json()) as { tree: TreeNode[] };\n })\n .then(({ tree }) => {\n if (cancelled) return;\n const jobsFolder = tree.find(\n (n) => n.name === \"jobs\" && n.type === \"folder\",\n );\n const items = jobsFolder?.children\n ? flattenJobs(jobsFolder.children)\n : [];\n setAutomations(items);\n setLoading(false);\n })\n .catch((err) => {\n if (cancelled) return;\n setError(err?.message ?? \"Failed to load\");\n setLoading(false);\n });\n return () => {\n cancelled = true;\n };\n }, [reloadToken]);\n\n const reload = useCallback(() => setReloadToken((t) => t + 1), []);\n\n const handleToggle = useCallback(\n async (item: AutomationItem) => {\n setTogglingId(item.id);\n try {\n const res = await fetch(\n agentNativePath(\n `/_agent-native/resources/${encodeURIComponent(item.id)}`,\n ),\n );\n if (!res.ok) {\n showToast(\"err\", \"Failed to read automation\");\n return;\n }\n const resource = await res.json();\n const content: string = resource.content ?? \"\";\n\n const newEnabled = !item.enabled;\n const updated = content.replace(\n /^(enabled:\\s*)(true|false)/m,\n `$1${newEnabled}`,\n );\n\n const putRes = await fetch(\n agentNativePath(\n `/_agent-native/resources/${encodeURIComponent(item.id)}`,\n ),\n {\n method: \"PUT\",\n headers: { \"Content-Type\": \"application/json\" },\n body: JSON.stringify({ content: updated }),\n },\n );\n if (!putRes.ok) {\n showToast(\"err\", \"Failed to update automation\");\n return;\n }\n showToast(\"ok\", newEnabled ? \"Enabled\" : \"Disabled\");\n reload();\n } finally {\n setTogglingId(null);\n }\n },\n [reload, showToast],\n );\n\n const handleDelete = useCallback(\n async (item: AutomationItem) => {\n setDeletingId(item.id);\n try {\n const res = await fetch(\n agentNativePath(\n `/_agent-native/resources/${encodeURIComponent(item.id)}`,\n ),\n {\n method: \"DELETE\",\n headers: { \"Content-Type\": \"application/json\" },\n },\n );\n if (!res.ok) {\n showToast(\"err\", \"Failed to delete automation\");\n return;\n }\n showToast(\"ok\", \"Deleted\");\n setConfirmDeleteId(null);\n reload();\n } finally {\n setDeletingId(null);\n }\n },\n [reload, showToast],\n );\n\n const handleFireTestEvent = useCallback(async () => {\n showToast(\"ok\", \"Firing test event...\");\n try {\n const res = await fetch(\n agentNativePath(\"/_agent-native/automations/fire-test\"),\n {\n method: \"POST\",\n headers: { \"Content-Type\": \"application/json\" },\n body: JSON.stringify({ data: {} }),\n },\n );\n if (!res.ok) {\n showToast(\"err\", `Failed to fire event (${res.status})`);\n return;\n }\n showToast(\"ok\", \"Event fired\");\n } catch (err: any) {\n showToast(\"err\", err?.message ?? \"Failed to fire event\");\n }\n }, [showToast]);\n\n const [newOpen, setNewOpen] = useState(false);\n const [newScope, setNewScope] = useState<\"personal\" | \"organization\">(\n \"personal\",\n );\n\n const handleNewSubmit = useCallback(\n (text: string) => {\n const trimmed = text.trim();\n if (!trimmed) return;\n window.dispatchEvent(\n new CustomEvent(\"agent-panel:set-mode\", {\n detail: { mode: \"chat\" },\n }),\n );\n sendToAgentChat({\n message: trimmed,\n context: `The user wants to create a new automation. Scope: ${newScope}. Use manage-automations with action=define to create it. Ask clarifying questions if needed about what event to trigger on, conditions, and what actions to take.`,\n submit: true,\n newTab: true,\n });\n setNewOpen(false);\n },\n [newScope],\n );\n\n if (error) {\n return (\n <p className=\"text-[10px] text-red-500\">\n Failed to load automations: {error}\n </p>\n );\n }\n\n if (loading) {\n return (\n <div className=\"flex items-center gap-1.5 text-[10px] text-muted-foreground\">\n <IconLoader2 size={10} className=\"animate-spin\" />\n Loading...\n </div>\n );\n }\n\n return (\n <div className=\"space-y-2\">\n <div className=\"flex items-center gap-1.5\">\n <Popover open={newOpen} onOpenChange={setNewOpen}>\n <PopoverTrigger asChild>\n <button\n type=\"button\"\n className=\"inline-flex items-center gap-1 rounded border border-border px-2 py-1 text-[10px] font-medium text-muted-foreground hover:text-foreground hover:bg-accent/40\"\n >\n <IconPlus size={10} />\n New Automation\n </button>\n </PopoverTrigger>\n <PopoverContent\n align=\"start\"\n sideOffset={6}\n collisionPadding={8}\n className=\"z-[260] w-[calc(100vw-24px)] max-w-[380px] p-3\"\n >\n <p className=\"px-1 pb-2 text-sm font-semibold text-foreground\">\n New automation\n </p>\n <PromptComposer\n autoFocus\n placeholder=\"Describe what you want to automate...\"\n draftScope=\"automations:create\"\n onSubmit={handleNewSubmit}\n />\n <div className=\"mt-2\">\n <select\n value={newScope}\n onChange={(e) =>\n setNewScope(e.target.value as \"personal\" | \"organization\")\n }\n className=\"w-full cursor-pointer rounded-md border border-input bg-background px-3 py-1.5 text-[12px] text-foreground\"\n >\n <option value=\"personal\">Personal</option>\n <option value=\"organization\">Organization</option>\n </select>\n </div>\n </PopoverContent>\n </Popover>\n {automations.length > 0 && (\n <button\n type=\"button\"\n onClick={handleFireTestEvent}\n className=\"inline-flex items-center gap-1 rounded border border-border px-2 py-1 text-[10px] font-medium text-muted-foreground hover:text-foreground hover:bg-accent/40\"\n >\n <IconPlayerPlay size={10} />\n Fire Test Event\n </button>\n )}\n </div>\n\n {automations.length === 0 ? (\n <p className=\"text-[10px] text-muted-foreground\">\n No automations yet. Click \"New Automation\" to create one, or ask the\n agent to set up a scheduled or event-triggered task.\n </p>\n ) : (\n automations.map((item) => (\n <div\n key={item.id}\n className=\"rounded-md border border-border px-2.5 py-2 bg-accent/30\"\n >\n <div className=\"flex items-center justify-between gap-2\">\n <div className=\"min-w-0 flex-1\">\n <div className=\"flex items-center gap-1.5\">\n <span className=\"text-muted-foreground shrink-0\">\n {item.schedule ? (\n <IconClock size={11} />\n ) : (\n <IconBolt size={11} />\n )}\n </span>\n <span className=\"text-[11px] font-medium text-foreground truncate capitalize\">\n {item.name}\n </span>\n </div>\n {item.scheduleDescription && (\n <p className=\"text-[10px] text-muted-foreground mt-0.5 ms-[17px]\">\n {item.scheduleDescription}\n </p>\n )}\n {item.schedule && !item.scheduleDescription && (\n <p className=\"text-[10px] text-muted-foreground mt-0.5 ms-[17px] font-mono\">\n {item.schedule}\n </p>\n )}\n </div>\n <div className=\"flex items-center gap-1.5 shrink-0\">\n <StatusBadge status={item.lastStatus} />\n <Tooltip>\n <TooltipTrigger asChild>\n <button\n type=\"button\"\n onClick={() => handleToggle(item)}\n disabled={togglingId === item.id}\n className={`rounded px-1.5 py-0.5 text-[9px] font-semibold uppercase tracking-wide ${\n item.enabled\n ? \"bg-green-500/15 text-green-500\"\n : \"bg-accent/60 text-muted-foreground\"\n } hover:opacity-80 disabled:opacity-40`}\n >\n {togglingId === item.id ? (\n <IconLoader2 size={10} className=\"animate-spin\" />\n ) : item.enabled ? (\n \"On\"\n ) : (\n \"Off\"\n )}\n </button>\n </TooltipTrigger>\n <TooltipContent>\n {item.enabled ? \"Disable\" : \"Enable\"}\n </TooltipContent>\n </Tooltip>\n {confirmDeleteId === item.id ? (\n <div className=\"flex items-center gap-1\">\n <button\n type=\"button\"\n onClick={() => handleDelete(item)}\n disabled={deletingId === item.id}\n className=\"rounded px-1.5 py-0.5 text-[9px] font-semibold uppercase tracking-wide bg-red-500/15 text-red-500 hover:bg-red-500/25 disabled:opacity-40\"\n >\n {deletingId === item.id ? (\n <IconLoader2 size={10} className=\"animate-spin\" />\n ) : (\n \"Confirm\"\n )}\n </button>\n <button\n type=\"button\"\n onClick={() => setConfirmDeleteId(null)}\n className=\"rounded px-1.5 py-0.5 text-[9px] font-semibold uppercase tracking-wide bg-accent/60 text-muted-foreground hover:text-foreground\"\n >\n Cancel\n </button>\n </div>\n ) : (\n <Tooltip>\n <TooltipTrigger asChild>\n <button\n type=\"button\"\n onClick={() => setConfirmDeleteId(item.id)}\n className=\"text-muted-foreground hover:text-red-500 disabled:opacity-40\"\n >\n <IconTrash size={12} />\n </button>\n </TooltipTrigger>\n <TooltipContent>Delete</TooltipContent>\n </Tooltip>\n )}\n </div>\n </div>\n {item.lastRun && (\n <p className=\"text-[10px] text-muted-foreground mt-1 ms-[17px]\">\n Last run:{\" \"}\n {new Date(item.lastRun).toLocaleString(undefined, {\n month: \"short\",\n day: \"numeric\",\n hour: \"numeric\",\n minute: \"2-digit\",\n })}\n </p>\n )}\n </div>\n ))\n )}\n\n {toast && (\n <p\n className={`text-[10px] ${toast.kind === \"ok\" ? \"text-green-500\" : \"text-red-500\"}`}\n >\n {toast.text}\n </p>\n )}\n </div>\n );\n}\n\nfunction StatusBadge({ status }: { status?: string }) {\n if (!status) return null;\n\n const styles: Record<string, string> = {\n success: \"bg-green-500/15 text-green-500\",\n error: \"bg-red-500/15 text-red-500\",\n running: \"bg-blue-500/15 text-blue-500\",\n skipped: \"bg-accent/60 text-muted-foreground\",\n };\n\n return (\n <span\n className={`rounded-full px-1.5 py-0.5 text-[9px] font-semibold uppercase tracking-wide ${styles[status] ?? styles.skipped}`}\n >\n {status}\n </span>\n );\n}\n"]}
|
|
1
|
+
{"version":3,"file":"AutomationsSection.js","sourceRoot":"","sources":["../../../src/client/settings/AutomationsSection.tsx"],"names":[],"mappings":"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","sourcesContent":["import { Button } from \"@agent-native/toolkit/ui/button\";\nimport {\n IconBolt,\n IconClock,\n IconEye,\n IconLoader2,\n IconPlayerPause,\n IconPlayerPlay,\n IconPlus,\n IconTrash,\n} from \"@tabler/icons-react\";\nimport { useCallback, useState } from \"react\";\n\nimport { sendToAgentChat } from \"../agent-chat.js\";\nimport {\n useAutomations,\n useManageAutomation,\n type Automation,\n type JobsScope,\n} from \"../agent-page/use-jobs.js\";\nimport { agentNativePath } from \"../api-path.js\";\nimport {\n Dialog,\n DialogContent,\n DialogDescription,\n DialogFooter,\n DialogHeader,\n DialogTitle,\n} from \"../components/ui/dialog.js\";\nimport {\n Popover,\n PopoverContent,\n PopoverTrigger,\n} from \"../components/ui/popover.js\";\nimport { PromptComposer } from \"../composer/PromptComposer.js\";\nimport { useFormatters, useT } from \"../i18n.js\";\n\nexport interface AutomationsListProps {\n scope?: JobsScope;\n compact?: boolean;\n emptyMessage?: string;\n}\n\nexport const AUTOMATION_CREATION_SCOPE = \"personal\" as const;\n\nexport function automationCreationContext(): string {\n return `The user wants to create a new ${AUTOMATION_CREATION_SCOPE} automation. Use manage-automations with action=define to create it. Ask clarifying questions if needed about what event to trigger on, conditions, and what actions to take.`;\n}\n\nexport function AutomationsList({\n scope = \"user\",\n compact = false,\n emptyMessage,\n}: AutomationsListProps) {\n const t = useT();\n const { formatDate } = useFormatters();\n const query = useAutomations(scope);\n const mutation = useManageAutomation(scope);\n const [deleteTarget, setDeleteTarget] = useState<Automation | null>(null);\n const [detailsTarget, setDetailsTarget] = useState<Automation | null>(null);\n\n const formatDateTime = (value: string | null) => {\n if (!value || Number.isNaN(new Date(value).getTime())) return null;\n return formatDate(value, {\n month: \"short\",\n day: \"numeric\",\n hour: \"numeric\",\n minute: \"2-digit\",\n });\n };\n\n if (query.isLoading) {\n return (\n <div\n className=\"flex items-center gap-2 text-sm text-muted-foreground\"\n aria-busy=\"true\"\n >\n <IconLoader2 className=\"size-4 animate-spin\" />\n {t(\"jobs.loading\", { defaultValue: \"Loading…\" })}\n </div>\n );\n }\n\n if (query.error) {\n return (\n <p className=\"text-sm text-destructive\">\n {t(\"jobs.automationsLoadError\", {\n defaultValue: \"Could not load automations.\",\n })}\n </p>\n );\n }\n\n const automations = query.data ?? [];\n if (automations.length === 0) {\n return (\n <p className=\"text-sm text-muted-foreground\">\n {emptyMessage ??\n t(\"jobs.automationsEmpty\", {\n defaultValue:\n \"No automations yet. Ask the agent to set up an event-triggered or scheduled task.\",\n })}\n </p>\n );\n }\n\n return (\n <div className={compact ? \"space-y-2\" : \"space-y-3\"}>\n {automations.map((automation) => {\n const lastRun = formatDateTime(automation.lastRun);\n const nextRun = formatDateTime(automation.nextRun);\n const trigger =\n automation.triggerType === \"event\"\n ? t(\"jobs.automationEventTrigger\", {\n defaultValue: \"On {{event}}\",\n event: automation.event ?? \"event\",\n })\n : (automation.scheduleDescription ??\n automation.schedule ??\n t(\"jobs.automationScheduleTrigger\", {\n defaultValue: \"Scheduled task\",\n }));\n\n return (\n <article\n key={automation.id}\n className=\"rounded-lg border border-border bg-card p-3\"\n >\n <div className=\"flex items-start gap-3\">\n <div className=\"mt-0.5 text-muted-foreground\">\n {automation.triggerType === \"event\" ? (\n <IconBolt className=\"size-4\" />\n ) : (\n <IconClock className=\"size-4\" />\n )}\n </div>\n <div className=\"min-w-0 flex-1\">\n <div className=\"flex flex-wrap items-center gap-2\">\n <h3 className=\"truncate text-sm font-medium text-foreground\">\n {automation.name.replace(/-/g, \" \")}\n </h3>\n <span\n className={\n automation.enabled\n ? \"rounded-full bg-emerald-500/15 px-2 py-0.5 text-[10px] font-medium text-emerald-600 dark:text-emerald-400\"\n : \"rounded-full bg-muted px-2 py-0.5 text-[10px] font-medium text-muted-foreground\"\n }\n >\n {automation.enabled\n ? t(\"jobs.enabled\", { defaultValue: \"Enabled\" })\n : t(\"jobs.disabled\", { defaultValue: \"Disabled\" })}\n </span>\n {automation.lastStatus ? (\n <span className=\"rounded-full bg-muted px-2 py-0.5 text-[10px] font-medium text-muted-foreground\">\n {automation.lastStatus}\n </span>\n ) : null}\n </div>\n <p className=\"mt-1 text-xs text-muted-foreground\">{trigger}</p>\n <p className=\"mt-1 line-clamp-2 text-xs text-muted-foreground/80\">\n {automation.body}\n </p>\n {lastRun || nextRun ? (\n <div className=\"mt-2 flex flex-wrap gap-x-4 gap-y-1 text-[11px] text-muted-foreground\">\n {lastRun ? (\n <span>\n {t(\"jobs.lastRun\", { defaultValue: \"Last run\" })}:{\" \"}\n {lastRun}\n </span>\n ) : null}\n {nextRun ? (\n <span>\n {t(\"jobs.nextRun\", { defaultValue: \"Next run\" })}:{\" \"}\n {nextRun}\n </span>\n ) : null}\n </div>\n ) : null}\n </div>\n <div className=\"flex shrink-0 items-center gap-1\">\n <Button\n type=\"button\"\n variant=\"ghost\"\n size=\"sm\"\n className=\"cursor-pointer px-2 text-xs\"\n onClick={() => setDetailsTarget(automation)}\n >\n <IconEye className=\"size-3.5\" />\n {t(\"jobs.details\", { defaultValue: \"Details\" })}\n </Button>\n {automation.canUpdate ? (\n <>\n <Button\n type=\"button\"\n variant=\"ghost\"\n size=\"sm\"\n className=\"cursor-pointer px-2 text-xs\"\n disabled={mutation.isPending}\n onClick={() =>\n mutation.mutate({\n operation: \"update\",\n name: automation.name,\n scope: automation.scope,\n enabled: !automation.enabled,\n })\n }\n >\n {automation.enabled ? (\n <IconPlayerPause className=\"size-3.5\" />\n ) : (\n <IconPlayerPlay className=\"size-3.5\" />\n )}\n {automation.enabled\n ? t(\"jobs.pause\", { defaultValue: \"Pause\" })\n : t(\"jobs.resume\", { defaultValue: \"Resume\" })}\n </Button>\n <Button\n type=\"button\"\n variant=\"ghost\"\n size=\"icon\"\n className=\"size-8 cursor-pointer text-muted-foreground hover:text-destructive\"\n aria-label={t(\"jobs.delete\", { defaultValue: \"Delete\" })}\n onClick={() => setDeleteTarget(automation)}\n >\n <IconTrash className=\"size-3.5\" />\n </Button>\n </>\n ) : null}\n </div>\n </div>\n </article>\n );\n })}\n\n {mutation.error ? (\n <p className=\"text-sm text-destructive\">\n {mutation.error.message ||\n t(\"jobs.automationUpdateError\", {\n defaultValue: \"Could not update automation.\",\n })}\n </p>\n ) : null}\n\n <Dialog\n open={deleteTarget !== null}\n onOpenChange={(open) => {\n if (!open && !mutation.isPending) setDeleteTarget(null);\n }}\n >\n <DialogContent>\n <DialogHeader>\n <DialogTitle>\n {t(\"jobs.deleteAutomationTitle\", {\n defaultValue: \"Delete automation?\",\n })}\n </DialogTitle>\n <DialogDescription>\n {t(\"jobs.deleteAutomationDescription\", {\n defaultValue:\n \"This permanently removes the automation and cannot be undone.\",\n })}\n </DialogDescription>\n </DialogHeader>\n <DialogFooter>\n <Button\n type=\"button\"\n variant=\"outline\"\n className=\"cursor-pointer\"\n disabled={mutation.isPending}\n onClick={() => setDeleteTarget(null)}\n >\n {t(\"jobs.cancel\", { defaultValue: \"Cancel\" })}\n </Button>\n <Button\n type=\"button\"\n variant=\"destructive\"\n className=\"cursor-pointer\"\n disabled={mutation.isPending}\n onClick={() => {\n if (!deleteTarget) return;\n mutation.mutate(\n {\n operation: \"delete\",\n name: deleteTarget.name,\n scope: deleteTarget.scope,\n },\n { onSuccess: () => setDeleteTarget(null) },\n );\n }}\n >\n {mutation.isPending ? (\n <IconLoader2 className=\"size-4 animate-spin\" />\n ) : null}\n {t(\"jobs.delete\", { defaultValue: \"Delete\" })}\n </Button>\n </DialogFooter>\n </DialogContent>\n </Dialog>\n\n <Dialog\n open={detailsTarget !== null}\n onOpenChange={(open) => {\n if (!open) setDetailsTarget(null);\n }}\n >\n <DialogContent className=\"max-w-2xl\">\n <DialogHeader>\n <DialogTitle>\n {detailsTarget?.name.replace(/-/g, \" \") ??\n t(\"jobs.automationDetails\", {\n defaultValue: \"Automation details\",\n })}\n </DialogTitle>\n <DialogDescription>\n {detailsTarget\n ? detailsTarget.triggerType === \"event\"\n ? t(\"jobs.automationEventDetails\", {\n defaultValue: \"Runs when {{event}}.\",\n event: detailsTarget.event ?? \"an event fires\",\n })\n : (detailsTarget.scheduleDescription ??\n detailsTarget.schedule ??\n t(\"jobs.automationScheduleTrigger\", {\n defaultValue: \"Scheduled task\",\n }))\n : null}\n </DialogDescription>\n </DialogHeader>\n {detailsTarget ? (\n <div className=\"space-y-3\">\n {detailsTarget.condition ? (\n <div>\n <p className=\"text-xs font-medium text-foreground\">\n {t(\"jobs.condition\", { defaultValue: \"Condition\" })}\n </p>\n <p className=\"mt-1 text-sm text-muted-foreground\">\n {detailsTarget.condition}\n </p>\n </div>\n ) : null}\n <div>\n <p className=\"text-xs font-medium text-foreground\">\n {t(\"jobs.instructions\", { defaultValue: \"Instructions\" })}\n </p>\n <p className=\"mt-1 whitespace-pre-wrap text-sm text-muted-foreground\">\n {detailsTarget.body}\n </p>\n </div>\n </div>\n ) : null}\n </DialogContent>\n </Dialog>\n </div>\n );\n}\n\nexport function AutomationsSection() {\n const t = useT();\n const { data: automations = [] } = useAutomations(\"user\");\n const [newOpen, setNewOpen] = useState(false);\n const [toast, setToast] = useState<{\n kind: \"ok\" | \"err\";\n text: string;\n } | null>(null);\n\n const showToast = useCallback(\n (kind: \"ok\" | \"err\", text: string, ms = 2500) => {\n setToast({ kind, text });\n window.setTimeout(() => setToast(null), ms);\n },\n [],\n );\n\n const handleFireTestEvent = useCallback(async () => {\n showToast(\n \"ok\",\n t(\"jobs.firingTestEvent\", { defaultValue: \"Firing test event…\" }),\n );\n try {\n const res = await fetch(\n agentNativePath(\"/_agent-native/automations/fire-test\"),\n {\n method: \"POST\",\n headers: { \"Content-Type\": \"application/json\" },\n body: JSON.stringify({ data: {} }),\n },\n );\n if (!res.ok) {\n showToast(\n \"err\",\n t(\"jobs.fireEventError\", {\n defaultValue: \"Failed to fire event ({{status}})\",\n status: res.status,\n }),\n );\n return;\n }\n showToast(\"ok\", t(\"jobs.eventFired\", { defaultValue: \"Event fired\" }));\n } catch (err: unknown) {\n showToast(\n \"err\",\n err instanceof Error\n ? err.message\n : t(\"jobs.fireEventErrorGeneric\", {\n defaultValue: \"Failed to fire event.\",\n }),\n );\n }\n }, [showToast, t]);\n\n const handleNewSubmit = useCallback((text: string) => {\n const trimmed = text.trim();\n if (!trimmed) return;\n window.dispatchEvent(\n new CustomEvent(\"agent-panel:set-mode\", {\n detail: { mode: \"chat\" },\n }),\n );\n sendToAgentChat({\n message: trimmed,\n context: automationCreationContext(),\n submit: true,\n newTab: true,\n });\n setNewOpen(false);\n }, []);\n\n return (\n <div className=\"space-y-2\">\n <div className=\"flex items-center gap-1.5\">\n <Popover open={newOpen} onOpenChange={setNewOpen}>\n <PopoverTrigger asChild>\n <Button\n type=\"button\"\n variant=\"outline\"\n size=\"sm\"\n className=\"cursor-pointer\"\n >\n <IconPlus className=\"size-3.5\" />\n {t(\"jobs.newAutomation\", { defaultValue: \"New automation\" })}\n </Button>\n </PopoverTrigger>\n <PopoverContent\n align=\"start\"\n sideOffset={6}\n collisionPadding={8}\n className=\"z-[260] w-[calc(100vw-24px)] max-w-[380px] p-3\"\n >\n <p className=\"px-1 pb-2 text-sm font-semibold text-foreground\">\n {t(\"jobs.newAutomation\", { defaultValue: \"New automation\" })}\n </p>\n <PromptComposer\n autoFocus\n placeholder={t(\"jobs.automationPlaceholder\", {\n defaultValue: \"Describe what you want to automate…\",\n })}\n draftScope=\"automations:create\"\n onSubmit={handleNewSubmit}\n />\n </PopoverContent>\n </Popover>\n {automations.length > 0 ? (\n <Button\n type=\"button\"\n variant=\"outline\"\n size=\"sm\"\n className=\"cursor-pointer\"\n onClick={handleFireTestEvent}\n >\n <IconPlayerPlay className=\"size-3.5\" />\n {t(\"jobs.fireTestEvent\", { defaultValue: \"Fire test event\" })}\n </Button>\n ) : null}\n </div>\n {toast ? (\n <p\n className={\n toast.kind === \"ok\"\n ? \"text-xs text-emerald-600\"\n : \"text-xs text-destructive\"\n }\n >\n {toast.text}\n </p>\n ) : null}\n <AutomationsList\n scope=\"user\"\n compact\n emptyMessage={t(\"jobs.automationsEmptySettings\", {\n defaultValue:\n 'No automations yet. Click \"New automation\" or ask the agent to set one up.',\n })}\n />\n </div>\n );\n}\n"]}
|
package/dist/collab/routes.d.ts
CHANGED
|
@@ -41,9 +41,9 @@ export declare const postCollabUpdate: import("h3").EventHandlerWithFetch<import
|
|
|
41
41
|
* Body: { text: string, fieldName?: string, requestSource?: string }
|
|
42
42
|
*/
|
|
43
43
|
export declare const postCollabText: import("h3").EventHandlerWithFetch<import("h3").EventHandlerRequest, Promise<{
|
|
44
|
-
text?: undefined;
|
|
45
44
|
ok?: undefined;
|
|
46
45
|
error: string;
|
|
46
|
+
text?: undefined;
|
|
47
47
|
} | {
|
|
48
48
|
error?: undefined;
|
|
49
49
|
ok: boolean;
|
|
@@ -13,8 +13,8 @@
|
|
|
13
13
|
* Body: { json: any, fieldName?: string, type?: "map"|"array", requestSource?: string }
|
|
14
14
|
*/
|
|
15
15
|
export declare const postCollabJson: import("h3").EventHandlerWithFetch<import("h3").EventHandlerRequest, Promise<{
|
|
16
|
-
ok?: undefined;
|
|
17
16
|
error: string;
|
|
17
|
+
ok?: undefined;
|
|
18
18
|
} | {
|
|
19
19
|
error?: undefined;
|
|
20
20
|
ok: boolean;
|
|
@@ -17,12 +17,12 @@ declare const _default: import("../../action.js").ActionDefinition<{
|
|
|
17
17
|
id?: undefined;
|
|
18
18
|
provider?: undefined;
|
|
19
19
|
} | {
|
|
20
|
-
error?: undefined;
|
|
21
20
|
configured?: undefined;
|
|
22
21
|
connectPath?: undefined;
|
|
23
22
|
url: string;
|
|
24
23
|
id: string;
|
|
25
24
|
provider: string;
|
|
25
|
+
error?: undefined;
|
|
26
26
|
}>;
|
|
27
27
|
export default _default;
|
|
28
28
|
//# sourceMappingURL=upload-image.d.ts.map
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
export interface RecurringJobActionItem {
|
|
2
|
+
id: string;
|
|
3
|
+
name: string;
|
|
4
|
+
path: string;
|
|
5
|
+
scope: "personal" | "organization";
|
|
6
|
+
schedule: string;
|
|
7
|
+
scheduleDescription: string;
|
|
8
|
+
instructions: string;
|
|
9
|
+
enabled: boolean;
|
|
10
|
+
lastRun: string | null;
|
|
11
|
+
lastStatus: string | null;
|
|
12
|
+
lastError: string | null;
|
|
13
|
+
nextRun: string | null;
|
|
14
|
+
createdBy: string | null;
|
|
15
|
+
canUpdate: boolean;
|
|
16
|
+
}
|
|
17
|
+
declare const _default: import("../../action.js").ActionDefinition<{
|
|
18
|
+
scope?: "organization" | "personal";
|
|
19
|
+
}, RecurringJobActionItem[]>;
|
|
20
|
+
export default _default;
|
|
21
|
+
//# sourceMappingURL=list-recurring-jobs.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"list-recurring-jobs.d.ts","sourceRoot":"","sources":["../../../src/jobs/actions/list-recurring-jobs.ts"],"names":[],"mappings":"AAkCA,MAAM,WAAW,sBAAsB;IACrC,EAAE,EAAE,MAAM,CAAC;IACX,IAAI,EAAE,MAAM,CAAC;IACb,IAAI,EAAE,MAAM,CAAC;IACb,KAAK,EAAE,UAAU,GAAG,cAAc,CAAC;IACnC,QAAQ,EAAE,MAAM,CAAC;IACjB,mBAAmB,EAAE,MAAM,CAAC;IAC5B,YAAY,EAAE,MAAM,CAAC;IACrB,OAAO,EAAE,OAAO,CAAC;IACjB,OAAO,EAAE,MAAM,GAAG,IAAI,CAAC;IACvB,UAAU,EAAE,MAAM,GAAG,IAAI,CAAC;IAC1B,SAAS,EAAE,MAAM,GAAG,IAAI,CAAC;IACzB,OAAO,EAAE,MAAM,GAAG,IAAI,CAAC;IACvB,SAAS,EAAE,MAAM,GAAG,IAAI,CAAC;IACzB,SAAS,EAAE,OAAO,CAAC;CACpB"}
|
|
@@ -0,0 +1,74 @@
|
|
|
1
|
+
import { z } from "zod";
|
|
2
|
+
import { defineAction } from "../../action.js";
|
|
3
|
+
import { organizationResourceOwner, resourceGetByPath, resourceList, } from "../../resources/store.js";
|
|
4
|
+
import { describeCron, isValidCron, nextOccurrence } from "../cron.js";
|
|
5
|
+
import { parseJobFrontmatter } from "../scheduler.js";
|
|
6
|
+
import { authorizeJobMutation } from "../tools.js";
|
|
7
|
+
const scopeSchema = z.enum(["personal", "organization"]);
|
|
8
|
+
function hasTriggerFrontmatter(content) {
|
|
9
|
+
const header = content.match(/^---\n([\s\S]*?)\n---/m)?.[1] ?? "";
|
|
10
|
+
return /^triggerType\s*:/m.test(header);
|
|
11
|
+
}
|
|
12
|
+
function jobName(path) {
|
|
13
|
+
return path.replace(/^jobs\//, "").replace(/\.md$/, "");
|
|
14
|
+
}
|
|
15
|
+
function nextRun(meta) {
|
|
16
|
+
if (!meta.enabled)
|
|
17
|
+
return null;
|
|
18
|
+
if (meta.nextRun)
|
|
19
|
+
return meta.nextRun;
|
|
20
|
+
if (meta.schedule && isValidCron(meta.schedule)) {
|
|
21
|
+
return nextOccurrence(meta.schedule).toISOString();
|
|
22
|
+
}
|
|
23
|
+
return null;
|
|
24
|
+
}
|
|
25
|
+
export default defineAction({
|
|
26
|
+
description: "List recurring cron jobs visible in the selected personal or organization scope. This read surface is used by the Agent Jobs page.",
|
|
27
|
+
agentTool: false,
|
|
28
|
+
schema: z.object({
|
|
29
|
+
scope: scopeSchema.default("personal"),
|
|
30
|
+
}),
|
|
31
|
+
http: { method: "GET" },
|
|
32
|
+
readOnly: true,
|
|
33
|
+
parallelSafe: true,
|
|
34
|
+
run: async ({ scope }, ctx) => {
|
|
35
|
+
const userEmail = ctx?.userEmail;
|
|
36
|
+
if (!userEmail)
|
|
37
|
+
throw new Error("Not authenticated.");
|
|
38
|
+
if (scope === "organization" && !ctx?.orgId)
|
|
39
|
+
return [];
|
|
40
|
+
const owner = scope === "organization"
|
|
41
|
+
? organizationResourceOwner(ctx.orgId)
|
|
42
|
+
: userEmail;
|
|
43
|
+
const resources = await resourceList(owner, "jobs/");
|
|
44
|
+
const jobs = [];
|
|
45
|
+
for (const resource of resources) {
|
|
46
|
+
if (!resource.path.endsWith(".md") || resource.path.endsWith(".keep")) {
|
|
47
|
+
continue;
|
|
48
|
+
}
|
|
49
|
+
const full = await resourceGetByPath(owner, resource.path);
|
|
50
|
+
if (!full || hasTriggerFrontmatter(full.content))
|
|
51
|
+
continue;
|
|
52
|
+
const { meta, body } = parseJobFrontmatter(full.content);
|
|
53
|
+
const canUpdate = scope === "personal" || !(await authorizeJobMutation(owner, meta));
|
|
54
|
+
jobs.push({
|
|
55
|
+
id: full.id,
|
|
56
|
+
name: jobName(full.path),
|
|
57
|
+
path: full.path,
|
|
58
|
+
scope,
|
|
59
|
+
schedule: meta.schedule,
|
|
60
|
+
scheduleDescription: meta.schedule ? describeCron(meta.schedule) : "",
|
|
61
|
+
instructions: body,
|
|
62
|
+
enabled: meta.enabled,
|
|
63
|
+
lastRun: meta.lastRun ?? null,
|
|
64
|
+
lastStatus: meta.lastStatus ?? null,
|
|
65
|
+
lastError: meta.lastError ?? null,
|
|
66
|
+
nextRun: nextRun(meta),
|
|
67
|
+
createdBy: meta.createdBy ?? null,
|
|
68
|
+
canUpdate,
|
|
69
|
+
});
|
|
70
|
+
}
|
|
71
|
+
return jobs;
|
|
72
|
+
},
|
|
73
|
+
});
|
|
74
|
+
//# sourceMappingURL=list-recurring-jobs.js.map
|