spine-framework 0.3.145 → 0.4.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/.env.example +76 -0
- package/.framework/.spine-manifest.json +19 -0
- package/.framework/cli/commands/agents.ts +61 -33
- package/.framework/cli/commands/auth.ts +60 -28
- package/.framework/cli/commands/create-app.ts +212 -80
- package/.framework/cli/commands/dev.ts +184 -68
- package/.framework/cli/commands/doctor.ts +324 -152
- package/.framework/cli/commands/generate.ts +119 -68
- package/.framework/cli/commands/init.ts +141 -242
- package/.framework/cli/commands/install-app.ts +1336 -314
- package/.framework/cli/commands/items.ts +31 -29
- package/.framework/cli/commands/migrate.ts +299 -156
- package/.framework/cli/commands/migrations.ts +62 -30
- package/.framework/cli/commands/pipelines.ts +31 -29
- package/.framework/cli/commands/status.ts +105 -45
- package/.framework/cli/commands/system.ts +47 -42
- package/.framework/cli/commands/test.ts +161 -102
- package/.framework/cli/commands/upgrade.ts +260 -0
- package/.framework/cli/commands/validate-app.ts +517 -161
- package/.framework/cli/context.ts +117 -85
- package/.framework/cli/env-loader.ts +74 -43
- package/.framework/cli/index.ts +70 -46
- package/.framework/cli/lib/project-files.ts +404 -0
- package/.framework/docs/guides/testing-guide.md +1 -1
- package/.framework/docs/runtime-types.md +72 -72
- package/.framework/functions/_shared/access.ts +84 -0
- package/.framework/functions/_shared/agent-runner.ts +5067 -1026
- package/.framework/functions/_shared/app-manifest.ts +214 -94
- package/.framework/functions/_shared/ast.ts +214 -0
- package/.framework/functions/_shared/audit.ts +91 -55
- package/.framework/functions/_shared/cil.ts +368 -127
- package/.framework/functions/_shared/db.ts +337 -68
- package/.framework/functions/_shared/funnel.ts +228 -0
- package/.framework/functions/_shared/geo.ts +105 -0
- package/.framework/functions/_shared/hash-api-key.ts +94 -17
- package/.framework/functions/_shared/index.ts +22 -224
- package/.framework/functions/_shared/kb.ts +832 -58
- package/.framework/functions/_shared/llm.ts +118 -18
- package/.framework/functions/_shared/logging.ts +317 -19
- package/.framework/functions/_shared/middleware.ts +701 -131
- package/.framework/functions/_shared/notify.ts +70 -0
- package/.framework/functions/_shared/outcomes.ts +34 -19
- package/.framework/functions/_shared/permissions.ts +501 -315
- package/.framework/functions/_shared/pipeline-runner.ts +704 -155
- package/.framework/functions/_shared/principal.ts +436 -263
- package/.framework/functions/_shared/rate-limit.ts +233 -0
- package/.framework/functions/_shared/resolve-credentials.ts +86 -19
- package/.framework/functions/_shared/resolve-ids.ts +203 -139
- package/.framework/functions/_shared/retry-deliveries.ts +51 -16
- package/.framework/functions/_shared/schema-utils.ts +602 -521
- package/.framework/functions/_shared/security.ts +345 -0
- package/.framework/functions/_shared/testing.ts +197 -172
- package/.framework/functions/_shared/tracing.ts +351 -21
- package/.framework/functions/_shared/trigger-engine.ts +425 -136
- package/.framework/functions/_shared/webhook-registration.ts +71 -70
- package/.framework/functions/_shared/webhook-registry.ts +126 -83
- package/.framework/functions/account-nodes.ts +30 -30
- package/.framework/functions/adapters/generic-webhook-inbound.ts +49 -16
- package/.framework/functions/adapters/generic-webhook-outbound.ts +17 -17
- package/.framework/functions/adapters/openai-outbound.ts +15 -16
- package/.framework/functions/admin-data.ts +596 -173
- package/.framework/functions/admin-funnel.ts +64 -60
- package/.framework/functions/admin-install-funnel.ts +84 -66
- package/.framework/functions/admin-signals.ts +69 -51
- package/.framework/functions/ai-agents.ts +431 -106
- package/.framework/functions/ai-interactions.ts +186 -112
- package/.framework/functions/api-keys.ts +107 -107
- package/.framework/functions/apps.ts +154 -136
- package/.framework/functions/auth.ts +83 -65
- package/.framework/functions/cil-agent-ingest.ts +189 -232
- package/.framework/functions/cil-agent.ts +433 -177
- package/.framework/functions/cil-callmap.ts +642 -430
- package/.framework/functions/cil-config.ts +139 -135
- package/.framework/functions/cil-context.ts +214 -127
- package/.framework/functions/cil-doc.ts +587 -458
- package/.framework/functions/cil-embeddings.ts +453 -364
- package/.framework/functions/cil-graph.ts +427 -142
- package/.framework/functions/cil-ingest.ts +1418 -1154
- package/.framework/functions/cil-pipeline.ts +276 -21
- package/.framework/functions/cil-project.ts +659 -132
- package/.framework/functions/cil-validate.ts +198 -164
- package/.framework/functions/debug-auth.ts +57 -55
- package/.framework/functions/deliveries.ts +80 -21
- package/.framework/functions/embeddings.ts +1023 -318
- package/.framework/functions/eval-harness.ts +146 -108
- package/.framework/functions/integration-outbound.ts +205 -75
- package/.framework/functions/integration-routes.ts +128 -23
- package/.framework/functions/integrations.ts +125 -100
- package/.framework/functions/invites.ts +1095 -460
- package/.framework/functions/item-progress.ts +158 -102
- package/.framework/functions/kb.ts +34 -10
- package/.framework/functions/logs.ts +133 -133
- package/.framework/functions/observability.ts +152 -122
- package/.framework/functions/pipeline-executions.ts +147 -132
- package/.framework/functions/pipelines.ts +134 -119
- package/.framework/functions/prompt-configs.ts +96 -80
- package/.framework/functions/roles.ts +112 -82
- package/.framework/functions/security.ts +450 -0
- package/.framework/functions/system-cron.ts +117 -80
- package/.framework/functions/system.ts +158 -98
- package/.framework/functions/tests.ts +29 -29
- package/.framework/functions/timers.ts +94 -95
- package/.framework/functions/trigger-scheduler.ts +10 -0
- package/.framework/functions/triggers.ts +179 -149
- package/.framework/functions/types.ts +137 -125
- package/.framework/mcp/index.ts +133 -0
- package/.framework/mcp/load-env.ts +60 -0
- package/.framework/mcp/shared/app-manifest.ts +275 -0
- package/.framework/mcp/shared/db.ts +477 -0
- package/.framework/mcp/shared/kb.ts +118 -0
- package/.framework/mcp/tools/architect.ts +431 -0
- package/.framework/mcp/tools/cil/context.ts +345 -0
- package/.framework/mcp/tools/cil/graph.ts +242 -0
- package/.framework/mcp/tools/cil/ingest.ts +1217 -0
- package/.framework/mcp/tools/cil/pipeline-orchestrator.ts +693 -0
- package/.framework/mcp/tools/cil/pipeline.ts +767 -0
- package/.framework/mcp/tools/cil/project.ts +791 -0
- package/.framework/mcp/tools/cil/retrieval.ts +336 -0
- package/.framework/mcp/tools/cil/search-core.ts +454 -0
- package/.framework/mcp/tools/cil/search.ts +97 -0
- package/.framework/mcp/tools/cil/suggest.ts +186 -0
- package/.framework/mcp/tools/cil/validate.ts +1369 -0
- package/.framework/mcp/tools/kb/delete.ts +139 -0
- package/.framework/mcp/tools/kb/index.ts +52 -0
- package/.framework/mcp/tools/kb/ingest.ts +84 -0
- package/.framework/mcp/tools/kb/list-types.ts +102 -0
- package/.framework/mcp/tools/kb/publish.ts +100 -0
- package/.framework/mcp/tools/kb/reindex.ts +86 -0
- package/.framework/mcp/tools/kb/revoke.ts +85 -0
- package/.framework/mcp/tools/kb/search.ts +101 -0
- package/.framework/mcp/tools/kb/upsert.ts +125 -0
- package/.framework/mcp/tools/observability.ts +510 -0
- package/.framework/migrations/001_core_schema.sql +15 -0
- package/.framework/migrations/002_core_rls_and_functions.sql +15 -0
- package/.framework/migrations/003_core_system_data.sql +16 -1
- package/.framework/migrations/004_core_rpc_and_broker.sql +17 -1
- package/.framework/migrations/005_core_observability.sql +17 -1
- package/.framework/migrations/006_security_hardening_rls.sql +15 -0
- package/.framework/migrations/007_kb_article_list.sql +17 -1
- package/.framework/migrations/008_items_target.sql +15 -0
- package/.framework/migrations/009_roles_slug_unique.sql +15 -0
- package/.framework/migrations/010_auth_user_trigger.sql +15 -0
- package/.framework/migrations/011_spine_system_account.sql +16 -0
- package/.framework/migrations/012_service_role_grants.sql +16 -0
- package/.framework/migrations/013_get_account_apps_role_filter.sql +15 -0
- package/.framework/migrations/014_apps_required_roles.sql +16 -0
- package/.framework/migrations/015_types_kind_slug_unique.sql +15 -0
- package/.framework/migrations/016_cil_types.sql +281 -0
- package/.framework/migrations/017_cil_stable_ids.sql +37 -0
- package/.framework/migrations/018_runtime_tables.sql +129 -0
- package/.framework/migrations/019_agent_prompt_columns.sql +56 -0
- package/.framework/migrations/020_schema_reconciliation.sql +67 -0
- package/.framework/migrations/021_kb_embedding_lifecycle.sql +31 -0
- package/.framework/migrations/032_cil_status_migration.sql +73 -0
- package/.framework/migrations/033_cil_versioning.sql +73 -0
- package/.framework/migrations/034_match_embeddings_knn.sql +115 -0
- package/.framework/migrations/035_rate_limits.sql +55 -0
- package/.framework/migrations/036_demo_record_flags.sql +72 -0
- package/.framework/migrations/037_kb_types_canonical.sql +244 -0
- package/.framework/migrations/038_drop_demo_record_flags.sql +38 -0
- package/.framework/migrations/042_registration_hierarchy.sql +309 -0
- package/.framework/migrations/043_policy_actor_cleanup.sql +39 -0
- package/.framework/migrations/044_match_embeddings_filtered_knn.sql +151 -0
- package/.framework/migrations/045_security_critical_rls.sql +139 -0
- package/.framework/migrations/046_security_missing_rls.sql +79 -0
- package/.framework/migrations/047_people_updated_by.sql +27 -0
- package/.framework/migrations/048_watcher_last_seen_at.sql +24 -0
- package/.framework/migrations/049_security_blocklist.sql +148 -0
- package/.framework/migrations/050_notifications.sql +49 -0
- package/.framework/migrations/051_message_agent_fields.sql +74 -0
- package/.framework/migrations/052_registration_security.sql +421 -0
- package/.framework/migrations/053_builtin_action_seeds.sql +66 -0
- package/.framework/migrations/054_kb_ingest_lease.sql +157 -0
- package/.framework/migrations/055_type_id_drift_reconciliation.sql +33 -0
- package/.framework/migrations/056_slug_column_reconciliation.sql +38 -0
- package/.framework/migrations/057_pipelines_slug_identity.sql +14 -0
- package/.framework/migrations/058_account_data_field_declarations.sql +53 -0
- package/.framework/migrations/059_registration_placement_fixes.sql +269 -0
- package/.framework/migrations/060_account_person_record_permissions.sql +38 -0
- package/.framework/migrations/061_fk_dedup.sql +32 -0
- package/.framework/public/spine-logo.svg +10 -3
- package/.framework/scripts/app-install-cli.ts +190 -93
- package/.framework/scripts/assemble-frontend.sh +127 -44
- package/.framework/scripts/assemble-functions.sh +128 -30
- package/.framework/scripts/boundary-check.sh +6 -2
- package/.framework/scripts/build-manifest.sh +24 -68
- package/.framework/scripts/check-core-integrity.sh +15 -76
- package/.framework/scripts/checksum-manifest.mts +343 -0
- package/.framework/scripts/cil-migrate-markers.ts +403 -0
- package/.framework/scripts/fix-cil-markers.mjs +176 -0
- package/.framework/scripts/verify-integrity.sh +21 -57
- package/.framework/scripts/verify-manifest.mts +305 -0
- package/.framework/seeds/types/funnel_signal_use.json +74 -21
- package/.framework/seeds/types/spine_instance.json +73 -21
- package/.framework/src/App.tsx +118 -72
- package/.framework/src/apps/admin/index.tsx +855 -58
- package/.framework/src/components/AppWrapper.tsx +43 -45
- package/.framework/src/components/CustomAppLoader.tsx +160 -116
- package/.framework/src/components/admin/AdminListPage.tsx +46 -44
- package/.framework/src/components/admin/AdminSidebar.tsx +57 -47
- package/.framework/src/components/admin/AdminStatsCard.tsx +46 -44
- package/.framework/src/components/admin/PageInstructions.tsx +98 -2
- package/.framework/src/components/admin/SortableTableHeader.tsx +44 -45
- package/.framework/src/components/app-shell/GenericAppShell.tsx +64 -65
- package/.framework/src/components/app-shell/GenericDetailPage.tsx +44 -47
- package/.framework/src/components/app-shell/GenericListPage.tsx +45 -49
- package/.framework/src/components/app-sidebar.tsx +42 -45
- package/.framework/src/components/auth/ProtectedRoute.tsx +48 -41
- package/.framework/src/components/auth/TurnstileWidget.tsx +27 -0
- package/.framework/src/components/kb/KBArticleEditor.tsx +231 -22
- package/.framework/src/components/kb/KBArticleList.tsx +251 -10
- package/.framework/src/components/layout/AppShell.tsx +51 -45
- package/.framework/src/components/layout/Header.tsx +42 -43
- package/.framework/src/components/layout/Layout.tsx +46 -46
- package/.framework/src/components/layout/Sidebar.tsx +196 -96
- package/.framework/src/components/runtime/DataDetailHeader.tsx +55 -30
- package/.framework/src/components/runtime/DataDetailPage.tsx +31 -269
- package/.framework/src/components/runtime/DataFilters.tsx +49 -74
- package/.framework/src/components/runtime/DataHeader.tsx +53 -32
- package/.framework/src/components/runtime/DataListPage.tsx +51 -155
- package/.framework/src/components/runtime/DataStats.tsx +66 -44
- package/.framework/src/components/runtime/DataTable.tsx +49 -149
- package/.framework/src/components/runtime/SchemaDetailForm.tsx +45 -75
- package/.framework/src/components/runtime/index.ts +119 -16
- package/.framework/src/components/search-form.tsx +46 -29
- package/.framework/src/components/shared/AgentView.tsx +65 -48
- package/.framework/src/components/shared/FieldRenderer.tsx +144 -50
- package/.framework/src/components/shared/InviteManager.tsx +207 -97
- package/.framework/src/components/shared/MemberList.tsx +97 -0
- package/.framework/src/components/shared/SchemaFields.tsx +107 -86
- package/.framework/src/components/ui/DataTable.tsx +80 -68
- package/.framework/src/components/ui/Form.tsx +157 -146
- package/.framework/src/components/ui/ItemCard.tsx +74 -67
- package/.framework/src/components/ui/ItemListView.tsx +73 -68
- package/.framework/src/components/ui/LoadingSpinner.tsx +43 -48
- package/.framework/src/components/ui/Modal.tsx +78 -68
- package/.framework/src/components/ui/RichTextEditor.tsx +89 -69
- package/.framework/src/components/ui/accordion.tsx +85 -86
- package/.framework/src/components/ui/alert-dialog.tsx +197 -184
- package/.framework/src/components/ui/alert.tsx +105 -94
- package/.framework/src/components/ui/aspect-ratio.tsx +57 -43
- package/.framework/src/components/ui/avatar.tsx +122 -107
- package/.framework/src/components/ui/badge.tsx +60 -55
- package/.framework/src/components/ui/breadcrumb.tsx +127 -128
- package/.framework/src/components/ui/button-group.tsx +86 -72
- package/.framework/src/components/ui/button.tsx +71 -50
- package/.framework/src/components/ui/calendar.tsx +72 -57
- package/.framework/src/components/ui/card.tsx +136 -129
- package/.framework/src/components/ui/carousel.tsx +226 -107
- package/.framework/src/components/ui/chart.tsx +252 -147
- package/.framework/src/components/ui/checkbox.tsx +43 -44
- package/.framework/src/components/ui/collapsible.tsx +86 -71
- package/.framework/src/components/ui/combobox.tsx +282 -249
- package/.framework/src/components/ui/command.tsx +158 -146
- package/.framework/src/components/ui/context-menu.tsx +239 -240
- package/.framework/src/components/ui/dialog.tsx +174 -157
- package/.framework/src/components/ui/direction.tsx +72 -56
- package/.framework/src/components/ui/drawer.tsx +168 -169
- package/.framework/src/components/ui/dropdown-menu.tsx +254 -223
- package/.framework/src/components/ui/empty.tsx +131 -120
- package/.framework/src/components/ui/field.tsx +205 -173
- package/.framework/src/components/ui/hover-card.tsx +71 -72
- package/.framework/src/components/ui/input-group.tsx +148 -133
- package/.framework/src/components/ui/input-otp.tsx +99 -86
- package/.framework/src/components/ui/input.tsx +43 -41
- package/.framework/src/components/ui/item.tsx +207 -185
- package/.framework/src/components/ui/kbd.tsx +57 -56
- package/.framework/src/components/ui/label.tsx +45 -41
- package/.framework/src/components/ui/menubar.tsx +268 -236
- package/.framework/src/components/ui/native-select.tsx +85 -86
- package/.framework/src/components/ui/navigation-menu.tsx +166 -156
- package/.framework/src/components/ui/pagination.tsx +131 -141
- package/.framework/src/components/ui/popover.tsx +125 -128
- package/.framework/src/components/ui/progress.tsx +47 -44
- package/.framework/src/components/ui/radio-group.tsx +60 -55
- package/.framework/src/components/ui/resizable.tsx +85 -72
- package/.framework/src/components/ui/scroll-area.tsx +57 -58
- package/.framework/src/components/ui/select.tsx +182 -169
- package/.framework/src/components/ui/separator.tsx +42 -43
- package/.framework/src/components/ui/sheet.tsx +170 -159
- package/.framework/src/components/ui/sidebar.tsx +395 -398
- package/.framework/src/components/ui/skeleton.tsx +42 -43
- package/.framework/src/components/ui/slider.tsx +61 -44
- package/.framework/src/components/ui/sonner.tsx +44 -44
- package/.framework/src/components/ui/spinner.tsx +47 -42
- package/.framework/src/components/ui/switch.tsx +56 -42
- package/.framework/src/components/ui/table-primitives.tsx +272 -132
- package/.framework/src/components/ui/table.tsx +140 -142
- package/.framework/src/components/ui/tabs.tsx +110 -93
- package/.framework/src/components/ui/textarea.tsx +43 -44
- package/.framework/src/components/ui/toggle-group.tsx +87 -71
- package/.framework/src/components/ui/toggle.tsx +56 -56
- package/.framework/src/components/ui/tooltip.tsx +99 -85
- package/.framework/src/contexts/AppContext.tsx +166 -114
- package/.framework/src/contexts/AuthContext.tsx +232 -137
- package/.framework/src/hooks/use-mobile.ts +43 -44
- package/.framework/src/hooks/useApi.ts +185 -172
- package/.framework/src/hooks/useAppPath.ts +31 -29
- package/.framework/src/hooks/useApps.ts +77 -42
- package/.framework/src/hooks/useEntityList.ts +66 -29
- package/.framework/src/hooks/useEntityRecord.ts +76 -32
- package/.framework/src/hooks/useForm.ts +62 -30
- package/.framework/src/hooks/useListSchema.ts +60 -43
- package/.framework/src/hooks/useSchemaRecord.ts +115 -95
- package/.framework/src/lib/api.ts +258 -134
- package/.framework/src/lib/registration.ts +181 -0
- package/.framework/src/lib/supabase.ts +118 -81
- package/.framework/src/lib/utils.ts +266 -266
- package/.framework/src/main.tsx +43 -44
- package/.framework/src/pages/DashboardPage.tsx +44 -43
- package/.framework/src/pages/NoAppPage.tsx +50 -0
- package/.framework/src/pages/NotFoundPage.tsx +32 -29
- package/.framework/src/pages/SetupPage.tsx +34 -33
- package/.framework/src/pages/admin/AIAgentDetailPage.tsx +69 -58
- package/.framework/src/pages/admin/AIAgentsPage.tsx +43 -40
- package/.framework/src/pages/admin/APIKeyDetailPage.tsx +63 -55
- package/.framework/src/pages/admin/APIKeysPage.tsx +44 -42
- package/.framework/src/pages/admin/AlertsConfigPage.tsx +117 -94
- package/.framework/src/pages/admin/AppDetailPage.tsx +48 -42
- package/.framework/src/pages/admin/AppsPage.tsx +45 -42
- package/.framework/src/pages/admin/DeliveriesPage.tsx +49 -17
- package/.framework/src/pages/admin/DesignedPage.tsx +31 -30
- package/.framework/src/pages/admin/EmbeddingDetailPage.tsx +58 -0
- package/.framework/src/pages/admin/EmbeddingsPage.tsx +49 -0
- package/.framework/src/pages/admin/ExtendedShadcnTestPage.tsx +31 -29
- package/.framework/src/pages/admin/IncrementalShadcnTestPage.tsx +46 -29
- package/.framework/src/pages/admin/IntegratedDashboard.tsx +32 -29
- package/.framework/src/pages/admin/IntegrationDetailPage.tsx +68 -55
- package/.framework/src/pages/admin/IntegrationsPage.tsx +45 -42
- package/.framework/src/pages/admin/InvitesPage.tsx +60 -44
- package/.framework/src/pages/admin/LogsPage.tsx +87 -137
- package/.framework/src/pages/admin/MinimalShadcnTestPage.tsx +31 -29
- package/.framework/src/pages/admin/ObservabilityDashboard.tsx +150 -89
- package/.framework/src/pages/admin/PipelineDetailPage.tsx +77 -104
- package/.framework/src/pages/admin/PipelineExecutionsPage.tsx +44 -43
- package/.framework/src/pages/admin/PipelinesPage.tsx +59 -145
- package/.framework/src/pages/admin/PromptConfigDetailPage.tsx +53 -42
- package/.framework/src/pages/admin/PromptConfigsPage.tsx +47 -117
- package/.framework/src/pages/admin/ProperlyDesignedPage.tsx +31 -44
- package/.framework/src/pages/admin/RoleDetailPage.tsx +49 -92
- package/.framework/src/pages/admin/RolesPage.tsx +47 -164
- package/.framework/src/pages/admin/SecurityPage.tsx +310 -0
- package/.framework/src/pages/admin/SelectTestPage.tsx +30 -32
- package/.framework/src/pages/admin/ShadcnTestPage.tsx +37 -44
- package/.framework/src/pages/admin/SimpleDashboard.tsx +32 -44
- package/.framework/src/pages/admin/TestRunDetailPage.tsx +97 -44
- package/.framework/src/pages/admin/TestingDashboard.tsx +126 -71
- package/.framework/src/pages/admin/TimerDetailPage.tsx +67 -55
- package/.framework/src/pages/admin/TimersPage.tsx +44 -42
- package/.framework/src/pages/admin/TriggerDetailPage.tsx +47 -42
- package/.framework/src/pages/admin/TriggersPage.tsx +58 -57
- package/.framework/src/pages/admin/TypeDetailPage.tsx +91 -55
- package/.framework/src/pages/admin/TypesPage.tsx +45 -42
- package/.framework/src/pages/admin/cil/CILAgentPage.tsx +258 -128
- package/.framework/src/pages/admin/cil/CILChunkDetailPage.tsx +127 -123
- package/.framework/src/pages/admin/cil/CILDashboardPage.tsx +308 -235
- package/.framework/src/pages/admin/cil/CILFileListPage.tsx +159 -110
- package/.framework/src/pages/admin/cil/CILFileSelectPage.tsx +432 -0
- package/.framework/src/pages/admin/cil/CILGraphPage.tsx +200 -178
- package/.framework/src/pages/admin/cil/CILIngestionPage.tsx +286 -239
- package/.framework/src/pages/admin/cil/CILProjectsPage.tsx +211 -90
- package/.framework/src/pages/admin/cil/CILSearchPage.tsx +156 -143
- package/.framework/src/pages/admin/cil/CILSuggestionsPage.tsx +379 -0
- package/.framework/src/pages/admin/cil/CILVersionsPage.tsx +337 -0
- package/.framework/src/pages/admin/cil/FlexiblePipelinePage.tsx +219 -214
- package/.framework/src/pages/admin/kb/KBAdminPage.tsx +64 -0
- package/.framework/src/pages/auth/AuthConfirmPage.tsx +135 -65
- package/.framework/src/pages/auth/ForgotPasswordPage.tsx +39 -31
- package/.framework/src/pages/auth/LoginPage.tsx +38 -32
- package/.framework/src/pages/auth/PendingApprovalPage.tsx +31 -28
- package/.framework/src/pages/auth/RegisterPage.tsx +429 -155
- package/.framework/src/pages/spine-framework/APIPage.tsx +33 -30
- package/.framework/src/pages/spine-framework/CLIPage.tsx +32 -30
- package/.framework/src/types/auth.ts +101 -93
- package/.framework/src/types/types.ts +283 -262
- package/.framework/templates/project.json +87 -0
- package/.framework/templates/spine.config.neutral.json +7 -0
- package/.framework/tests/api/api-surface.test.ts +381 -0
- package/.framework/tests/fixtures/seed.ts +427 -0
- package/.framework/tests/fixtures/teardown.ts +228 -0
- package/.framework/tests/reporter.ts +351 -0
- package/.framework/tests/setup.ts +135 -0
- package/.framework/tests/ui/ui-sweep.ts +278 -0
- package/.framework/tests/unit/admin-data-logger.test.ts +310 -0
- package/.framework/tests/unit/agent-runner.test.ts +2389 -0
- package/.framework/tests/unit/ai-interactions.test.ts +81 -0
- package/.framework/tests/unit/app-manifest.test.ts +359 -0
- package/.framework/tests/unit/assembly-scripts.test.ts +172 -0
- package/.framework/tests/unit/cil-determinism.test.ts +85 -0
- package/.framework/tests/unit/core-isolation.test.ts +153 -0
- package/.framework/tests/unit/funnel-signals.test.ts +135 -0
- package/.framework/tests/unit/install-app.test.ts +1759 -0
- package/.framework/tests/unit/invites-security.test.ts +572 -0
- package/.framework/tests/unit/kb-ingest-lease.test.ts +287 -0
- package/.framework/tests/unit/kb-search.test.ts +119 -0
- package/.framework/tests/unit/migrate.test.ts +509 -0
- package/.framework/tests/unit/notify.test.ts +136 -0
- package/.framework/tests/unit/permissions.test.ts +269 -0
- package/.framework/tests/unit/pipeline-runner.test.ts +755 -0
- package/.framework/tests/unit/principal-cache.test.ts +138 -0
- package/.framework/tests/unit/retrieval-golden.test.ts +520 -0
- package/.framework/tests/unit/runtime-isolation.test.ts +642 -0
- package/.framework/tests/unit/schema-utils.test.ts +225 -0
- package/.framework/tests/unit/trigger-engine.test.ts +513 -0
- package/.framework/tests/unit/validate-app.test.ts +527 -0
- package/README.md +34 -3
- package/bin/spine-framework.cjs +1 -0
- package/config/tailwind.config.cjs +7 -0
- package/config/tsconfig.functions.json +42 -0
- package/config/tsconfig.json +37 -9
- package/config/vite.config.ts +31 -2
- package/netlify.toml +31 -3
- package/package.json +46 -29
- package/scripts/assemble-frontend.sh +127 -44
- package/scripts/assemble-functions.sh +127 -29
- package/scripts/boundary-check.sh +6 -2
- package/scripts/build-manifest.sh +24 -68
- package/scripts/checksum-manifest.mts +345 -0
- package/scripts/dev-clean.sh +86 -0
- package/scripts/dev-netlify.sh +49 -0
- package/scripts/netlify-dev-wrapper.sh +2 -0
- package/scripts/verify-install.ts +358 -0
- package/scripts/verify-integrity.sh +21 -57
- package/scripts/verify-manifest.mts +305 -0
- package/templates/project/gitignore +45 -0
- package/{config → templates/project}/package-lock.json +22335 -9366
- package/vitest.config.ts +46 -0
- package/.framework/public/spine.config.json +0 -91
- package/config/deno.lock +0 -108
- package/config/tsconfig.node.tsbuildinfo +0 -1
- package/config/tsconfig.tsbuildinfo +0 -1
- package/config/vite.config.d.ts +0 -2
- package/custom/.devin/AGENT.md +0 -357
- package/custom/.devin/skills/install-app/SKILL.md +0 -39
- package/custom/.devin/skills/spine-workbench-discovery/SKILL.md +0 -39
- package/custom/.devin/skills/spine-workbench-idea/SKILL.md +0 -36
- package/custom/.devin/skills/spine-workbench-implement/SKILL.md +0 -46
- package/custom/.devin/skills/spine-workbench-initiative/SKILL.md +0 -28
- package/custom/.devin/skills/spine-workbench-plan/SKILL.md +0 -38
- package/custom/.devin/workflows/app-install.yaml +0 -83
- package/custom/README.md +0 -79
- package/docs/README.md +0 -15
- package/scripts/app-install-cli.ts +0 -286
- package/scripts/check-core-integrity.sh +0 -82
- package/scripts/ingest-chunks.cjs +0 -202
- package/scripts/kb-chunk-parser.cjs +0 -312
- package/scripts/kb-chunk-parser.ts +0 -330
- package/scripts/kb-ingest-docs.ts +0 -203
- package/scripts/load-test-app-install.ts +0 -484
- package/scripts/test-login.js +0 -33
- package/spine.config.json +0 -91
|
@@ -1,46 +1,114 @@
|
|
|
1
|
+
// CIL[BEGIN stable_id="~/.framework/functions/ai-agents.ts:module_header:module_header" type="module_header" identity="module_header" parent="~/.framework/functions/ai-agents.ts"]
|
|
2
|
+
/**
|
|
3
|
+
* @module functions/ai-agents
|
|
4
|
+
* @audience internal
|
|
5
|
+
* @layer app-specific
|
|
6
|
+
* @stability stable
|
|
7
|
+
*
|
|
8
|
+
* This module provides functionality for AI agents within the application, facilitating their execution and management. It integrates middleware for handling requests, checks permissions, and manages rate limits to ensure system integrity. INVARIANT: Only system administrators can execute certain actions related to agents.
|
|
9
|
+
*
|
|
10
|
+
* @seeAlso functions/_shared/middleware (provides request handling)
|
|
11
|
+
* @seeAlso functions/_shared/permissions (manages access control)
|
|
12
|
+
* @seeAlso functions/_shared/rate-limit (ensures system stability)
|
|
13
|
+
* @seeAlso functions/_shared/agent-runner (executes agent logic)
|
|
14
|
+
*
|
|
15
|
+
* @cil-generated
|
|
16
|
+
*/
|
|
17
|
+
|
|
18
|
+
|
|
19
|
+
|
|
20
|
+
|
|
21
|
+
|
|
1
22
|
|
|
2
23
|
|
|
3
24
|
|
|
4
25
|
|
|
5
26
|
|
|
6
27
|
|
|
7
|
-
// CIL[BEGIN chunk_id="ai-agents_module_header_1784019432" type="module_header" identity="imports" parent="none"]
|
|
8
|
-
// CIL[DOC-MACRO purpose="Import dependencies for AI agents CRUD operations"]
|
|
9
|
-
// CIL[DOC-RESPONSIBILITY responsibility="Provide core middleware, database joins, audit logging, and permissions"]
|
|
10
|
-
// CIL[DOC-CONTEXT module="ai-agents" layer="api-handler" related_files="[\"custom/apps/cortex/pages/operations/OperationsDashboard.tsx\",\".framework/src/pages/admin/TypeDetailPage.tsx\",\".framework/functions/_shared/schema-utils.ts\",\".framework/functions/_shared/principal.ts\",\"custom/apps/portal/pages/ContentPage.tsx\",\"\\\"]"]
|
|
11
|
-
// CIL[DOC-CONTRACT inputs="none" outputs="imported_modules" errors="none" side_effects="none"]
|
|
12
|
-
// CIL[DOC-MICRO logic_summary="Imports required modules and configures permissions engine" notable_decisions="[]"]
|
|
13
|
-
// CIL[DOC-CONFIDENCE pass="second" score="0.95" flags="none"]
|
|
14
|
-
// CIL[DOC-STABILITY stability="stable"]
|
|
15
|
-
// CIL[DOC-AUDIENCE audience="developer"]
|
|
16
|
-
// CIL[DOC-VECTOR type="context" content="Layer: api-handler. Direct callers: 0. Direct calls: 0. Related files: custom/apps/cortex/pages/operations/OperationsDashboard.tsx, .framework/src/pages/admin/TypeDetailPage.tsx, .framework/functions/_shared/schema-utils.ts, .framework/functions/_shared/principal.ts, custom/apps/portal/pages/ContentPage.tsx, \."]
|
|
17
|
-
// CIL[DOC-VECTOR type="blast_radius" content="Direct callers: 0. Total affected: 0."]
|
|
18
|
-
// CIL[DOC-VECTOR type="configuration" content="No configuration dependencies."]
|
|
19
|
-
// CIL[DOC-VECTOR type="constraint" content="No test paths identified."]
|
|
20
|
-
// CIL[DOC-VECTOR type="implementation_pattern" content="" status="pending_human_input"]
|
|
21
|
-
// CIL[DOC-VECTOR type="user_journey" content="" status="pending_human_input"]
|
|
22
28
|
import { createHandler } from './_shared/middleware'
|
|
23
29
|
import { adminDb } from './_shared/db'
|
|
24
30
|
import { emitLog } from './_shared/audit'
|
|
25
31
|
import { isSystemAdmin } from './_shared/principal'
|
|
26
32
|
import { PermissionEngine, sanitizeRecordData } from './_shared/permissions'
|
|
33
|
+
import { runAgent, kickAgentEpisode } from './_shared/agent-runner'
|
|
34
|
+
import { checkRateLimit } from './_shared/rate-limit'
|
|
35
|
+
import { detectInjection, emitSecurityEvent, getAppSecurityConfig } from './_shared/security'
|
|
36
|
+
// CIL[END stable_id="~/.framework/functions/ai-agents.ts:module_header:module_header"]
|
|
37
|
+
|
|
38
|
+
|
|
39
|
+
|
|
40
|
+
|
|
41
|
+
|
|
42
|
+
|
|
43
|
+
|
|
44
|
+
|
|
45
|
+
|
|
46
|
+
|
|
47
|
+
|
|
48
|
+
|
|
49
|
+
|
|
50
|
+
|
|
51
|
+
|
|
52
|
+
|
|
53
|
+
// CIL[BEGIN stable_id="~/.framework/functions/ai-agents.ts:permissions:constant" type="constant" identity="permissions" parent="~/.framework/functions/ai-agents.ts"]
|
|
54
|
+
/**
|
|
55
|
+
* The 'permissions' constant provides access to the PermissionEngine, allowing for permission management within the module. It exists to facilitate the handling of user permissions in AI agent functionalities.
|
|
56
|
+
*
|
|
57
|
+
* @sideEffects none
|
|
58
|
+
* @stability stable
|
|
59
|
+
* @cil-generated
|
|
60
|
+
*/
|
|
61
|
+
|
|
62
|
+
|
|
63
|
+
|
|
64
|
+
|
|
65
|
+
|
|
66
|
+
|
|
67
|
+
|
|
27
68
|
|
|
28
69
|
const permissions = PermissionEngine as any
|
|
29
|
-
// CIL[END
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
70
|
+
// CIL[END stable_id="~/.framework/functions/ai-agents.ts:permissions:constant"]
|
|
71
|
+
|
|
72
|
+
|
|
73
|
+
|
|
74
|
+
|
|
75
|
+
|
|
76
|
+
|
|
77
|
+
|
|
78
|
+
|
|
79
|
+
|
|
80
|
+
|
|
81
|
+
|
|
82
|
+
|
|
83
|
+
|
|
84
|
+
|
|
85
|
+
|
|
86
|
+
|
|
87
|
+
|
|
88
|
+
|
|
89
|
+
|
|
90
|
+
|
|
91
|
+
|
|
92
|
+
|
|
93
|
+
|
|
94
|
+
// CIL[BEGIN stable_id="~/.framework/functions/ai-agents.ts:list:constant" type="constant" identity="list" parent="~/.framework/functions/ai-agents.ts"]
|
|
95
|
+
/**
|
|
96
|
+
* Fetches a list of AI agents based on query parameters such as agent type and active status. This function is designed to provide a sanitized view of AI agents for the requesting account.
|
|
97
|
+
*
|
|
98
|
+
* @throws Error — Account context required.
|
|
99
|
+
* @sideEffects none
|
|
100
|
+
* @stability stable
|
|
101
|
+
* @calls isSystemAdmin, adminDb.from, ctx.db.from, sanitizeRecordData
|
|
102
|
+
* @cil-generated
|
|
103
|
+
*/
|
|
104
|
+
|
|
105
|
+
|
|
106
|
+
|
|
107
|
+
|
|
108
|
+
|
|
109
|
+
|
|
110
|
+
|
|
111
|
+
|
|
44
112
|
export const list = createHandler(async (ctx, _body) => {
|
|
45
113
|
const { agent_type, is_active, limit = 100, offset = 0 } = ctx.query || {}
|
|
46
114
|
|
|
@@ -76,21 +144,41 @@ export const list = createHandler(async (ctx, _body) => {
|
|
|
76
144
|
|
|
77
145
|
return sanitized
|
|
78
146
|
})
|
|
79
|
-
// CIL[END
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
147
|
+
// CIL[END stable_id="~/.framework/functions/ai-agents.ts:list:constant"]
|
|
148
|
+
|
|
149
|
+
|
|
150
|
+
|
|
151
|
+
|
|
152
|
+
|
|
153
|
+
|
|
154
|
+
|
|
155
|
+
|
|
156
|
+
|
|
157
|
+
|
|
158
|
+
|
|
159
|
+
|
|
160
|
+
|
|
161
|
+
|
|
162
|
+
|
|
163
|
+
|
|
164
|
+
// CIL[BEGIN stable_id="~/.framework/functions/ai-agents.ts:get:constant" type="constant" identity="get" parent="~/.framework/functions/ai-agents.ts"]
|
|
165
|
+
/**
|
|
166
|
+
* Fetches an AI agent record by its ID from the database. This function ensures that only authorized users can access the data based on their role.
|
|
167
|
+
*
|
|
168
|
+
* @throws Error — Agent ID is required, Error — database query error
|
|
169
|
+
* @sideEffects none
|
|
170
|
+
* @stability stable
|
|
171
|
+
* @calls adminDb.from('ai_agents'), ctx.db.from('ai_agents'), sanitizeRecordData
|
|
172
|
+
* @cil-generated
|
|
173
|
+
*/
|
|
174
|
+
|
|
175
|
+
|
|
176
|
+
|
|
177
|
+
|
|
178
|
+
|
|
179
|
+
|
|
180
|
+
|
|
181
|
+
|
|
94
182
|
export const get = createHandler(async (ctx, _body) => {
|
|
95
183
|
const { id } = ctx.query || {}
|
|
96
184
|
|
|
@@ -110,21 +198,41 @@ export const get = createHandler(async (ctx, _body) => {
|
|
|
110
198
|
|
|
111
199
|
return await sanitizeRecordData(ctx, data, 'ai_agent')
|
|
112
200
|
})
|
|
113
|
-
// CIL[END
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
201
|
+
// CIL[END stable_id="~/.framework/functions/ai-agents.ts:get:constant"]
|
|
202
|
+
|
|
203
|
+
|
|
204
|
+
|
|
205
|
+
|
|
206
|
+
|
|
207
|
+
|
|
208
|
+
|
|
209
|
+
|
|
210
|
+
|
|
211
|
+
|
|
212
|
+
|
|
213
|
+
|
|
214
|
+
|
|
215
|
+
|
|
216
|
+
|
|
217
|
+
|
|
218
|
+
// CIL[BEGIN stable_id="~/.framework/functions/ai-agents.ts:create:constant" type="constant" identity="create" parent="~/.framework/functions/ai-agents.ts"]
|
|
219
|
+
/**
|
|
220
|
+
* Creates a new AI agent in the database based on the provided parameters. It ensures that required fields are present and that the user context is valid before performing the insertion.
|
|
221
|
+
*
|
|
222
|
+
* @throws Error — name and agent_type are required; Error — User context (person and account) required; Error — database insertion error.
|
|
223
|
+
* @sideEffects Inserts a new record into the 'ai_agents' table; emits a log event for the creation of the AI agent.
|
|
224
|
+
* @stability stable
|
|
225
|
+
* @calls ctx.db.from('ai_agents'), emitLog
|
|
226
|
+
* @cil-generated
|
|
227
|
+
*/
|
|
228
|
+
|
|
229
|
+
|
|
230
|
+
|
|
231
|
+
|
|
232
|
+
|
|
233
|
+
|
|
234
|
+
|
|
235
|
+
|
|
128
236
|
export const create = createHandler(async (ctx, body) => {
|
|
129
237
|
const { app_id, name, description, agent_type, model_config, system_prompt, tools, capabilities, constraints, metadata } = body
|
|
130
238
|
|
|
@@ -164,21 +272,41 @@ export const create = createHandler(async (ctx, body) => {
|
|
|
164
272
|
|
|
165
273
|
return data
|
|
166
274
|
})
|
|
167
|
-
// CIL[END
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
|
|
180
|
-
|
|
181
|
-
|
|
275
|
+
// CIL[END stable_id="~/.framework/functions/ai-agents.ts:create:constant"]
|
|
276
|
+
|
|
277
|
+
|
|
278
|
+
|
|
279
|
+
|
|
280
|
+
|
|
281
|
+
|
|
282
|
+
|
|
283
|
+
|
|
284
|
+
|
|
285
|
+
|
|
286
|
+
|
|
287
|
+
|
|
288
|
+
|
|
289
|
+
|
|
290
|
+
|
|
291
|
+
|
|
292
|
+
// CIL[BEGIN stable_id="~/.framework/functions/ai-agents.ts:update:constant" type="constant" identity="update" parent="~/.framework/functions/ai-agents.ts"]
|
|
293
|
+
/**
|
|
294
|
+
* Updates an AI agent's properties in the database based on the provided ID and update data. It ensures that the user context is valid and that the ID is provided before performing the update.
|
|
295
|
+
*
|
|
296
|
+
* @throws Error — Agent ID is required, Error — User context (person and account) required
|
|
297
|
+
* @sideEffects Database update on 'ai_agents' table, logging of the update event.
|
|
298
|
+
* @stability stable
|
|
299
|
+
* @calls ctx.db.from('ai_agents'), emitLog
|
|
300
|
+
* @cil-generated
|
|
301
|
+
*/
|
|
302
|
+
|
|
303
|
+
|
|
304
|
+
|
|
305
|
+
|
|
306
|
+
|
|
307
|
+
|
|
308
|
+
|
|
309
|
+
|
|
182
310
|
export const update = createHandler(async (ctx, body) => {
|
|
183
311
|
const id = body?.id || ctx.query?.id
|
|
184
312
|
const { id: _bodyId, ...updates } = body || {}
|
|
@@ -213,21 +341,41 @@ export const update = createHandler(async (ctx, body) => {
|
|
|
213
341
|
|
|
214
342
|
return data
|
|
215
343
|
})
|
|
216
|
-
// CIL[END
|
|
217
|
-
|
|
218
|
-
|
|
219
|
-
|
|
220
|
-
|
|
221
|
-
|
|
222
|
-
|
|
223
|
-
|
|
224
|
-
|
|
225
|
-
|
|
226
|
-
|
|
227
|
-
|
|
228
|
-
|
|
229
|
-
|
|
230
|
-
|
|
344
|
+
// CIL[END stable_id="~/.framework/functions/ai-agents.ts:update:constant"]
|
|
345
|
+
|
|
346
|
+
|
|
347
|
+
|
|
348
|
+
|
|
349
|
+
|
|
350
|
+
|
|
351
|
+
|
|
352
|
+
|
|
353
|
+
|
|
354
|
+
|
|
355
|
+
|
|
356
|
+
|
|
357
|
+
|
|
358
|
+
|
|
359
|
+
|
|
360
|
+
|
|
361
|
+
// CIL[BEGIN stable_id="~/.framework/functions/ai-agents.ts:remove:constant" type="constant" identity="remove" parent="~/.framework/functions/ai-agents.ts"]
|
|
362
|
+
/**
|
|
363
|
+
* The 'remove' constant defines a handler for deleting an AI agent from the database based on its ID. It ensures that the ID is provided and logs the deletion event.
|
|
364
|
+
*
|
|
365
|
+
* @throws Error — Agent ID is required, Error — Agent not found, Error — database error during deletion
|
|
366
|
+
* @sideEffects Deletes an entry from the 'ai_agents' table, emits a log event.
|
|
367
|
+
* @stability stable
|
|
368
|
+
* @calls ctx.db.from('ai_agents'), ctx.db.select, ctx.db.eq, ctx.db.single, ctx.db.delete, emitLog
|
|
369
|
+
* @cil-generated
|
|
370
|
+
*/
|
|
371
|
+
|
|
372
|
+
|
|
373
|
+
|
|
374
|
+
|
|
375
|
+
|
|
376
|
+
|
|
377
|
+
|
|
378
|
+
|
|
231
379
|
export const remove = createHandler(async (ctx, _body) => {
|
|
232
380
|
const id = ctx.query?.id
|
|
233
381
|
|
|
@@ -257,26 +405,196 @@ export const remove = createHandler(async (ctx, _body) => {
|
|
|
257
405
|
|
|
258
406
|
return { success: true }
|
|
259
407
|
})
|
|
260
|
-
// CIL[END
|
|
261
|
-
|
|
262
|
-
|
|
263
|
-
|
|
264
|
-
|
|
265
|
-
|
|
266
|
-
|
|
267
|
-
|
|
268
|
-
|
|
269
|
-
|
|
270
|
-
|
|
271
|
-
|
|
272
|
-
|
|
273
|
-
|
|
274
|
-
|
|
408
|
+
// CIL[END stable_id="~/.framework/functions/ai-agents.ts:remove:constant"]
|
|
409
|
+
|
|
410
|
+
|
|
411
|
+
|
|
412
|
+
|
|
413
|
+
|
|
414
|
+
|
|
415
|
+
|
|
416
|
+
|
|
417
|
+
|
|
418
|
+
|
|
419
|
+
|
|
420
|
+
|
|
421
|
+
|
|
422
|
+
|
|
423
|
+
|
|
424
|
+
|
|
425
|
+
// CIL[BEGIN stable_id="~/.framework/functions/ai-agents.ts:run:constant" type="constant" identity="run" parent="~/.framework/functions/ai-agents.ts"]
|
|
426
|
+
/**
|
|
427
|
+
* The 'run' constant defines an asynchronous handler that processes user messages within a specified thread context. It ensures that necessary parameters are provided and manages the execution of an agent based on the provided mode.
|
|
428
|
+
*
|
|
429
|
+
* @throws Error — thread_id is required, Error — User context (person and account) required, Error — Thread not found
|
|
430
|
+
* @sideEffects Database reads from 'threads' and updates to 'threads' based on agent execution.
|
|
431
|
+
* @stability stable
|
|
432
|
+
* @calls checkRateLimit, runAgent, adminDb.from('threads'), adminDb.select, adminDb.eq, adminDb.single
|
|
433
|
+
* @cil-generated
|
|
434
|
+
*/
|
|
435
|
+
|
|
436
|
+
|
|
437
|
+
|
|
438
|
+
|
|
439
|
+
|
|
440
|
+
|
|
441
|
+
|
|
442
|
+
|
|
443
|
+
export const run = createHandler(async (ctx, body) => {
|
|
444
|
+
const { thread_id, user_message, mode } = body || {}
|
|
445
|
+
if (!thread_id) {
|
|
446
|
+
throw new Error('thread_id is required')
|
|
447
|
+
}
|
|
448
|
+
if (!ctx.principal || ctx.principal.id === 'anonymous' || !ctx.accountId) {
|
|
449
|
+
throw new Error('User context (person and account) required')
|
|
450
|
+
}
|
|
451
|
+
|
|
452
|
+
const { data, error: err } = await ctx.db
|
|
453
|
+
.from('threads')
|
|
454
|
+
.select('*, type:types(*)')
|
|
455
|
+
.eq('id', thread_id)
|
|
456
|
+
.single()
|
|
457
|
+
if (err || !data) throw new Error(err?.message || 'Thread not found')
|
|
458
|
+
|
|
459
|
+
// Prompt-injection pre-flight. Mode comes from the calling app's
|
|
460
|
+
// config.security.prompt_injection: 'off' | 'flag' (default) | 'block'.
|
|
461
|
+
// 'block' refuses before any tokens are spent — callers translate the
|
|
462
|
+
// error into human-routing; 'flag' audits the hit so the security
|
|
463
|
+
// report can aggregate repeat offenders.
|
|
464
|
+
const injectionHit = detectInjection(user_message)
|
|
465
|
+
if (injectionHit) {
|
|
466
|
+
const secCfg = await getAppSecurityConfig(ctx.appId)
|
|
467
|
+
const injectionMode = secCfg?.prompt_injection ?? 'flag'
|
|
468
|
+
void emitSecurityEvent(ctx, 'security.injection_detected', {
|
|
469
|
+
type: 'thread', id: thread_id, account_id: ctx.accountId
|
|
470
|
+
}, {
|
|
471
|
+
result: injectionMode === 'block' ? 'denied' : 'flagged',
|
|
472
|
+
pattern: injectionHit,
|
|
473
|
+
injection_mode: injectionMode,
|
|
474
|
+
})
|
|
475
|
+
if (injectionMode === 'block') {
|
|
476
|
+
const e: any = new Error('Your message could not be processed automatically. A support specialist will review it.')
|
|
477
|
+
e.statusCode = 400
|
|
478
|
+
throw e
|
|
479
|
+
}
|
|
480
|
+
}
|
|
481
|
+
|
|
482
|
+
const runMode = (mode as 'step' | 'complete' | 'episode') || 'complete'
|
|
483
|
+
|
|
484
|
+
// Episode single-flight: the in-flight driver stamps driver_id +
|
|
485
|
+
// driver_heartbeat_at into research_state. A different driver asking to
|
|
486
|
+
// step/kick while the lease is fresh gets 'running' instead of a second
|
|
487
|
+
// interleaved write pass. The owner itself is never refused (its own
|
|
488
|
+
// staleness check is finer-grained), and a lease expires after
|
|
489
|
+
// DRIVER_LEASE_MS so a crashed driver can't wedge the thread.
|
|
490
|
+
const DRIVER_LEASE_MS = 60000
|
|
491
|
+
const existingState = (data as any)?.data?.research_state
|
|
492
|
+
const heartbeatAt = Date.parse(existingState?.driver_heartbeat_at || '')
|
|
493
|
+
const leaseHolder = existingState?.driver_id
|
|
494
|
+
const callerToken = (body?.driver_token as string) || null
|
|
495
|
+
const callerId = callerToken || ctx.requestId
|
|
496
|
+
const leaseLive =
|
|
497
|
+
!!leaseHolder &&
|
|
498
|
+
leaseHolder !== callerId &&
|
|
499
|
+
!!existingState?.status &&
|
|
500
|
+
!['complete', 'awaiting_input', 'failed'].includes(existingState.status) &&
|
|
501
|
+
Number.isFinite(heartbeatAt) &&
|
|
502
|
+
Date.now() - heartbeatAt < DRIVER_LEASE_MS
|
|
503
|
+
|
|
504
|
+
if ((runMode === 'step' || runMode === 'complete') && leaseLive) {
|
|
505
|
+
return { ok: true, thread_id, status: 'running', driver_id: leaseHolder }
|
|
506
|
+
}
|
|
507
|
+
|
|
508
|
+
if (runMode === 'episode') {
|
|
509
|
+
if (leaseLive) {
|
|
510
|
+
return { ok: true, thread_id, status: 'running', detached: true, already_running: true }
|
|
511
|
+
}
|
|
512
|
+
// Debit agent_step only when a new driver will actually start work —
|
|
513
|
+
// lease-refused requests and ticket-creation kicks already debited or
|
|
514
|
+
// started nothing, and counting them would double-charge each episode.
|
|
515
|
+
await checkRateLimit(ctx, 'agent_step')
|
|
516
|
+
// Claim the lease before detaching so a step request landing during
|
|
517
|
+
// resolveAgentConfig still sees a live driver. Shared implementation lives
|
|
518
|
+
// in kickAgentEpisode (also used by ticket-creation handlers).
|
|
519
|
+
const leaseId = callerToken || ctx.requestId
|
|
520
|
+
const kick = await kickAgentEpisode(thread_id, user_message || '', ctx, leaseId, (data as any)?.data)
|
|
521
|
+
if (!kick.claimed) {
|
|
522
|
+
return { ok: true, thread_id, status: 'running', detached: true, already_running: true }
|
|
523
|
+
}
|
|
524
|
+
return { ok: true, thread_id, status: 'running', detached: true }
|
|
525
|
+
}
|
|
526
|
+
|
|
527
|
+
// step/complete modes debit here — same rule: only when work will start.
|
|
528
|
+
await checkRateLimit(ctx, 'agent_step')
|
|
529
|
+
const message = await runAgent(thread_id, user_message || '', ctx, runMode, callerToken || undefined)
|
|
530
|
+
|
|
531
|
+
const { data: updatedThread } = await adminDb
|
|
532
|
+
.from('threads')
|
|
533
|
+
.select('data')
|
|
534
|
+
.eq('id', thread_id)
|
|
535
|
+
.single()
|
|
536
|
+
|
|
537
|
+
const state = updatedThread?.data?.research_state || {}
|
|
538
|
+
const messageType = message?.data?.message_type ||
|
|
539
|
+
(state.status === 'awaiting_input' ? 'awaiting_input' : 'final')
|
|
540
|
+
|
|
541
|
+
return {
|
|
542
|
+
ok: true,
|
|
543
|
+
thread_id,
|
|
544
|
+
message_id: message?.id || null,
|
|
545
|
+
status: state.status || (message ? 'complete' : 'failed'),
|
|
546
|
+
turn_count: state.turn_count ?? 0,
|
|
547
|
+
content: message?.content || '',
|
|
548
|
+
message_type: messageType,
|
|
549
|
+
data: message?.data || null,
|
|
550
|
+
// Intermediate research messages (tool_call/tool_result/plan) don't carry
|
|
551
|
+
// agent/prompt ids — fall back to the thread's resolved config.
|
|
552
|
+
agent_id: message?.data?.agent_id || updatedThread?.data?.agent_id || null,
|
|
553
|
+
prompt_config_id: message?.data?.prompt_config_id || updatedThread?.data?.prompt_config_id || null,
|
|
554
|
+
}
|
|
555
|
+
})
|
|
556
|
+
// CIL[END stable_id="~/.framework/functions/ai-agents.ts:run:constant"]
|
|
557
|
+
|
|
558
|
+
|
|
559
|
+
|
|
560
|
+
|
|
561
|
+
|
|
562
|
+
|
|
563
|
+
|
|
564
|
+
|
|
565
|
+
|
|
566
|
+
|
|
567
|
+
|
|
568
|
+
|
|
569
|
+
|
|
570
|
+
|
|
571
|
+
|
|
572
|
+
|
|
573
|
+
// CIL[BEGIN stable_id="~/.framework/functions/ai-agents.ts:handler:constant" type="constant" identity="handler" parent="~/.framework/functions/ai-agents.ts"]
|
|
574
|
+
/**
|
|
575
|
+
* The handler processes incoming requests based on the specified action and HTTP method, routing them to the appropriate function. It exists to manage different operations like retrieving, creating, or deleting resources in a structured manner.
|
|
576
|
+
*
|
|
577
|
+
* @throws Error — Invalid action or method
|
|
578
|
+
* @sideEffects none
|
|
579
|
+
* @stability stable
|
|
580
|
+
* @calls run, get, list, create, remove
|
|
581
|
+
* @cil-generated
|
|
582
|
+
*/
|
|
583
|
+
|
|
584
|
+
|
|
585
|
+
|
|
586
|
+
|
|
587
|
+
|
|
588
|
+
|
|
589
|
+
|
|
590
|
+
|
|
275
591
|
export const handler = createHandler(async (ctx, body) => {
|
|
276
592
|
const { action } = ctx.query || {}
|
|
277
593
|
const method = ctx.query?.method || 'GET'
|
|
278
594
|
|
|
279
595
|
switch (action) {
|
|
596
|
+
case 'run':
|
|
597
|
+
return await run(ctx, body)
|
|
280
598
|
default:
|
|
281
599
|
if (method === 'GET') {
|
|
282
600
|
if (ctx.query?.id) {
|
|
@@ -295,4 +613,11 @@ export const handler = createHandler(async (ctx, body) => {
|
|
|
295
613
|
|
|
296
614
|
throw new Error('Invalid action or method')
|
|
297
615
|
})
|
|
298
|
-
// CIL[END
|
|
616
|
+
// CIL[END stable_id="~/.framework/functions/ai-agents.ts:handler:constant"]
|
|
617
|
+
|
|
618
|
+
|
|
619
|
+
|
|
620
|
+
|
|
621
|
+
|
|
622
|
+
|
|
623
|
+
|