spine-framework 0.3.145 → 0.4.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.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 +5051 -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,3 +1,27 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @module admin-data
|
|
3
|
+
* @audience internal
|
|
4
|
+
* @layer app-specific
|
|
5
|
+
* @stability stable
|
|
6
|
+
*
|
|
7
|
+
* This module handles administrative data operations within the system, providing essential functionalities for managing records and permissions. It serves as an API handler for various administrative actions, ensuring that only authorized users can perform updates and access sensitive data. INVARIANT: Only users with system admin privileges can execute these operations.
|
|
8
|
+
*
|
|
9
|
+
* @seeAlso middleware.ts (provides request handling logic).
|
|
10
|
+
* @seeAlso permissions.ts (manages access control and validation).
|
|
11
|
+
* @seeAlso db.ts (interfaces with the database for data operations).
|
|
12
|
+
* @seeAlso principal.ts (determines user roles and permissions).
|
|
13
|
+
*
|
|
14
|
+
* @cil-generated
|
|
15
|
+
*/
|
|
16
|
+
// CIL[BEGIN stable_id="~/.framework/functions/admin-data.ts:module_header:module_header" type="module_header" identity="module_header" parent="~/.framework/functions/admin-data.ts"]
|
|
17
|
+
// CIL[DOC-MACRO purpose="This module handles administrative data operations within the system, providing essential functionalities for managing records and permissions."]
|
|
18
|
+
// CIL[DOC-RESPONSIBILITY responsibility="This module handles administrative data operations within the system, providing essential functionalities for managing records and permissions. It serves as an API handler for various administrative actions, ensuring that only authorized users can perform updates and access sensitive data. INVARIANT: Only users with system admin privileges can execute these operations."]
|
|
19
|
+
// CIL[DOC-CONTEXT module="admin-data" layer="app-specific" related_files="middleware.ts (provides request handling logic).,permissions.ts (manages access control and validation).,db.ts (interfaces with the database for data operations).,principal.ts (determines user roles and permissions)."]
|
|
20
|
+
// CIL[DOC-CONTRACT inputs="none" outputs="none" errors="none" side_effects="none"]
|
|
21
|
+
// CIL[DOC-MICRO logic_summary="This module handles administrative data operations within the system, providing essential functionalities for managing records and permissions. It serves as an API handler for various administrative actions, ensuring that only authorized users can perform updates and access sensitive data. INVARIANT: Only users with system admin privileges can execute these operations." notable_decisions="none"]
|
|
22
|
+
// CIL[DOC-CONFIDENCE pass="second" score="0.90" flags="none"]
|
|
23
|
+
// CIL[DOC-STABILITY stability="stable"]
|
|
24
|
+
// CIL[DOC-AUDIENCE audience="internal"]
|
|
1
25
|
|
|
2
26
|
|
|
3
27
|
|
|
@@ -7,21 +31,6 @@
|
|
|
7
31
|
|
|
8
32
|
|
|
9
33
|
|
|
10
|
-
// CIL[BEGIN chunk_id="admin-data_module_header_1784019432" type="module_header" identity="imports" parent="none"]
|
|
11
|
-
// CIL[DOC-MACRO purpose="Import dependencies for generic CRUD operations"]
|
|
12
|
-
// CIL[DOC-RESPONSIBILITY responsibility="Provide middleware, permissions, database access, type resolution, and triggers"]
|
|
13
|
-
// CIL[DOC-CONTEXT module="admin-data" layer="api-handler" related_files="[\"custom/apps/cortex/pages/operations/OperationsDashboard.tsx\",\".framework/functions/_shared/db.ts\",\".framework/src/pages/admin/TypeDetailPage.tsx\",\".framework/functions/_shared/principal.ts\",\".framework/functions/_shared/schema-utils.ts\",\"\\\"]"]
|
|
14
|
-
// CIL[DOC-CONTRACT inputs="none" outputs="imported_modules,constants" errors="none" side_effects="none"]
|
|
15
|
-
// CIL[DOC-MICRO logic_summary="Imports modules and defines entity validation constants" notable_decisions="[]"]
|
|
16
|
-
// CIL[DOC-CONFIDENCE pass="second" score="0.95" flags="none"]
|
|
17
|
-
// CIL[DOC-STABILITY stability="stable"]
|
|
18
|
-
// CIL[DOC-AUDIENCE audience="developer"]
|
|
19
|
-
// 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/functions/_shared/db.ts, .framework/src/pages/admin/TypeDetailPage.tsx, .framework/functions/_shared/principal.ts, .framework/functions/_shared/schema-utils.ts, \."]
|
|
20
|
-
// CIL[DOC-VECTOR type="blast_radius" content="Direct callers: 0. Total affected: 0."]
|
|
21
|
-
// CIL[DOC-VECTOR type="configuration" content="No configuration dependencies."]
|
|
22
|
-
// CIL[DOC-VECTOR type="constraint" content="No test paths identified."]
|
|
23
|
-
// CIL[DOC-VECTOR type="implementation_pattern" content="" status="pending_human_input"]
|
|
24
|
-
// CIL[DOC-VECTOR type="user_journey" content="" status="pending_human_input"]
|
|
25
34
|
import { createHandler } from './_shared/middleware'
|
|
26
35
|
import { sanitizeRecordData, resolveFirstSurfacePermissions, validateUpdatePermissions } from './_shared/permissions'
|
|
27
36
|
import { adminDb } from './_shared/db'
|
|
@@ -29,16 +38,151 @@ import { isSystemAdmin } from './_shared/principal'
|
|
|
29
38
|
import { resolveTypeId, resolveTypeIds, resolveTypeRecord } from './_shared/resolve-ids'
|
|
30
39
|
import { fireCreateTriggers, fireUpdateTriggers, fireDeleteTriggers } from './_shared/trigger-engine'
|
|
31
40
|
import { withAdminLogging } from './_shared/logging'
|
|
41
|
+
import { hasInternalAudience, projectMessageForCustomer } from './_shared/access'
|
|
42
|
+
import { checkTypeSlugRateLimit } from './_shared/security'
|
|
43
|
+
// CIL[END stable_id="~/.framework/functions/admin-data.ts:module_header:module_header"]
|
|
44
|
+
// CIL[DOC-VECTOR type="context" content="purpose='This module handles administrative data operations within the system, providing essential functionalities for managing records and permissions.'; No verified external callers" status="ready"]
|
|
45
|
+
// CIL[DOC-VECTOR type="blast_radius" content="No direct caller data from CIL graph; local impact only" status="ready"]
|
|
46
|
+
// CIL[DOC-VECTOR type="configuration" content="No environment or build configuration dependencies identified" status="ready"]
|
|
47
|
+
// CIL[DOC-VECTOR type="constraint" content="Standard runtime; no special invariants documented" status="ready"]
|
|
48
|
+
// CIL[DOC-VECTOR type="implementation_pattern" content="" status="pending_human_input"]
|
|
49
|
+
// CIL[DOC-VECTOR type="user_journey" content="" status="pending_human_input"]
|
|
32
50
|
|
|
51
|
+
// CIL[DOC-MACRO purpose="PERMISSIONS_ALL defines a comprehensive set of permissions for record management, including create, read, update, and delete actions."]
|
|
52
|
+
// CIL[DOC-RESPONSIBILITY responsibility="PERMISSIONS_ALL defines a comprehensive set of permissions for record management, including create, read, update, and delete actions. It serves as a centralized reference for managing access control in the application."]
|
|
53
|
+
// CIL[DOC-CONTEXT module="admin-data" layer="app-specific" related_files=".framework/functions/_shared/middleware,.framework/functions/_shared/permissions,.framework/functions/_shared/db,.framework/functions/_shared/principal,.framework/functions/_shared/resolve-ids,.framework/functions/_shared/trigger-engine,.framework/functions/_shared/logging,.framework/functions/_shared/access"]
|
|
54
|
+
// CIL[DOC-CONTRACT inputs="none" outputs="none" errors="none" side_effects="none"]
|
|
55
|
+
// CIL[DOC-MICRO logic_summary="PERMISSIONS_ALL defines a comprehensive set of permissions for record management, including create, read, update, and delete actions. It serves as a centralized reference for managing access control in the application." notable_decisions="none"]
|
|
56
|
+
// CIL[DOC-CONFIDENCE pass="second" score="0.90" flags="none"]
|
|
57
|
+
// CIL[DOC-STABILITY stability="stable"]
|
|
58
|
+
/**
|
|
59
|
+
* PERMISSIONS_ALL defines a comprehensive set of permissions for record management, including create, read, update, and delete actions. It serves as a centralized reference for managing access control in the application.
|
|
60
|
+
*
|
|
61
|
+
* @sideEffects none
|
|
62
|
+
* @stability stable
|
|
63
|
+
* @cil-generated
|
|
64
|
+
*/
|
|
65
|
+
// CIL[BEGIN stable_id="~/.framework/functions/admin-data.ts:permissions_all:constant" type="constant" identity="PERMISSIONS_ALL" parent="~/.framework/functions/admin-data.ts"]
|
|
66
|
+
// CIL[DOC-MACRO purpose="PERMISSIONS_ALL constant"]
|
|
67
|
+
// CIL[DOC-RESPONSIBILITY responsibility="Implements the PERMISSIONS_ALL constant."]
|
|
68
|
+
// CIL[DOC-CONTEXT module=".framework/functions/admin-data.ts" layer="app-specific" related_files=""]
|
|
69
|
+
// CIL[DOC-CONTRACT inputs="none" outputs="none" errors="none" side_effects="none"]
|
|
70
|
+
// CIL[DOC-MICRO logic_summary="Implements the PERMISSIONS_ALL constant." notable_decisions="[]"]
|
|
71
|
+
// CIL[DOC-CONFIDENCE pass="first" score="0.8" flags="none"]
|
|
72
|
+
// CIL[DOC-STABILITY stability="stable"]
|
|
33
73
|
const PERMISSIONS_ALL = {
|
|
34
74
|
record_permissions: { all: ['create', 'read', 'update', 'delete'] },
|
|
35
75
|
fields: {}
|
|
36
76
|
}
|
|
77
|
+
// CIL[END stable_id="~/.framework/functions/admin-data.ts:permissions_all:constant"]
|
|
78
|
+
// CIL[DOC-VECTOR type="context" content="purpose='PERMISSIONS_ALL defines a comprehensive set of permissions for record management, including create, read, update, and delete actions.'; No verified external callers" status="ready"]
|
|
79
|
+
// CIL[DOC-VECTOR type="blast_radius" content="No direct caller data from CIL graph; local impact only" status="ready"]
|
|
80
|
+
// CIL[DOC-VECTOR type="configuration" content="No environment or build configuration dependencies identified" status="ready"]
|
|
81
|
+
// CIL[DOC-VECTOR type="constraint" content="Standard runtime; no special invariants documented" status="ready"]
|
|
82
|
+
// CIL[DOC-VECTOR type="implementation_pattern" content="" status="pending_human_input"]
|
|
83
|
+
// CIL[DOC-VECTOR type="user_journey" content="" status="pending_human_input"]
|
|
37
84
|
|
|
85
|
+
// CIL[DOC-MACRO purpose="VALID_ENTITIES is a constant array that defines the valid entity types used throughout the admin data functions."]
|
|
86
|
+
// CIL[DOC-RESPONSIBILITY responsibility="VALID_ENTITIES is a constant array that defines the valid entity types used throughout the admin data functions. It ensures that only recognized entity types are processed in the module."]
|
|
87
|
+
// CIL[DOC-CONTEXT module="admin-data" layer="app-specific" related_files=".framework/functions/_shared/middleware,.framework/functions/_shared/permissions,.framework/functions/_shared/db,.framework/functions/_shared/principal,.framework/functions/_shared/resolve-ids,.framework/functions/_shared/trigger-engine,.framework/functions/_shared/logging,.framework/functions/_shared/access"]
|
|
88
|
+
// CIL[DOC-CONTRACT inputs="none" outputs="none" errors="none" side_effects="none"]
|
|
89
|
+
// CIL[DOC-MICRO logic_summary="VALID_ENTITIES is a constant array that defines the valid entity types used throughout the admin data functions. It ensures that only recognized entity types are processed in the module." notable_decisions="none"]
|
|
90
|
+
// CIL[DOC-CONFIDENCE pass="second" score="0.90" flags="none"]
|
|
91
|
+
// CIL[DOC-STABILITY stability="stable"]
|
|
92
|
+
/**
|
|
93
|
+
* VALID_ENTITIES is a constant array that defines the valid entity types used throughout the admin data functions. It ensures that only recognized entity types are processed in the module.
|
|
94
|
+
*
|
|
95
|
+
* @sideEffects none
|
|
96
|
+
* @stability stable
|
|
97
|
+
* @cil-generated
|
|
98
|
+
*/
|
|
99
|
+
// CIL[BEGIN stable_id="~/.framework/functions/admin-data.ts:valid_entities:constant" type="constant" identity="VALID_ENTITIES" parent="~/.framework/functions/admin-data.ts"]
|
|
100
|
+
// CIL[DOC-MACRO purpose="VALID_ENTITIES constant"]
|
|
101
|
+
// CIL[DOC-RESPONSIBILITY responsibility="Implements the VALID_ENTITIES constant."]
|
|
102
|
+
// CIL[DOC-CONTEXT module=".framework/functions/admin-data.ts" layer="app-specific" related_files=""]
|
|
103
|
+
// CIL[DOC-CONTRACT inputs="none" outputs="none" errors="none" side_effects="none"]
|
|
104
|
+
// CIL[DOC-MICRO logic_summary="Implements the VALID_ENTITIES constant." notable_decisions="[]"]
|
|
105
|
+
// CIL[DOC-CONFIDENCE pass="first" score="0.8" flags="none"]
|
|
106
|
+
// CIL[DOC-STABILITY stability="stable"]
|
|
38
107
|
const VALID_ENTITIES = ['accounts', 'people', 'items', 'threads', 'messages', 'links', 'attachments', 'watchers', 'item_progress', 'logs', 'test_runs', 'observability', 'test_cases', 'types', 'link_types', 'ai_agents', 'prompt_configs']
|
|
108
|
+
// CIL[END stable_id="~/.framework/functions/admin-data.ts:valid_entities:constant"]
|
|
109
|
+
// CIL[DOC-MACRO purpose="VALID_ENTITIES constant"]
|
|
110
|
+
// CIL[DOC-RESPONSIBILITY responsibility="Implements the VALID_ENTITIES constant."]
|
|
111
|
+
// CIL[DOC-CONTEXT module=".framework/functions/admin-data.ts" layer="app-specific" related_files=""]
|
|
112
|
+
// CIL[DOC-CONTRACT inputs="none" outputs="none" errors="none" side_effects="none"]
|
|
113
|
+
// CIL[DOC-MICRO logic_summary="Implements the VALID_ENTITIES constant." notable_decisions="[]"]
|
|
114
|
+
// CIL[DOC-CONFIDENCE pass="first" score="0.8" flags="none"]
|
|
115
|
+
// CIL[DOC-STABILITY stability="stable"]
|
|
116
|
+
// CIL[DOC-VECTOR type="context" content="purpose='VALID_ENTITIES is a constant array that defines the valid entity types used throughout the admin data functions.'; No verified external callers" status="ready"]
|
|
117
|
+
// CIL[DOC-VECTOR type="blast_radius" content="No direct caller data from CIL graph; local impact only" status="ready"]
|
|
118
|
+
// CIL[DOC-VECTOR type="configuration" content="No environment or build configuration dependencies identified" status="ready"]
|
|
119
|
+
// CIL[DOC-VECTOR type="constraint" content="Standard runtime; no special invariants documented" status="ready"]
|
|
120
|
+
// CIL[DOC-VECTOR type="implementation_pattern" content="" status="pending_human_input"]
|
|
121
|
+
// CIL[DOC-VECTOR type="user_journey" content="" status="pending_human_input"]
|
|
39
122
|
|
|
123
|
+
// CIL[DOC-MACRO purpose="RAW_ENTITIES is a constant array that defines a set of entity names used in the admin data functions."]
|
|
124
|
+
// CIL[DOC-RESPONSIBILITY responsibility="RAW_ENTITIES is a constant array that defines a set of entity names used in the admin data functions. It exists to provide a centralized reference for these entity types, ensuring consistency across the module."]
|
|
125
|
+
// CIL[DOC-CONTEXT module="admin-data" layer="app-specific" related_files=".framework/functions/_shared/middleware,.framework/functions/_shared/permissions,.framework/functions/_shared/db,.framework/functions/_shared/principal,.framework/functions/_shared/resolve-ids,.framework/functions/_shared/trigger-engine,.framework/functions/_shared/logging,.framework/functions/_shared/access"]
|
|
126
|
+
// CIL[DOC-CONTRACT inputs="none" outputs="none" errors="none" side_effects="none"]
|
|
127
|
+
// CIL[DOC-MICRO logic_summary="RAW_ENTITIES is a constant array that defines a set of entity names used in the admin data functions. It exists to provide a centralized reference for these entity types, ensuring consistency across the module." notable_decisions="none"]
|
|
128
|
+
// CIL[DOC-CONFIDENCE pass="second" score="0.90" flags="none"]
|
|
129
|
+
// CIL[DOC-STABILITY stability="stable"]
|
|
130
|
+
/**
|
|
131
|
+
* RAW_ENTITIES is a constant array that defines a set of entity names used in the admin data functions. It exists to provide a centralized reference for these entity types, ensuring consistency across the module.
|
|
132
|
+
*
|
|
133
|
+
* @sideEffects none
|
|
134
|
+
* @stability stable
|
|
135
|
+
* @cil-generated
|
|
136
|
+
*/
|
|
137
|
+
// CIL[BEGIN stable_id="~/.framework/functions/admin-data.ts:raw_entities:constant" type="constant" identity="RAW_ENTITIES" parent="~/.framework/functions/admin-data.ts"]
|
|
138
|
+
// CIL[DOC-MACRO purpose="RAW_ENTITIES constant"]
|
|
139
|
+
// CIL[DOC-RESPONSIBILITY responsibility="Implements the RAW_ENTITIES constant."]
|
|
140
|
+
// CIL[DOC-CONTEXT module=".framework/functions/admin-data.ts" layer="app-specific" related_files=""]
|
|
141
|
+
// CIL[DOC-CONTRACT inputs="none" outputs="none" errors="none" side_effects="none"]
|
|
142
|
+
// CIL[DOC-MICRO logic_summary="Implements the RAW_ENTITIES constant." notable_decisions="[]"]
|
|
143
|
+
// CIL[DOC-CONFIDENCE pass="first" score="0.8" flags="none"]
|
|
144
|
+
// CIL[DOC-STABILITY stability="stable"]
|
|
40
145
|
const RAW_ENTITIES = ['logs', 'test_runs', 'observability', 'test_cases']
|
|
146
|
+
// Entities with no created_by/updated_by columns — audit stamps must be
|
|
147
|
+
// omitted or writes fail with schema-cache errors.
|
|
148
|
+
const UNAUDITED_ENTITIES = ['types', 'link_types']
|
|
149
|
+
// CIL[END stable_id="~/.framework/functions/admin-data.ts:raw_entities:constant"]
|
|
150
|
+
// CIL[DOC-MACRO purpose="RAW_ENTITIES constant"]
|
|
151
|
+
// CIL[DOC-RESPONSIBILITY responsibility="Implements the RAW_ENTITIES constant."]
|
|
152
|
+
// CIL[DOC-CONTEXT module=".framework/functions/admin-data.ts" layer="app-specific" related_files=""]
|
|
153
|
+
// CIL[DOC-CONTRACT inputs="none" outputs="none" errors="none" side_effects="none"]
|
|
154
|
+
// CIL[DOC-MICRO logic_summary="Implements the RAW_ENTITIES constant." notable_decisions="[]"]
|
|
155
|
+
// CIL[DOC-CONFIDENCE pass="first" score="0.8" flags="none"]
|
|
156
|
+
// CIL[DOC-STABILITY stability="stable"]
|
|
157
|
+
// CIL[DOC-VECTOR type="context" content="purpose='RAW_ENTITIES is a constant array that defines a set of entity names used in the admin data functions.'; No verified external callers" status="ready"]
|
|
158
|
+
// CIL[DOC-VECTOR type="blast_radius" content="No direct caller data from CIL graph; local impact only" status="ready"]
|
|
159
|
+
// CIL[DOC-VECTOR type="configuration" content="No environment or build configuration dependencies identified" status="ready"]
|
|
160
|
+
// CIL[DOC-VECTOR type="constraint" content="Standard runtime; no special invariants documented" status="ready"]
|
|
161
|
+
// CIL[DOC-VECTOR type="implementation_pattern" content="" status="pending_human_input"]
|
|
162
|
+
// CIL[DOC-VECTOR type="user_journey" content="" status="pending_human_input"]
|
|
41
163
|
|
|
164
|
+
// CIL[DOC-MACRO purpose="ENTITY_TO_KIND is a mapping of entity names to their corresponding kind identifiers."]
|
|
165
|
+
// CIL[DOC-RESPONSIBILITY responsibility="ENTITY_TO_KIND is a mapping of entity names to their corresponding kind identifiers. It exists to provide a centralized reference for translating entity types within the application."]
|
|
166
|
+
// CIL[DOC-CONTEXT module="admin-data" layer="app-specific" related_files=".framework/functions/_shared/middleware,.framework/functions/_shared/permissions,.framework/functions/_shared/db,.framework/functions/_shared/principal,.framework/functions/_shared/resolve-ids,.framework/functions/_shared/trigger-engine,.framework/functions/_shared/logging,.framework/functions/_shared/access"]
|
|
167
|
+
// CIL[DOC-CONTRACT inputs="none" outputs="none" errors="none" side_effects="none"]
|
|
168
|
+
// CIL[DOC-MICRO logic_summary="ENTITY_TO_KIND is a mapping of entity names to their corresponding kind identifiers. It exists to provide a centralized reference for translating entity types within the application." notable_decisions="none"]
|
|
169
|
+
// CIL[DOC-CONFIDENCE pass="second" score="0.90" flags="none"]
|
|
170
|
+
// CIL[DOC-STABILITY stability="stable"]
|
|
171
|
+
/**
|
|
172
|
+
* ENTITY_TO_KIND is a mapping of entity names to their corresponding kind identifiers. It exists to provide a centralized reference for translating entity types within the application.
|
|
173
|
+
*
|
|
174
|
+
* @sideEffects none
|
|
175
|
+
* @stability stable
|
|
176
|
+
* @cil-generated
|
|
177
|
+
*/
|
|
178
|
+
// CIL[BEGIN stable_id="~/.framework/functions/admin-data.ts:entity_to_kind:constant" type="constant" identity="ENTITY_TO_KIND" parent="~/.framework/functions/admin-data.ts"]
|
|
179
|
+
// CIL[DOC-MACRO purpose="ENTITY_TO_KIND constant"]
|
|
180
|
+
// CIL[DOC-RESPONSIBILITY responsibility="Implements the ENTITY_TO_KIND constant."]
|
|
181
|
+
// CIL[DOC-CONTEXT module=".framework/functions/admin-data.ts" layer="app-specific" related_files=""]
|
|
182
|
+
// CIL[DOC-CONTRACT inputs="none" outputs="none" errors="none" side_effects="none"]
|
|
183
|
+
// CIL[DOC-MICRO logic_summary="Implements the ENTITY_TO_KIND constant." notable_decisions="[]"]
|
|
184
|
+
// CIL[DOC-CONFIDENCE pass="first" score="0.8" flags="none"]
|
|
185
|
+
// CIL[DOC-STABILITY stability="stable"]
|
|
42
186
|
const ENTITY_TO_KIND: Record<string, string> = {
|
|
43
187
|
accounts: 'account',
|
|
44
188
|
people: 'person',
|
|
@@ -50,23 +194,39 @@ const ENTITY_TO_KIND: Record<string, string> = {
|
|
|
50
194
|
watchers: 'watcher',
|
|
51
195
|
item_progress: 'item_progress'
|
|
52
196
|
}
|
|
53
|
-
// CIL[END
|
|
54
|
-
// CIL[
|
|
55
|
-
// CIL[DOC-
|
|
56
|
-
// CIL[DOC-
|
|
57
|
-
// CIL[DOC-
|
|
58
|
-
// CIL[DOC-CONTRACT inputs="none" outputs="sanitized_records[] or {data,schema,view}" errors="entity_required,database_error" side_effects="database_queries,permission_filtering"]
|
|
59
|
-
// CIL[DOC-MICRO logic_summary="Builds query with filters, applies pagination, sanitizes results, optionally resolves views" notable_decisions="[]"]
|
|
60
|
-
// CIL[DOC-CONFIDENCE pass="second" score="0.95" flags="complex_dependencies"]
|
|
61
|
-
// CIL[DOC-STABILITY stability="stable"]
|
|
62
|
-
// CIL[DOC-VECTOR type="context" content="Layer: api-handler. Direct callers: 0. Direct calls: 0. Related files: custom/apps/portal/pages/ContentPage.tsx, .framework/src/pages/admin/TypeDetailPage.tsx, custom/apps/cortex/pages/operations/OperationsDashboard.tsx, .framework/src/components/ui/dialog.tsx, .framework/functions/_shared/principal.ts, \."]
|
|
63
|
-
// CIL[DOC-VECTOR type="blast_radius" content="Direct callers: 0. Total affected: 0."]
|
|
64
|
-
// CIL[DOC-VECTOR type="configuration" content="No configuration dependencies."]
|
|
65
|
-
// CIL[DOC-VECTOR type="constraint" content="No test paths identified."]
|
|
197
|
+
// CIL[END stable_id="~/.framework/functions/admin-data.ts:entity_to_kind:constant"]
|
|
198
|
+
// CIL[DOC-VECTOR type="context" content="purpose='ENTITY_TO_KIND is a mapping of entity names to their corresponding kind identifiers.'; No verified external callers" status="ready"]
|
|
199
|
+
// CIL[DOC-VECTOR type="blast_radius" content="No direct caller data from CIL graph; local impact only" status="ready"]
|
|
200
|
+
// CIL[DOC-VECTOR type="configuration" content="No environment or build configuration dependencies identified" status="ready"]
|
|
201
|
+
// CIL[DOC-VECTOR type="constraint" content="Standard runtime; no special invariants documented" status="ready"]
|
|
66
202
|
// CIL[DOC-VECTOR type="implementation_pattern" content="" status="pending_human_input"]
|
|
67
203
|
// CIL[DOC-VECTOR type="user_journey" content="" status="pending_human_input"]
|
|
204
|
+
// CIL[DOC-MACRO purpose="The 'list' constant defines an asynchronous handler for listing entities based on various query parameters."]
|
|
205
|
+
// CIL[DOC-RESPONSIBILITY responsibility="The 'list' constant defines an asynchronous handler for listing entities based on various query parameters. It validates input parameters and constructs a database query to retrieve the requested data."]
|
|
206
|
+
// CIL[DOC-CONTEXT module="admin-data" layer="app-specific" related_files=".framework/functions/_shared/middleware,.framework/functions/_shared/permissions,.framework/functions/_shared/db,.framework/functions/_shared/principal,.framework/functions/_shared/resolve-ids,.framework/functions/_shared/trigger-engine,.framework/functions/_shared/logging,.framework/functions/_shared/access"]
|
|
207
|
+
// CIL[DOC-CONTRACT inputs="none" outputs="none" errors="Error — Valid entity parameter is required" side_effects="none dependencies="withAdminLogging, resolveTypeIds, getSearchField"]
|
|
208
|
+
// CIL[DOC-MICRO logic_summary="The 'list' constant defines an asynchronous handler for listing entities based on various query parameters. It validates input parameters and constructs a database query to retrieve the requested data." notable_decisions="none"]
|
|
209
|
+
// CIL[DOC-CONFIDENCE pass="second" score="0.90" flags="none"]
|
|
210
|
+
// CIL[DOC-STABILITY stability="stable"]
|
|
211
|
+
/**
|
|
212
|
+
* The 'list' constant defines an asynchronous handler for listing entities based on various query parameters. It validates input parameters and constructs a database query to retrieve the requested data.
|
|
213
|
+
*
|
|
214
|
+
* @throws Error — Valid entity parameter is required
|
|
215
|
+
* @sideEffects none
|
|
216
|
+
* @stability stable
|
|
217
|
+
* @calls withAdminLogging, resolveTypeIds, getSearchField
|
|
218
|
+
* @cil-generated
|
|
219
|
+
*/
|
|
220
|
+
// CIL[BEGIN stable_id="~/.framework/functions/admin-data.ts:list:constant" type="constant" identity="list" parent="~/.framework/functions/admin-data.ts"]
|
|
221
|
+
// CIL[DOC-MACRO purpose="list constant"]
|
|
222
|
+
// CIL[DOC-RESPONSIBILITY responsibility="Implements the list constant."]
|
|
223
|
+
// CIL[DOC-CONTEXT module=".framework/functions/admin-data.ts" layer="app-specific" related_files=""]
|
|
224
|
+
// CIL[DOC-CONTRACT inputs="none" outputs="none" errors="none" side_effects="none"]
|
|
225
|
+
// CIL[DOC-MICRO logic_summary="Implements the list constant." notable_decisions="[]"]
|
|
226
|
+
// CIL[DOC-CONFIDENCE pass="first" score="0.8" flags="none"]
|
|
227
|
+
// CIL[DOC-STABILITY stability="stable"]
|
|
68
228
|
export const list = createHandler(async (ctx, _body) => {
|
|
69
|
-
const { entity, action, method, search, sort_field = 'created_at', sort_direction = 'desc', limit = 50, offset = 0, type_slug, type_slugs, view: viewSlug, ...filters } = ctx.query || {}
|
|
229
|
+
const { entity, action, method, search, sort_field = 'created_at', sort_direction = 'desc', limit = 50, offset = 0, type_slug, type_slugs, view: viewSlug, flag_only, exclude_flag, ...filters } = ctx.query || {}
|
|
70
230
|
|
|
71
231
|
return await withAdminLogging(
|
|
72
232
|
ctx,
|
|
@@ -85,6 +245,12 @@ export const list = createHandler(async (ctx, _body) => {
|
|
|
85
245
|
const db = (ctx.principal?.isInternal || isSystemAdmin(ctx.principal)) ? adminDb : ctx.db
|
|
86
246
|
let query = db.from(entity).select('*')
|
|
87
247
|
|
|
248
|
+
// Customer-scoped principals never receive internal threads.
|
|
249
|
+
const internalAudience = hasInternalAudience(ctx.principal)
|
|
250
|
+
if (entity === 'threads' && !internalAudience) {
|
|
251
|
+
query = query.neq('visibility', 'internal')
|
|
252
|
+
}
|
|
253
|
+
|
|
88
254
|
const targetSlugs: string[] = []
|
|
89
255
|
if (type_slug) targetSlugs.push(type_slug)
|
|
90
256
|
if (type_slugs) {
|
|
@@ -126,6 +292,26 @@ export const list = createHandler(async (ctx, _body) => {
|
|
|
126
292
|
}
|
|
127
293
|
})
|
|
128
294
|
|
|
295
|
+
// Generic record-flag filters on the row's data jsonb. flag_only=<field>
|
|
296
|
+
// returns only rows where data->>field is 'true'; exclude_flag=<field>
|
|
297
|
+
// hides them (null counts as unset). Flag fields are stamped server-side
|
|
298
|
+
// — clients can only filter on them, never set them. Only entities whose
|
|
299
|
+
// rows carry flaggable data payloads are eligible (accounts/people are
|
|
300
|
+
// excluded). The field name is validated before it is interpolated into
|
|
301
|
+
// the PostgREST filter string.
|
|
302
|
+
const FLAGGABLE_ENTITIES = ['items', 'threads', 'messages', 'links', 'attachments', 'watchers']
|
|
303
|
+
const flagParam = flag_only ?? exclude_flag
|
|
304
|
+
if (flagParam !== undefined && !/^[a-z][a-z0-9_]{0,62}$/.test(String(flagParam))) {
|
|
305
|
+
const e: any = new Error('Invalid flag field name'); e.statusCode = 400; throw e
|
|
306
|
+
}
|
|
307
|
+
if (FLAGGABLE_ENTITIES.includes(entity)) {
|
|
308
|
+
if (flag_only) {
|
|
309
|
+
query = query.eq(`data->>${flag_only}`, 'true')
|
|
310
|
+
} else if (exclude_flag) {
|
|
311
|
+
query = query.or(`data->>${exclude_flag}.is.null,data->>${exclude_flag}.eq.false`)
|
|
312
|
+
}
|
|
313
|
+
}
|
|
314
|
+
|
|
129
315
|
query = query.order(sort_field, { ascending: sort_direction === 'asc' })
|
|
130
316
|
|
|
131
317
|
const { count, error: countError } = await db.from(entity)
|
|
@@ -145,12 +331,32 @@ export const list = createHandler(async (ctx, _body) => {
|
|
|
145
331
|
throw new Error(err.message || 'Database error listing records')
|
|
146
332
|
}
|
|
147
333
|
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
|
|
334
|
+
// Customer-scoped message reads project internal rows into safe
|
|
335
|
+
// step summaries — only when the parent thread itself is external.
|
|
336
|
+
let threadIsInternal = true
|
|
337
|
+
if (entity === 'messages' && !internalAudience && filters.thread_id) {
|
|
338
|
+
const { data: parentThread } = await adminDb
|
|
339
|
+
.from('threads')
|
|
340
|
+
.select('visibility')
|
|
341
|
+
.eq('id', filters.thread_id)
|
|
342
|
+
.maybeSingle()
|
|
343
|
+
threadIsInternal = parentThread?.visibility !== 'external' && parentThread?.visibility !== 'public'
|
|
344
|
+
? true
|
|
345
|
+
: false
|
|
152
346
|
}
|
|
153
347
|
|
|
348
|
+
// Sanitize rows concurrently — the sequential loop turned every list
|
|
349
|
+
// request into an N+1 of permission lookups.
|
|
350
|
+
const sanitizedData = (
|
|
351
|
+
await Promise.all((data || []).map(async (record: any) => {
|
|
352
|
+
const sanitizedRecord = await sanitizeRecordData(ctx, record, entity)
|
|
353
|
+
if (entity === 'messages' && !internalAudience) {
|
|
354
|
+
return projectMessageForCustomer(sanitizedRecord, { threadIsInternal })
|
|
355
|
+
}
|
|
356
|
+
return sanitizedRecord
|
|
357
|
+
}))
|
|
358
|
+
).filter(Boolean)
|
|
359
|
+
|
|
154
360
|
if (viewSlug && type_slug) {
|
|
155
361
|
const { data: typeRecord } = await adminDb
|
|
156
362
|
.from('types')
|
|
@@ -170,36 +376,70 @@ export const list = createHandler(async (ctx, _body) => {
|
|
|
170
376
|
}
|
|
171
377
|
)
|
|
172
378
|
})
|
|
173
|
-
// CIL[END
|
|
174
|
-
// CIL[
|
|
175
|
-
// CIL[DOC-
|
|
176
|
-
// CIL[DOC-
|
|
177
|
-
// CIL[DOC-
|
|
178
|
-
// CIL[DOC-CONTRACT inputs="none" outputs="sanitized_record or {data,schema,view}" errors="entity_required,id_required,record_not_found" side_effects="database_query,permission_filtering"]
|
|
179
|
-
// CIL[DOC-MICRO logic_summary="Queries single record by ID, applies permission sanitization, optionally resolves view" notable_decisions="[]"]
|
|
180
|
-
// CIL[DOC-CONFIDENCE pass="second" score="0.95" flags="none"]
|
|
181
|
-
// CIL[DOC-STABILITY stability="stable"]
|
|
182
|
-
// CIL[DOC-VECTOR type="context" content="Layer: api-handler. Direct callers: 0. Direct calls: 0. Related files: .framework/functions/_shared/schema-utils.ts, .framework/src/pages/admin/TypeDetailPage.tsx, .framework/src/pages/admin/RolesPage.tsx, custom/apps/cortex/functions/custom_cil-embeddings.ts, \."]
|
|
183
|
-
// CIL[DOC-VECTOR type="blast_radius" content="Direct callers: 0. Total affected: 0."]
|
|
184
|
-
// CIL[DOC-VECTOR type="configuration" content="No configuration dependencies."]
|
|
185
|
-
// CIL[DOC-VECTOR type="constraint" content="No test paths identified."]
|
|
379
|
+
// CIL[END stable_id="~/.framework/functions/admin-data.ts:list:constant"]
|
|
380
|
+
// CIL[DOC-VECTOR type="context" content="purpose='The 'list' constant defines an asynchronous handler for listing entities based on various query parameters.'; No verified external callers" status="ready"]
|
|
381
|
+
// CIL[DOC-VECTOR type="blast_radius" content="No direct caller data from CIL graph; local impact only" status="ready"]
|
|
382
|
+
// CIL[DOC-VECTOR type="configuration" content="No environment or build configuration dependencies identified" status="ready"]
|
|
383
|
+
// CIL[DOC-VECTOR type="constraint" content="Standard runtime; no special invariants documented" status="ready"]
|
|
186
384
|
// CIL[DOC-VECTOR type="implementation_pattern" content="" status="pending_human_input"]
|
|
187
385
|
// CIL[DOC-VECTOR type="user_journey" content="" status="pending_human_input"]
|
|
386
|
+
// CIL[DOC-MACRO purpose="Async function that resolves and attaches hierarchical lineage data to a record."]
|
|
387
|
+
// CIL[DOC-RESPONSIBILITY responsibility="The attachLineage function retrieves and attaches parent and child records to a given record based on the lineage configuration declared on the record's type (design_schema.functionality.lineage). It is designed to facilitate the understanding of relationships between different entities in the database."]
|
|
388
|
+
// CIL[DOC-CONTEXT module="admin-data" layer="app-specific" related_files=".framework/functions/_shared/middleware,.framework/functions/_shared/permissions,.framework/functions/_shared/db,.framework/functions/_shared/principal,.framework/functions/_shared/resolve-ids,.framework/functions/_shared/trigger-engine,.framework/functions/_shared/logging,.framework/functions/_shared/access"]
|
|
389
|
+
// CIL[DOC-CONTRACT inputs="- record: any (required) — the record to which lineage will be attached.\\n- ctx: any (required) — the context containing database access and other utilities." outputs="Promise<void>" errors="none" side_effects="Database reads from 'types', 'links' and 'items' tables. dependencies="ctx.db.from, ctx.db.select, ctx.db.eq, ctx.db.limit, ctx.db.single, sanitizeRecordData, resolveTypeIds, adminDb.from"]
|
|
390
|
+
// CIL[DOC-MICRO logic_summary="Reads functionality.lineage off the record's type; walks declared parent_fields/link_type for parents (max 5 hops, cycle-guarded) and resolves declared children via links plus per-type data-field lookups." notable_decisions="Lineage traversal is fully declared on the owning app's type design_schema — no app-specific maps in framework code; each leg is guarded by its own declaration so partial blocks still work; types without a lineage block attach empty parents/children with no link/data queries."]
|
|
391
|
+
// CIL[DOC-CONFIDENCE pass="second" score="0.90" flags="none"]
|
|
392
|
+
// CIL[DOC-STABILITY stability="stable"]
|
|
393
|
+
/**
|
|
394
|
+
* The attachLineage function retrieves and attaches parent and child records to a given record based on its lineage in a hierarchical structure. It is designed to facilitate the understanding of relationships between different entities in the database.
|
|
395
|
+
*
|
|
396
|
+
* @macro Async function that resolves and attaches hierarchical lineage data to a record.
|
|
397
|
+
* @micro Reads the type-declared functionality.lineage config (parent_fields, link_type, children) and resolves parents via link + data-field walks and children via reverse links + per-type field lookups.
|
|
398
|
+
* @inputSpec
|
|
399
|
+
* - record: any (required) — the record to which lineage will be attached.
|
|
400
|
+
* - ctx: any (required) — the context containing database access and other utilities.
|
|
401
|
+
* @outputSpec Promise<void>
|
|
402
|
+
* @sideEffects Database reads from 'types', 'links' and 'items' tables.
|
|
403
|
+
* @stability stable
|
|
404
|
+
* @calls adminDb.from, ctx.db.from, ctx.db.select, ctx.db.eq, ctx.db.limit, ctx.db.single, sanitizeRecordData, resolveTypeIds
|
|
405
|
+
* @errorHandling returns null on error during data fetching.
|
|
406
|
+
* @cil-generated
|
|
407
|
+
*/
|
|
408
|
+
// CIL[BEGIN stable_id="~/.framework/functions/admin-data.ts:attachlineage:function" type="function" identity="attachLineage" parent="~/.framework/functions/admin-data.ts"]
|
|
409
|
+
// CIL[DOC-MACRO purpose="attachLineage function"]
|
|
410
|
+
// CIL[DOC-RESPONSIBILITY responsibility="Implements the attachLineage function from type-declared lineage config."]
|
|
411
|
+
// CIL[DOC-CONTEXT module=".framework/functions/admin-data.ts" layer="app-specific" related_files=""]
|
|
412
|
+
// CIL[DOC-CONTRACT inputs="record: any — item record with type_id, ctx: any — request context with db" outputs="mutates record (parents, children, type_slug)" errors="none" side_effects="reads types/links/items"]
|
|
413
|
+
// CIL[DOC-MICRO logic_summary="Reads functionality.lineage off the record's type design_schema; parents walk declared link_type then parent_fields (5-hop, visited-set cycle guard); children resolve via reverse link_type edges plus per-child-type data field lookups." notable_decisions="['link_type queries are guarded by the declared link_type, parent scan by declared parent_fields, child field lookups by declared children — a type with no lineage block attaches empty arrays with no link/data queries']"]
|
|
414
|
+
// CIL[DOC-CONFIDENCE pass="first" score="0.8" flags="none"]
|
|
415
|
+
// CIL[DOC-STABILITY stability="stable"]
|
|
188
416
|
async function attachLineage(record: any, ctx: any): Promise<void> {
|
|
189
|
-
|
|
190
|
-
|
|
191
|
-
|
|
192
|
-
|
|
193
|
-
|
|
194
|
-
|
|
195
|
-
|
|
196
|
-
|
|
197
|
-
|
|
417
|
+
// Lineage is declared per item type in design_schema.functionality.lineage:
|
|
418
|
+
// { parent_fields: string[], link_type: string, children: { [childTypeSlug]: field } }
|
|
419
|
+
// Each leg is guarded by its own declaration — link queries run only when
|
|
420
|
+
// link_type is declared, the parent field-scan only iterates declared
|
|
421
|
+
// parent_fields, and data-field child lookups only run for declared children
|
|
422
|
+
// entries. A type with no lineage block gets empty parents/children and no
|
|
423
|
+
// link/data queries run at all.
|
|
424
|
+
const { data: typeRow } = await adminDb
|
|
425
|
+
.from('types')
|
|
426
|
+
.select('slug, design_schema')
|
|
427
|
+
.eq('id', record.type_id)
|
|
428
|
+
.single()
|
|
429
|
+
const lineage = typeRow?.design_schema?.functionality?.lineage
|
|
430
|
+
const linkType = typeof lineage?.link_type === 'string' && lineage.link_type ? lineage.link_type : null
|
|
431
|
+
const parentFields: string[] = Array.isArray(lineage?.parent_fields)
|
|
432
|
+
? lineage.parent_fields.filter((f: any) => typeof f === 'string' && f)
|
|
433
|
+
: []
|
|
434
|
+
const childrenMap: Record<string, string> =
|
|
435
|
+
lineage?.children && typeof lineage.children === 'object' ? lineage.children : {}
|
|
198
436
|
|
|
199
437
|
async function parentIdFor(current: any, visited: Set<string>): Promise<string | null> {
|
|
200
|
-
|
|
201
|
-
|
|
202
|
-
|
|
438
|
+
if (linkType) {
|
|
439
|
+
const { data: links } = await ctx.db.from('links').select('target_id').eq('source_id', current.id).eq('link_type', linkType).eq('source_type', 'items').limit(1)
|
|
440
|
+
const linkTarget = links?.[0]?.target_id
|
|
441
|
+
if (linkTarget && !visited.has(linkTarget)) return linkTarget
|
|
442
|
+
}
|
|
203
443
|
const d = current.data || {}
|
|
204
444
|
for (const key of parentFields) {
|
|
205
445
|
const id = d[key]
|
|
@@ -209,6 +449,7 @@ async function attachLineage(record: any, ctx: any): Promise<void> {
|
|
|
209
449
|
}
|
|
210
450
|
|
|
211
451
|
async function getParents(record: any): Promise<any[]> {
|
|
452
|
+
if (!linkType && parentFields.length === 0) return []
|
|
212
453
|
const parents: any[] = []
|
|
213
454
|
const visited = new Set<string>([record.id])
|
|
214
455
|
let current: any = record
|
|
@@ -227,19 +468,21 @@ async function attachLineage(record: any, ctx: any): Promise<void> {
|
|
|
227
468
|
|
|
228
469
|
async function getChildren(record: any): Promise<any[]> {
|
|
229
470
|
const childIds = new Set<string>()
|
|
230
|
-
|
|
231
|
-
|
|
232
|
-
|
|
471
|
+
if (linkType) {
|
|
472
|
+
const { data: linkRows } = await ctx.db.from('links').select('source_id').eq('target_id', record.id).eq('link_type', linkType).eq('target_type', 'items').limit(50)
|
|
473
|
+
for (const row of linkRows || []) {
|
|
474
|
+
if (row.source_id && row.source_id !== record.id) childIds.add(row.source_id)
|
|
475
|
+
}
|
|
233
476
|
}
|
|
234
|
-
const
|
|
235
|
-
|
|
236
|
-
if (
|
|
477
|
+
const childEntries = Object.entries(childrenMap)
|
|
478
|
+
.filter(([slug, field]) => slug && typeof field === 'string' && field)
|
|
479
|
+
if (childEntries.length) {
|
|
237
480
|
try {
|
|
238
|
-
const
|
|
239
|
-
const
|
|
240
|
-
|
|
241
|
-
|
|
242
|
-
const { data: dataChildren } = await ctx.db.from('items').select('id').
|
|
481
|
+
const resolved = await resolveTypeIds(childEntries.map(([slug]) => ({ kind: 'item', slug })))
|
|
482
|
+
for (const [slug, field] of childEntries) {
|
|
483
|
+
const childTypeId = resolved[`item/${slug}`]
|
|
484
|
+
if (!childTypeId) continue
|
|
485
|
+
const { data: dataChildren } = await ctx.db.from('items').select('id').eq('type_id', childTypeId).eq(`data->>${field}`, record.id)
|
|
243
486
|
for (const child of dataChildren || []) {
|
|
244
487
|
if (child.id && child.id !== record.id) childIds.add(child.id)
|
|
245
488
|
}
|
|
@@ -273,7 +516,38 @@ async function attachLineage(record: any, ctx: any): Promise<void> {
|
|
|
273
516
|
record.parents = parents
|
|
274
517
|
record.children = children
|
|
275
518
|
}
|
|
519
|
+
// CIL[END stable_id="~/.framework/functions/admin-data.ts:attachlineage:function"]
|
|
520
|
+
// CIL[DOC-VECTOR type="context" content="purpose='The attachLineage function retrieves and attaches parent and child records to a given record based on its lineage in a hierarchical structure.'; No verified external callers" status="ready"]
|
|
521
|
+
// CIL[DOC-VECTOR type="blast_radius" content="No direct caller data from CIL graph; local impact only" status="ready"]
|
|
522
|
+
// CIL[DOC-VECTOR type="configuration" content="No environment or build configuration dependencies identified" status="ready"]
|
|
523
|
+
// CIL[DOC-VECTOR type="constraint" content="Standard runtime; no special invariants documented" status="ready"]
|
|
524
|
+
// CIL[DOC-VECTOR type="implementation_pattern" content="" status="pending_human_input"]
|
|
525
|
+
// CIL[DOC-VECTOR type="user_journey" content="" status="pending_human_input"]
|
|
276
526
|
|
|
527
|
+
// CIL[DOC-MACRO purpose="The 'get' constant defines an asynchronous handler for retrieving records from a database based on entity type and ID."]
|
|
528
|
+
// CIL[DOC-RESPONSIBILITY responsibility="The 'get' constant defines an asynchronous handler for retrieving records from a database based on entity type and ID. It ensures proper logging and validation of input parameters before fetching and sanitizing the requested data."]
|
|
529
|
+
// CIL[DOC-CONTEXT module="admin-data" layer="app-specific" related_files=".framework/functions/_shared/middleware,.framework/functions/_shared/permissions,.framework/functions/_shared/db,.framework/functions/_shared/principal,.framework/functions/_shared/resolve-ids,.framework/functions/_shared/trigger-engine,.framework/functions/_shared/logging,.framework/functions/_shared/access"]
|
|
530
|
+
// CIL[DOC-CONTRACT inputs="none" outputs="none" errors="Error — Valid entity parameter is required, Error — ID parameter is required, Error — Record not found" side_effects="none dependencies="withAdminLogging, ctx.db.from, sanitizeRecordData, adminDb.from, attachLineage, projectMessageForCustomer"]
|
|
531
|
+
// CIL[DOC-MICRO logic_summary="The 'get' constant defines an asynchronous handler for retrieving records from a database based on entity type and ID. It ensures proper logging and validation of input parameters before fetching and sanitizing the requested data." notable_decisions="none"]
|
|
532
|
+
// CIL[DOC-CONFIDENCE pass="second" score="0.90" flags="none"]
|
|
533
|
+
// CIL[DOC-STABILITY stability="stable"]
|
|
534
|
+
/**
|
|
535
|
+
* The 'get' constant defines an asynchronous handler for retrieving records from a database based on entity type and ID. It ensures proper logging and validation of input parameters before fetching and sanitizing the requested data.
|
|
536
|
+
*
|
|
537
|
+
* @throws Error — Valid entity parameter is required, Error — ID parameter is required, Error — Record not found
|
|
538
|
+
* @sideEffects none
|
|
539
|
+
* @stability stable
|
|
540
|
+
* @calls withAdminLogging, ctx.db.from, sanitizeRecordData, adminDb.from, attachLineage, projectMessageForCustomer
|
|
541
|
+
* @cil-generated
|
|
542
|
+
*/
|
|
543
|
+
// CIL[BEGIN stable_id="~/.framework/functions/admin-data.ts:get:constant" type="constant" identity="get" parent="~/.framework/functions/admin-data.ts"]
|
|
544
|
+
// CIL[DOC-MACRO purpose="get constant"]
|
|
545
|
+
// CIL[DOC-RESPONSIBILITY responsibility="Implements the get constant."]
|
|
546
|
+
// CIL[DOC-CONTEXT module=".framework/functions/admin-data.ts" layer="app-specific" related_files=""]
|
|
547
|
+
// CIL[DOC-CONTRACT inputs="none" outputs="none" errors="none" side_effects="none"]
|
|
548
|
+
// CIL[DOC-MICRO logic_summary="Implements the get constant." notable_decisions="[]"]
|
|
549
|
+
// CIL[DOC-CONFIDENCE pass="first" score="0.8" flags="none"]
|
|
550
|
+
// CIL[DOC-STABILITY stability="stable"]
|
|
277
551
|
export const get = createHandler(async (ctx, _body) => {
|
|
278
552
|
const { entity, id, view: viewSlug } = ctx.query || {}
|
|
279
553
|
const method = ctx.query?.method || 'GET'
|
|
@@ -306,9 +580,29 @@ export const get = createHandler(async (ctx, _body) => {
|
|
|
306
580
|
throw new Error('Record not found')
|
|
307
581
|
}
|
|
308
582
|
|
|
309
|
-
|
|
583
|
+
let sanitizedRecord = await sanitizeRecordData(ctx, data, entity)
|
|
584
|
+
|
|
585
|
+
// Customer-scoped principals cannot fetch internal threads or
|
|
586
|
+
// unprojectable internal messages by id.
|
|
587
|
+
if (!hasInternalAudience(ctx.principal) && sanitizedRecord?.visibility === 'internal') {
|
|
588
|
+
if (entity === 'threads') {
|
|
589
|
+
throw new Error('Record not found')
|
|
590
|
+
}
|
|
591
|
+
if (entity === 'messages') {
|
|
592
|
+
const { data: parentThread } = await adminDb
|
|
593
|
+
.from('threads')
|
|
594
|
+
.select('visibility')
|
|
595
|
+
.eq('id', sanitizedRecord.thread_id)
|
|
596
|
+
.maybeSingle()
|
|
597
|
+
const threadIsInternal = parentThread?.visibility !== 'external' && parentThread?.visibility !== 'public'
|
|
598
|
+
sanitizedRecord = projectMessageForCustomer(sanitizedRecord, { threadIsInternal })
|
|
599
|
+
if (!sanitizedRecord) throw new Error('Record not found')
|
|
600
|
+
}
|
|
601
|
+
}
|
|
310
602
|
|
|
311
|
-
|
|
603
|
+
// Lineage traversal costs several sequential reads — polling callers
|
|
604
|
+
// that never render it pass lineage=0 to skip it.
|
|
605
|
+
if (entity === 'items' && (ctx as any).query?.lineage !== '0') {
|
|
312
606
|
await attachLineage(sanitizedRecord, ctx)
|
|
313
607
|
}
|
|
314
608
|
|
|
@@ -322,23 +616,37 @@ export const get = createHandler(async (ctx, _body) => {
|
|
|
322
616
|
}
|
|
323
617
|
)
|
|
324
618
|
})
|
|
325
|
-
// CIL[END
|
|
326
|
-
// CIL[
|
|
327
|
-
// CIL[DOC-
|
|
328
|
-
// CIL[DOC-
|
|
329
|
-
// CIL[DOC-
|
|
330
|
-
// CIL[DOC-RESPONSIBILITY responsibility="Validate, resolve type, create record with inheritance and triggers"]
|
|
331
|
-
// CIL[DOC-CONTEXT module="admin-data" layer="api-handler" related_files="[\".framework/src/pages/admin/TypeDetailPage.tsx\",\".framework/functions/_shared/db.ts\",\".framework/src/components/ui/dialog.tsx\",\"custom/apps/cortex/pages/operations/OperationsDashboard.tsx\",\".framework/functions/_shared/schema-utils.ts\",\"\\\"]"]
|
|
332
|
-
// CIL[DOC-CONTRACT inputs="none" outputs="created_record" errors="entity_required,type_resolution_failed,parent_not_found" side_effects="database_insert,trigger_fire,permission_inheritance"]
|
|
333
|
-
// CIL[DOC-MICRO logic_summary="Resolves type, handles account inheritance, applies defaults, fires triggers" notable_decisions="[]"]
|
|
334
|
-
// CIL[DOC-CONFIDENCE pass="second" score="0.95" flags="complex_dependencies"]
|
|
335
|
-
// CIL[DOC-STABILITY stability="stable"]
|
|
336
|
-
// CIL[DOC-VECTOR type="context" content="Layer: api-handler. Direct callers: 0. Direct calls: 0. Related files: .framework/src/pages/admin/TypeDetailPage.tsx, .framework/functions/_shared/db.ts, .framework/src/components/ui/dialog.tsx, custom/apps/cortex/pages/operations/OperationsDashboard.tsx, .framework/functions/_shared/schema-utils.ts, \."]
|
|
337
|
-
// CIL[DOC-VECTOR type="blast_radius" content="Direct callers: 0. Total affected: 0."]
|
|
338
|
-
// CIL[DOC-VECTOR type="configuration" content="No configuration dependencies."]
|
|
339
|
-
// CIL[DOC-VECTOR type="constraint" content="No test paths identified."]
|
|
619
|
+
// CIL[END stable_id="~/.framework/functions/admin-data.ts:get:constant"]
|
|
620
|
+
// CIL[DOC-VECTOR type="context" content="purpose='The 'get' constant defines an asynchronous handler for retrieving records from a database based on entity type and ID.'; No verified external callers" status="ready"]
|
|
621
|
+
// CIL[DOC-VECTOR type="blast_radius" content="No direct caller data from CIL graph; local impact only" status="ready"]
|
|
622
|
+
// CIL[DOC-VECTOR type="configuration" content="No environment or build configuration dependencies identified" status="ready"]
|
|
623
|
+
// CIL[DOC-VECTOR type="constraint" content="Standard runtime; no special invariants documented" status="ready"]
|
|
340
624
|
// CIL[DOC-VECTOR type="implementation_pattern" content="" status="pending_human_input"]
|
|
341
625
|
// CIL[DOC-VECTOR type="user_journey" content="" status="pending_human_input"]
|
|
626
|
+
// CIL[DOC-MACRO purpose="The 'create' constant defines an asynchronous handler for creating new entities in the admin data context."]
|
|
627
|
+
// CIL[DOC-RESPONSIBILITY responsibility="The 'create' constant defines an asynchronous handler for creating new entities in the admin data context. It validates input data and logs the creation action while handling various entity types."]
|
|
628
|
+
// CIL[DOC-CONTEXT module="admin-data" layer="app-specific" related_files=".framework/functions/_shared/middleware,.framework/functions/_shared/permissions,.framework/functions/_shared/db,.framework/functions/_shared/principal,.framework/functions/_shared/resolve-ids,.framework/functions/_shared/trigger-engine,.framework/functions/_shared/logging,.framework/functions/_shared/access"]
|
|
629
|
+
// CIL[DOC-CONTRACT inputs="none" outputs="none" errors="Error — Valid entity parameter is required; Error — level and message are required for logs; Error — suite is required for test_runs; Error — metric_name and metric_value are required for observability; Error — slug and name are required for test_cases." side_effects="Database writes for new entity records, logging actions, and triggering additional processes. dependencies="withAdminLogging, ctx.db.from, fireCreateTriggers, sanitizeRecordData"]
|
|
630
|
+
// CIL[DOC-MICRO logic_summary="The 'create' constant defines an asynchronous handler for creating new entities in the admin data context. It validates input data and logs the creation action while handling various entity types." notable_decisions="none"]
|
|
631
|
+
// CIL[DOC-CONFIDENCE pass="second" score="0.90" flags="none"]
|
|
632
|
+
// CIL[DOC-STABILITY stability="stable"]
|
|
633
|
+
/**
|
|
634
|
+
* The 'create' constant defines an asynchronous handler for creating new entities in the admin data context. It validates input data and logs the creation action while handling various entity types.
|
|
635
|
+
*
|
|
636
|
+
* @throws Error — Valid entity parameter is required; Error — level and message are required for logs; Error — suite is required for test_runs; Error — metric_name and metric_value are required for observability; Error — slug and name are required for test_cases.
|
|
637
|
+
* @sideEffects Database writes for new entity records, logging actions, and triggering additional processes.
|
|
638
|
+
* @stability stable
|
|
639
|
+
* @calls withAdminLogging, ctx.db.from, fireCreateTriggers, sanitizeRecordData
|
|
640
|
+
* @cil-generated
|
|
641
|
+
*/
|
|
642
|
+
// CIL[BEGIN stable_id="~/.framework/functions/admin-data.ts:create:constant" type="constant" identity="create" parent="~/.framework/functions/admin-data.ts"]
|
|
643
|
+
// CIL[DOC-MACRO purpose="create constant"]
|
|
644
|
+
// CIL[DOC-RESPONSIBILITY responsibility="Implements the create constant."]
|
|
645
|
+
// CIL[DOC-CONTEXT module=".framework/functions/admin-data.ts" layer="app-specific" related_files=""]
|
|
646
|
+
// CIL[DOC-CONTRACT inputs="none" outputs="none" errors="none" side_effects="none"]
|
|
647
|
+
// CIL[DOC-MICRO logic_summary="Implements the create constant." notable_decisions="[]"]
|
|
648
|
+
// CIL[DOC-CONFIDENCE pass="first" score="0.8" flags="none"]
|
|
649
|
+
// CIL[DOC-STABILITY stability="stable"]
|
|
342
650
|
export const create = createHandler(async (ctx, body) => {
|
|
343
651
|
const entity = body?.entity || ctx.query?.entity
|
|
344
652
|
const type_slug = body?.type_slug
|
|
@@ -407,6 +715,11 @@ export const create = createHandler(async (ctx, body) => {
|
|
|
407
715
|
|
|
408
716
|
recordData.type_id = typeRecord.id
|
|
409
717
|
|
|
718
|
+
// Per-type create rate limit. Apps opt in by declaring
|
|
719
|
+
// config.rate_limits['<type_slug>_create'] in their manifest;
|
|
720
|
+
// with no policy the cached config read is the only cost.
|
|
721
|
+
await checkTypeSlugRateLimit(ctx, body?.type_slug)
|
|
722
|
+
|
|
410
723
|
let designSchema = typeRecord.design_schema || {}
|
|
411
724
|
if (!designSchema.record_permissions) {
|
|
412
725
|
designSchema = { ...PERMISSIONS_ALL, ...designSchema }
|
|
@@ -456,7 +769,7 @@ export const create = createHandler(async (ctx, body) => {
|
|
|
456
769
|
...recordData,
|
|
457
770
|
design_schema: designSchema,
|
|
458
771
|
validation_schema: typeRecord.validation_schema || {},
|
|
459
|
-
created_by: ctx.principal?.id,
|
|
772
|
+
...(UNAUDITED_ENTITIES.includes(entity) ? {} : { created_by: ctx.principal?.type === 'human' ? ctx.principal.id : null }),
|
|
460
773
|
created_at: new Date().toISOString(),
|
|
461
774
|
updated_at: new Date().toISOString()
|
|
462
775
|
}
|
|
@@ -477,7 +790,9 @@ export const create = createHandler(async (ctx, body) => {
|
|
|
477
790
|
'create',
|
|
478
791
|
designSchema
|
|
479
792
|
)
|
|
480
|
-
|
|
793
|
+
const isMachineGlobal = ctx.principal?.type === 'machine' &&
|
|
794
|
+
(ctx.principal.scopes || []).includes('*:*')
|
|
795
|
+
if (!perms.canCreate && !isMachineGlobal) {
|
|
481
796
|
const e: any = new Error('Insufficient permissions to create this record')
|
|
482
797
|
e.statusCode = 403
|
|
483
798
|
throw e
|
|
@@ -499,21 +814,37 @@ export const create = createHandler(async (ctx, body) => {
|
|
|
499
814
|
}
|
|
500
815
|
)
|
|
501
816
|
})
|
|
502
|
-
// CIL[END
|
|
503
|
-
// CIL[
|
|
504
|
-
// CIL[DOC-
|
|
505
|
-
// CIL[DOC-
|
|
506
|
-
// CIL[DOC-
|
|
507
|
-
// CIL[DOC-CONTRACT inputs="none" outputs="updated_record" errors="entity_required,id_required" side_effects="database_update,trigger_fire"]
|
|
508
|
-
// CIL[DOC-MICRO logic_summary="Filters protected fields, adds audit fields, updates record, fires triggers" notable_decisions="[]"]
|
|
509
|
-
// CIL[DOC-CONFIDENCE pass="second" score="0.95" flags="none"]
|
|
510
|
-
// CIL[DOC-STABILITY stability="stable"]
|
|
511
|
-
// CIL[DOC-VECTOR type="context" content="Layer: api-handler. Direct callers: 0. Direct calls: 0. Related files: .framework/src/pages/admin/TypeDetailPage.tsx."]
|
|
512
|
-
// CIL[DOC-VECTOR type="blast_radius" content="Direct callers: 0. Total affected: 0."]
|
|
513
|
-
// CIL[DOC-VECTOR type="configuration" content="No configuration dependencies."]
|
|
514
|
-
// CIL[DOC-VECTOR type="constraint" content="No test paths identified."]
|
|
817
|
+
// CIL[END stable_id="~/.framework/functions/admin-data.ts:create:constant"]
|
|
818
|
+
// CIL[DOC-VECTOR type="context" content="purpose='The 'create' constant defines an asynchronous handler for creating new entities in the admin data context.'; No verified external callers" status="ready"]
|
|
819
|
+
// CIL[DOC-VECTOR type="blast_radius" content="No direct caller data from CIL graph; local impact only" status="ready"]
|
|
820
|
+
// CIL[DOC-VECTOR type="configuration" content="No environment or build configuration dependencies identified" status="ready"]
|
|
821
|
+
// CIL[DOC-VECTOR type="constraint" content="Standard runtime; no special invariants documented" status="ready"]
|
|
515
822
|
// CIL[DOC-VECTOR type="implementation_pattern" content="" status="pending_human_input"]
|
|
516
823
|
// CIL[DOC-VECTOR type="user_journey" content="" status="pending_human_input"]
|
|
824
|
+
// CIL[DOC-MACRO purpose="The update function handles updating records in the database while ensuring proper validation and permissions."]
|
|
825
|
+
// CIL[DOC-RESPONSIBILITY responsibility="The update function handles updating records in the database while ensuring proper validation and permissions. It logs the update action and sanitizes the data before performing the update."]
|
|
826
|
+
// CIL[DOC-CONTEXT module="admin-data" layer="app-specific" related_files=".framework/functions/_shared/middleware,.framework/functions/_shared/permissions,.framework/functions/_shared/db,.framework/functions/_shared/principal,.framework/functions/_shared/resolve-ids,.framework/functions/_shared/trigger-engine,.framework/functions/_shared/logging,.framework/functions/_shared/access"]
|
|
827
|
+
// CIL[DOC-CONTRACT inputs="none" outputs="none" errors="Error — Valid entity parameter is required; Error — ID is required for update; Error — Record not found or access denied; Error — Insufficient permissions to update this record." side_effects="Database update operation, logging actions, and triggering update events. dependencies="withAdminLogging, validateUpdatePermissions, ctx.db.from, fireUpdateTriggers, sanitizeRecordData"]
|
|
828
|
+
// CIL[DOC-MICRO logic_summary="The update function handles updating records in the database while ensuring proper validation and permissions. It logs the update action and sanitizes the data before performing the update." notable_decisions="none"]
|
|
829
|
+
// CIL[DOC-CONFIDENCE pass="second" score="0.90" flags="none"]
|
|
830
|
+
// CIL[DOC-STABILITY stability="stable"]
|
|
831
|
+
/**
|
|
832
|
+
* The update function handles updating records in the database while ensuring proper validation and permissions. It logs the update action and sanitizes the data before performing the update.
|
|
833
|
+
*
|
|
834
|
+
* @throws Error — Valid entity parameter is required; Error — ID is required for update; Error — Record not found or access denied; Error — Insufficient permissions to update this record.
|
|
835
|
+
* @sideEffects Database update operation, logging actions, and triggering update events.
|
|
836
|
+
* @stability stable
|
|
837
|
+
* @calls withAdminLogging, validateUpdatePermissions, ctx.db.from, fireUpdateTriggers, sanitizeRecordData
|
|
838
|
+
* @cil-generated
|
|
839
|
+
*/
|
|
840
|
+
// CIL[BEGIN stable_id="~/.framework/functions/admin-data.ts:update:constant" type="constant" identity="update" parent="~/.framework/functions/admin-data.ts"]
|
|
841
|
+
// CIL[DOC-MACRO purpose="update constant"]
|
|
842
|
+
// CIL[DOC-RESPONSIBILITY responsibility="Implements the update constant."]
|
|
843
|
+
// CIL[DOC-CONTEXT module=".framework/functions/admin-data.ts" layer="app-specific" related_files=""]
|
|
844
|
+
// CIL[DOC-CONTRACT inputs="none" outputs="none" errors="none" side_effects="none"]
|
|
845
|
+
// CIL[DOC-MICRO logic_summary="Implements the update constant." notable_decisions="[]"]
|
|
846
|
+
// CIL[DOC-CONFIDENCE pass="first" score="0.8" flags="none"]
|
|
847
|
+
// CIL[DOC-STABILITY stability="stable"]
|
|
517
848
|
export const update = createHandler(async (ctx, body) => {
|
|
518
849
|
const { entity, id } = ctx.query || {}
|
|
519
850
|
const method = ctx.query?.method || 'PATCH'
|
|
@@ -528,7 +859,7 @@ export const update = createHandler(async (ctx, body) => {
|
|
|
528
859
|
typeSlug: type_slug
|
|
529
860
|
},
|
|
530
861
|
async () => {
|
|
531
|
-
const { design_schema: _ds, validation_schema: _vs, type_id: _ti, type_slug: _ts, id: _id, account_id: requestedAccountId, ...recordData } = body || {}
|
|
862
|
+
const { design_schema: _ds, validation_schema: _vs, type_id: _ti, type_slug: _ts, id: _id, account_id: requestedAccountId, entity: _entity, ...recordData } = body || {}
|
|
532
863
|
|
|
533
864
|
if (!entity || !VALID_ENTITIES.includes(entity)) {
|
|
534
865
|
throw new Error('Valid entity parameter is required')
|
|
@@ -560,16 +891,20 @@ export const update = createHandler(async (ctx, body) => {
|
|
|
560
891
|
typeSlugForPermissions
|
|
561
892
|
)
|
|
562
893
|
|
|
563
|
-
if (!validation.valid) {
|
|
894
|
+
if (!validation.valid && !isSystemAdmin(ctx.principal)) {
|
|
564
895
|
const e: any = new Error(validation.error || 'Insufficient permissions to update this record')
|
|
565
896
|
e.statusCode = 403
|
|
566
897
|
throw e
|
|
567
898
|
}
|
|
568
899
|
|
|
569
|
-
const sanitizedUpdate = validation.sanitizedData || recordData
|
|
900
|
+
const sanitizedUpdate = (validation as any).sanitizedData || recordData
|
|
570
901
|
const dataToUpdate = RAW_ENTITIES.includes(entity)
|
|
571
902
|
? { ...sanitizedUpdate }
|
|
572
|
-
: {
|
|
903
|
+
: {
|
|
904
|
+
...sanitizedUpdate,
|
|
905
|
+
...(UNAUDITED_ENTITIES.includes(entity) ? {} : { updated_by: ctx.principal?.type === 'human' ? ctx.principal.id : null }),
|
|
906
|
+
updated_at: new Date().toISOString()
|
|
907
|
+
}
|
|
573
908
|
|
|
574
909
|
const { data, error: err } = await ctx.db.from(entity)
|
|
575
910
|
.update(dataToUpdate)
|
|
@@ -586,21 +921,37 @@ export const update = createHandler(async (ctx, body) => {
|
|
|
586
921
|
}
|
|
587
922
|
)
|
|
588
923
|
})
|
|
589
|
-
// CIL[END
|
|
590
|
-
// CIL[
|
|
591
|
-
// CIL[DOC-
|
|
592
|
-
// CIL[DOC-
|
|
593
|
-
// CIL[DOC-
|
|
594
|
-
// CIL[DOC-CONTRACT inputs="none" outputs="delete_confirmation" errors="entity_required,id_required" side_effects="database_delete,trigger_fire"]
|
|
595
|
-
// CIL[DOC-MICRO logic_summary="Checks soft delete support, performs appropriate delete method, fires triggers" notable_decisions="[]"]
|
|
596
|
-
// CIL[DOC-CONFIDENCE pass="second" score="0.95" flags="none"]
|
|
597
|
-
// CIL[DOC-STABILITY stability="stable"]
|
|
598
|
-
// CIL[DOC-VECTOR type="context" content="Layer: api-handler. Direct callers: 0. Direct calls: 0. Related files: none."]
|
|
599
|
-
// CIL[DOC-VECTOR type="blast_radius" content="Direct callers: 0. Total affected: 0."]
|
|
600
|
-
// CIL[DOC-VECTOR type="configuration" content="No configuration dependencies."]
|
|
601
|
-
// CIL[DOC-VECTOR type="constraint" content="No test paths identified."]
|
|
924
|
+
// CIL[END stable_id="~/.framework/functions/admin-data.ts:update:constant"]
|
|
925
|
+
// CIL[DOC-VECTOR type="context" content="purpose='The update function handles updating records in the database while ensuring proper validation and permissions.'; No verified external callers" status="ready"]
|
|
926
|
+
// CIL[DOC-VECTOR type="blast_radius" content="No direct caller data from CIL graph; local impact only" status="ready"]
|
|
927
|
+
// CIL[DOC-VECTOR type="configuration" content="No environment or build configuration dependencies identified" status="ready"]
|
|
928
|
+
// CIL[DOC-VECTOR type="constraint" content="Standard runtime; no special invariants documented" status="ready"]
|
|
602
929
|
// CIL[DOC-VECTOR type="implementation_pattern" content="" status="pending_human_input"]
|
|
603
930
|
// CIL[DOC-VECTOR type="user_journey" content="" status="pending_human_input"]
|
|
931
|
+
// CIL[DOC-MACRO purpose="The 'remove' constant defines an asynchronous handler for removing records from a database, supporting both soft and hard deletes based on the provided parameters."]
|
|
932
|
+
// CIL[DOC-RESPONSIBILITY responsibility="The 'remove' constant defines an asynchronous handler for removing records from a database, supporting both soft and hard deletes based on the provided parameters. It ensures that the entity and ID are valid and checks for sufficient permissions before performing the delete operation."]
|
|
933
|
+
// CIL[DOC-CONTEXT module="admin-data" layer="app-specific" related_files=".framework/functions/_shared/middleware,.framework/functions/_shared/permissions,.framework/functions/_shared/db,.framework/functions/_shared/principal,.framework/functions/_shared/resolve-ids,.framework/functions/_shared/trigger-engine,.framework/functions/_shared/logging,.framework/functions/_shared/access"]
|
|
934
|
+
// CIL[DOC-CONTRACT inputs="none" outputs="none" errors="Error — Valid entity parameter is required, Error — ID is required for delete, Error — Record not found or access denied, Error — Insufficient permissions to delete this record." side_effects="Updates or deletes records in the database. dependencies="withAdminLogging, ctx.db.from, resolveFirstSurfacePermissions, entitySupportsSoftDelete, sanitizeRecordData"]
|
|
935
|
+
// CIL[DOC-MICRO logic_summary="The 'remove' constant defines an asynchronous handler for removing records from a database, supporting both soft and hard deletes based on the provided parameters. It ensures that the entity and ID are valid and checks for sufficient permissions before performing the delete operation." notable_decisions="none"]
|
|
936
|
+
// CIL[DOC-CONFIDENCE pass="second" score="0.90" flags="none"]
|
|
937
|
+
// CIL[DOC-STABILITY stability="stable"]
|
|
938
|
+
/**
|
|
939
|
+
* The 'remove' constant defines an asynchronous handler for removing records from a database, supporting both soft and hard deletes based on the provided parameters. It ensures that the entity and ID are valid and checks for sufficient permissions before performing the delete operation.
|
|
940
|
+
*
|
|
941
|
+
* @throws Error — Valid entity parameter is required, Error — ID is required for delete, Error — Record not found or access denied, Error — Insufficient permissions to delete this record.
|
|
942
|
+
* @sideEffects Updates or deletes records in the database.
|
|
943
|
+
* @stability stable
|
|
944
|
+
* @calls withAdminLogging, ctx.db.from, resolveFirstSurfacePermissions, entitySupportsSoftDelete, sanitizeRecordData
|
|
945
|
+
* @cil-generated
|
|
946
|
+
*/
|
|
947
|
+
// CIL[BEGIN stable_id="~/.framework/functions/admin-data.ts:remove:constant" type="constant" identity="remove" parent="~/.framework/functions/admin-data.ts"]
|
|
948
|
+
// CIL[DOC-MACRO purpose="remove constant"]
|
|
949
|
+
// CIL[DOC-RESPONSIBILITY responsibility="Implements the remove constant."]
|
|
950
|
+
// CIL[DOC-CONTEXT module=".framework/functions/admin-data.ts" layer="app-specific" related_files=""]
|
|
951
|
+
// CIL[DOC-CONTRACT inputs="none" outputs="none" errors="none" side_effects="none"]
|
|
952
|
+
// CIL[DOC-MICRO logic_summary="Implements the remove constant." notable_decisions="[]"]
|
|
953
|
+
// CIL[DOC-CONFIDENCE pass="first" score="0.8" flags="none"]
|
|
954
|
+
// CIL[DOC-STABILITY stability="stable"]
|
|
604
955
|
export const remove = createHandler(async (ctx, _body) => {
|
|
605
956
|
const { entity, id, soft = 'true' } = ctx.query || {}
|
|
606
957
|
const method = ctx.query?.method || 'DELETE'
|
|
@@ -640,7 +991,7 @@ export const remove = createHandler(async (ctx, _body) => {
|
|
|
640
991
|
existing.design_schema
|
|
641
992
|
)
|
|
642
993
|
|
|
643
|
-
if (!perms.canDelete) {
|
|
994
|
+
if (!perms.canDelete && !isSystemAdmin(ctx.principal)) {
|
|
644
995
|
const e: any = new Error('Insufficient permissions to delete this record')
|
|
645
996
|
e.statusCode = 403
|
|
646
997
|
throw e
|
|
@@ -652,7 +1003,7 @@ export const remove = createHandler(async (ctx, _body) => {
|
|
|
652
1003
|
const { data, error: err } = await ctx.db.from(entity)
|
|
653
1004
|
.update({
|
|
654
1005
|
is_active: false,
|
|
655
|
-
updated_by: ctx.principal?.id,
|
|
1006
|
+
updated_by: ctx.principal?.type === 'human' ? ctx.principal.id : null,
|
|
656
1007
|
updated_at: new Date().toISOString()
|
|
657
1008
|
})
|
|
658
1009
|
.eq('id', id)
|
|
@@ -672,21 +1023,38 @@ export const remove = createHandler(async (ctx, _body) => {
|
|
|
672
1023
|
}
|
|
673
1024
|
)
|
|
674
1025
|
})
|
|
675
|
-
// CIL[END
|
|
676
|
-
// CIL[
|
|
677
|
-
// CIL[DOC-
|
|
678
|
-
// CIL[DOC-
|
|
679
|
-
// CIL[DOC-
|
|
680
|
-
// CIL[DOC-CONTRACT inputs="none" outputs="search_field:string" errors="none" side_effects="none"]
|
|
681
|
-
// CIL[DOC-MICRO logic_summary="Maps entity types to their primary display fields for search" notable_decisions="[]"]
|
|
682
|
-
// CIL[DOC-CONFIDENCE pass="second" score="0.95" flags="none"]
|
|
683
|
-
// CIL[DOC-STABILITY stability="stable"]
|
|
684
|
-
// CIL[DOC-VECTOR type="context" content="Layer: api-handler. Direct callers: 0. Direct calls: 0. Related files: none."]
|
|
685
|
-
// CIL[DOC-VECTOR type="blast_radius" content="Direct callers: 0. Total affected: 0."]
|
|
686
|
-
// CIL[DOC-VECTOR type="configuration" content="No configuration dependencies."]
|
|
687
|
-
// CIL[DOC-VECTOR type="constraint" content="No test paths identified."]
|
|
1026
|
+
// CIL[END stable_id="~/.framework/functions/admin-data.ts:remove:constant"]
|
|
1027
|
+
// CIL[DOC-VECTOR type="context" content="purpose='The 'remove' constant defines an asynchronous handler for removing records from a database, supporting both soft and hard deletes based on the provided parameters.'; No verified external callers" status="ready"]
|
|
1028
|
+
// CIL[DOC-VECTOR type="blast_radius" content="No direct caller data from CIL graph; local impact only" status="ready"]
|
|
1029
|
+
// CIL[DOC-VECTOR type="configuration" content="No environment or build configuration dependencies identified" status="ready"]
|
|
1030
|
+
// CIL[DOC-VECTOR type="constraint" content="Standard runtime; no special invariants documented" status="ready"]
|
|
688
1031
|
// CIL[DOC-VECTOR type="implementation_pattern" content="" status="pending_human_input"]
|
|
689
1032
|
// CIL[DOC-VECTOR type="user_journey" content="" status="pending_human_input"]
|
|
1033
|
+
// CIL[DOC-MACRO purpose="Retrieves the appropriate search field name for a given entity type."]
|
|
1034
|
+
// CIL[DOC-RESPONSIBILITY responsibility="Retrieves the appropriate search field name for a given entity type. This function helps standardize search queries across different entity types in the application."]
|
|
1035
|
+
// CIL[DOC-CONTEXT module="admin-data" layer="app-specific" related_files=".framework/functions/_shared/middleware,.framework/functions/_shared/permissions,.framework/functions/_shared/db,.framework/functions/_shared/principal,.framework/functions/_shared/resolve-ids,.framework/functions/_shared/trigger-engine,.framework/functions/_shared/logging,.framework/functions/_shared/access"]
|
|
1036
|
+
// CIL[DOC-CONTRACT inputs="entity: string (required) — the name of the entity for which to retrieve the search field." outputs="string — the search field name associated with the entity or 'id' if not found." errors="none" side_effects="none"]
|
|
1037
|
+
// CIL[DOC-MICRO logic_summary="Retrieves the appropriate search field name for a given entity type. This function helps standardize search queries across different entity types in the application." notable_decisions="none"]
|
|
1038
|
+
// CIL[DOC-CONFIDENCE pass="second" score="0.90" flags="none"]
|
|
1039
|
+
// CIL[DOC-STABILITY stability="stable"]
|
|
1040
|
+
/**
|
|
1041
|
+
* Retrieves the appropriate search field name for a given entity type. This function helps standardize search queries across different entity types in the application.
|
|
1042
|
+
*
|
|
1043
|
+
* @inputSpec
|
|
1044
|
+
* entity: string (required) — the name of the entity for which to retrieve the search field.
|
|
1045
|
+
* @outputSpec string — the search field name associated with the entity or 'id' if not found.
|
|
1046
|
+
* @sideEffects none
|
|
1047
|
+
* @stability stable
|
|
1048
|
+
* @cil-generated
|
|
1049
|
+
*/
|
|
1050
|
+
// CIL[BEGIN stable_id="~/.framework/functions/admin-data.ts:getsearchfield:function" type="function" identity="getSearchField" parent="~/.framework/functions/admin-data.ts"]
|
|
1051
|
+
// CIL[DOC-MACRO purpose="getSearchField function"]
|
|
1052
|
+
// CIL[DOC-RESPONSIBILITY responsibility="Implements the getSearchField function."]
|
|
1053
|
+
// CIL[DOC-CONTEXT module=".framework/functions/admin-data.ts" layer="app-specific" related_files=""]
|
|
1054
|
+
// CIL[DOC-CONTRACT inputs="none" outputs="none" errors="none" side_effects="none"]
|
|
1055
|
+
// CIL[DOC-MICRO logic_summary="Implements the getSearchField function." notable_decisions="[]"]
|
|
1056
|
+
// CIL[DOC-CONFIDENCE pass="first" score="0.8" flags="none"]
|
|
1057
|
+
// CIL[DOC-STABILITY stability="stable"]
|
|
690
1058
|
function getSearchField(entity: string): string {
|
|
691
1059
|
const searchFields: Record<string, string> = {
|
|
692
1060
|
accounts: 'display_name',
|
|
@@ -705,40 +1073,73 @@ function getSearchField(entity: string): string {
|
|
|
705
1073
|
}
|
|
706
1074
|
return searchFields[entity] || 'id'
|
|
707
1075
|
}
|
|
708
|
-
// CIL[END
|
|
709
|
-
// CIL[
|
|
710
|
-
// CIL[DOC-
|
|
711
|
-
// CIL[DOC-
|
|
712
|
-
// CIL[DOC-
|
|
713
|
-
// CIL[DOC-CONTRACT inputs="none" outputs="boolean:supports_soft_delete" errors="none" side_effects="none"]
|
|
714
|
-
// CIL[DOC-MICRO logic_summary="Returns true if entity has is_active column for soft delete" notable_decisions="[]"]
|
|
715
|
-
// CIL[DOC-CONFIDENCE pass="second" score="0.95" flags="none"]
|
|
716
|
-
// CIL[DOC-STABILITY stability="stable"]
|
|
717
|
-
// CIL[DOC-VECTOR type="context" content="Layer: api-handler. Direct callers: 0. Direct calls: 0. Related files: none."]
|
|
718
|
-
// CIL[DOC-VECTOR type="blast_radius" content="Direct callers: 0. Total affected: 0."]
|
|
719
|
-
// CIL[DOC-VECTOR type="configuration" content="No configuration dependencies."]
|
|
720
|
-
// CIL[DOC-VECTOR type="constraint" content="No test paths identified."]
|
|
1076
|
+
// CIL[END stable_id="~/.framework/functions/admin-data.ts:getsearchfield:function"]
|
|
1077
|
+
// CIL[DOC-VECTOR type="context" content="purpose='Retrieves the appropriate search field name for a given entity type.'; No verified external callers" status="ready"]
|
|
1078
|
+
// CIL[DOC-VECTOR type="blast_radius" content="No direct caller data from CIL graph; local impact only" status="ready"]
|
|
1079
|
+
// CIL[DOC-VECTOR type="configuration" content="No environment or build configuration dependencies identified" status="ready"]
|
|
1080
|
+
// CIL[DOC-VECTOR type="constraint" content="Standard runtime; no special invariants documented" status="ready"]
|
|
721
1081
|
// CIL[DOC-VECTOR type="implementation_pattern" content="" status="pending_human_input"]
|
|
722
1082
|
// CIL[DOC-VECTOR type="user_journey" content="" status="pending_human_input"]
|
|
1083
|
+
// CIL[DOC-MACRO purpose="Determines if a given entity supports soft deletion by checking against a predefined list of entities."]
|
|
1084
|
+
// CIL[DOC-RESPONSIBILITY responsibility="Determines if a given entity supports soft deletion by checking against a predefined list of entities. This function exists to facilitate operations that depend on the soft delete capability of certain entities."]
|
|
1085
|
+
// CIL[DOC-CONTEXT module="admin-data" layer="app-specific" related_files=".framework/functions/_shared/middleware,.framework/functions/_shared/permissions,.framework/functions/_shared/db,.framework/functions/_shared/principal,.framework/functions/_shared/resolve-ids,.framework/functions/_shared/trigger-engine,.framework/functions/_shared/logging,.framework/functions/_shared/access"]
|
|
1086
|
+
// CIL[DOC-CONTRACT inputs="entity: string (required) — the name of the entity to check for soft delete support." outputs="boolean — returns true if the entity supports soft deletion, otherwise false." errors="none" side_effects="none"]
|
|
1087
|
+
// CIL[DOC-MICRO logic_summary="Determines if a given entity supports soft deletion by checking against a predefined list of entities. This function exists to facilitate operations that depend on the soft delete capability of certain entities." notable_decisions="none"]
|
|
1088
|
+
// CIL[DOC-CONFIDENCE pass="second" score="0.90" flags="none"]
|
|
1089
|
+
// CIL[DOC-STABILITY stability="stable"]
|
|
1090
|
+
/**
|
|
1091
|
+
* Determines if a given entity supports soft deletion by checking against a predefined list of entities. This function exists to facilitate operations that depend on the soft delete capability of certain entities.
|
|
1092
|
+
*
|
|
1093
|
+
* @inputSpec
|
|
1094
|
+
* entity: string (required) — the name of the entity to check for soft delete support.
|
|
1095
|
+
* @outputSpec boolean — returns true if the entity supports soft deletion, otherwise false.
|
|
1096
|
+
* @sideEffects none
|
|
1097
|
+
* @stability stable
|
|
1098
|
+
* @cil-generated
|
|
1099
|
+
*/
|
|
1100
|
+
// CIL[BEGIN stable_id="~/.framework/functions/admin-data.ts:entitysupportssoftdelete:function" type="function" identity="entitySupportsSoftDelete" parent="~/.framework/functions/admin-data.ts"]
|
|
1101
|
+
// CIL[DOC-MACRO purpose="entitySupportsSoftDelete function"]
|
|
1102
|
+
// CIL[DOC-RESPONSIBILITY responsibility="Implements the entitySupportsSoftDelete function."]
|
|
1103
|
+
// CIL[DOC-CONTEXT module=".framework/functions/admin-data.ts" layer="app-specific" related_files=""]
|
|
1104
|
+
// CIL[DOC-CONTRACT inputs="none" outputs="none" errors="none" side_effects="none"]
|
|
1105
|
+
// CIL[DOC-MICRO logic_summary="Implements the entitySupportsSoftDelete function." notable_decisions="[]"]
|
|
1106
|
+
// CIL[DOC-CONFIDENCE pass="first" score="0.8" flags="none"]
|
|
1107
|
+
// CIL[DOC-STABILITY stability="stable"]
|
|
723
1108
|
function entitySupportsSoftDelete(entity: string): boolean {
|
|
724
1109
|
const softDeleteEntities = ['accounts', 'people', 'items', 'threads', 'messages', 'watchers', 'item_progress', 'test_cases']
|
|
725
1110
|
return softDeleteEntities.includes(entity)
|
|
726
1111
|
}
|
|
727
|
-
// CIL[END
|
|
728
|
-
// CIL[
|
|
729
|
-
// CIL[DOC-
|
|
730
|
-
// CIL[DOC-
|
|
731
|
-
// CIL[DOC-
|
|
732
|
-
// CIL[DOC-CONTRACT inputs="none" outputs="{entity,count}" errors="entity_required,database_error" side_effects="database_count_query"]
|
|
733
|
-
// CIL[DOC-MICRO logic_summary="Performs count query with RLS filtering applied" notable_decisions="[]"]
|
|
734
|
-
// CIL[DOC-CONFIDENCE pass="second" score="0.95" flags="none"]
|
|
735
|
-
// CIL[DOC-STABILITY stability="stable"]
|
|
736
|
-
// CIL[DOC-VECTOR type="context" content="Layer: api-handler. Direct callers: 0. Direct calls: 0. Related files: none."]
|
|
737
|
-
// CIL[DOC-VECTOR type="blast_radius" content="Direct callers: 0. Total affected: 0."]
|
|
738
|
-
// CIL[DOC-VECTOR type="configuration" content="No configuration dependencies."]
|
|
739
|
-
// CIL[DOC-VECTOR type="constraint" content="No test paths identified."]
|
|
1112
|
+
// CIL[END stable_id="~/.framework/functions/admin-data.ts:entitysupportssoftdelete:function"]
|
|
1113
|
+
// CIL[DOC-VECTOR type="context" content="purpose='Determines if a given entity supports soft deletion by checking against a predefined list of entities.'; No verified external callers" status="ready"]
|
|
1114
|
+
// CIL[DOC-VECTOR type="blast_radius" content="No direct caller data from CIL graph; local impact only" status="ready"]
|
|
1115
|
+
// CIL[DOC-VECTOR type="configuration" content="No environment or build configuration dependencies identified" status="ready"]
|
|
1116
|
+
// CIL[DOC-VECTOR type="constraint" content="Standard runtime; no special invariants documented" status="ready"]
|
|
740
1117
|
// CIL[DOC-VECTOR type="implementation_pattern" content="" status="pending_human_input"]
|
|
741
1118
|
// CIL[DOC-VECTOR type="user_journey" content="" status="pending_human_input"]
|
|
1119
|
+
// CIL[DOC-MACRO purpose="The 'stats' constant provides an asynchronous handler for retrieving the count of records for a specified entity in the database."]
|
|
1120
|
+
// CIL[DOC-RESPONSIBILITY responsibility="The 'stats' constant provides an asynchronous handler for retrieving the count of records for a specified entity in the database. It ensures that the entity is valid and logs the request for administrative purposes."]
|
|
1121
|
+
// CIL[DOC-CONTEXT module="admin-data" layer="app-specific" related_files=".framework/functions/_shared/middleware,.framework/functions/_shared/permissions,.framework/functions/_shared/db,.framework/functions/_shared/principal,.framework/functions/_shared/resolve-ids,.framework/functions/_shared/trigger-engine,.framework/functions/_shared/logging,.framework/functions/_shared/access"]
|
|
1122
|
+
// CIL[DOC-CONTRACT inputs="none" outputs="none" errors="Error — Valid entity parameter is required, Error — database query error." side_effects="none dependencies="withAdminLogging, ctx.db.from"]
|
|
1123
|
+
// CIL[DOC-MICRO logic_summary="The 'stats' constant provides an asynchronous handler for retrieving the count of records for a specified entity in the database. It ensures that the entity is valid and logs the request for administrative purposes." notable_decisions="none"]
|
|
1124
|
+
// CIL[DOC-CONFIDENCE pass="second" score="0.90" flags="none"]
|
|
1125
|
+
// CIL[DOC-STABILITY stability="stable"]
|
|
1126
|
+
/**
|
|
1127
|
+
* The 'stats' constant provides an asynchronous handler for retrieving the count of records for a specified entity in the database. It ensures that the entity is valid and logs the request for administrative purposes.
|
|
1128
|
+
*
|
|
1129
|
+
* @throws Error — Valid entity parameter is required, Error — database query error.
|
|
1130
|
+
* @sideEffects none
|
|
1131
|
+
* @stability stable
|
|
1132
|
+
* @calls withAdminLogging, ctx.db.from
|
|
1133
|
+
* @cil-generated
|
|
1134
|
+
*/
|
|
1135
|
+
// CIL[BEGIN stable_id="~/.framework/functions/admin-data.ts:stats:constant" type="constant" identity="stats" parent="~/.framework/functions/admin-data.ts"]
|
|
1136
|
+
// CIL[DOC-MACRO purpose="stats constant"]
|
|
1137
|
+
// CIL[DOC-RESPONSIBILITY responsibility="Implements the stats constant."]
|
|
1138
|
+
// CIL[DOC-CONTEXT module=".framework/functions/admin-data.ts" layer="app-specific" related_files=""]
|
|
1139
|
+
// CIL[DOC-CONTRACT inputs="none" outputs="none" errors="none" side_effects="none"]
|
|
1140
|
+
// CIL[DOC-MICRO logic_summary="Implements the stats constant." notable_decisions="[]"]
|
|
1141
|
+
// CIL[DOC-CONFIDENCE pass="first" score="0.8" flags="none"]
|
|
1142
|
+
// CIL[DOC-STABILITY stability="stable"]
|
|
742
1143
|
export const stats = createHandler(async (ctx, _body) => {
|
|
743
1144
|
const { entity } = ctx.query || {}
|
|
744
1145
|
const method = ctx.query?.method || 'GET'
|
|
@@ -764,21 +1165,37 @@ export const stats = createHandler(async (ctx, _body) => {
|
|
|
764
1165
|
}
|
|
765
1166
|
)
|
|
766
1167
|
})
|
|
767
|
-
// CIL[END
|
|
768
|
-
// CIL[
|
|
769
|
-
// CIL[DOC-
|
|
770
|
-
// CIL[DOC-
|
|
771
|
-
// CIL[DOC-
|
|
772
|
-
// CIL[DOC-CONTRACT inputs="none" outputs="handler_response" errors="invalid_action_or_method" side_effects="delegates_to_crud_handlers"]
|
|
773
|
-
// CIL[DOC-MICRO logic_summary="Routes GET/POST/PATCH/DELETE to list/get/create/update/remove/stats" notable_decisions="[]"]
|
|
774
|
-
// CIL[DOC-CONFIDENCE pass="second" score="0.95" flags="none"]
|
|
775
|
-
// CIL[DOC-STABILITY stability="stable"]
|
|
776
|
-
// CIL[DOC-VECTOR type="context" content="Layer: api-handler. Direct callers: 0. Direct calls: 0. Related files: none."]
|
|
777
|
-
// CIL[DOC-VECTOR type="blast_radius" content="Direct callers: 0. Total affected: 0."]
|
|
778
|
-
// CIL[DOC-VECTOR type="configuration" content="No configuration dependencies."]
|
|
779
|
-
// CIL[DOC-VECTOR type="constraint" content="No test paths identified."]
|
|
1168
|
+
// CIL[END stable_id="~/.framework/functions/admin-data.ts:stats:constant"]
|
|
1169
|
+
// CIL[DOC-VECTOR type="context" content="purpose='The 'stats' constant provides an asynchronous handler for retrieving the count of records for a specified entity in the database.'; No verified external callers" status="ready"]
|
|
1170
|
+
// CIL[DOC-VECTOR type="blast_radius" content="No direct caller data from CIL graph; local impact only" status="ready"]
|
|
1171
|
+
// CIL[DOC-VECTOR type="configuration" content="No environment or build configuration dependencies identified" status="ready"]
|
|
1172
|
+
// CIL[DOC-VECTOR type="constraint" content="Standard runtime; no special invariants documented" status="ready"]
|
|
780
1173
|
// CIL[DOC-VECTOR type="implementation_pattern" content="" status="pending_human_input"]
|
|
781
1174
|
// CIL[DOC-VECTOR type="user_journey" content="" status="pending_human_input"]
|
|
1175
|
+
// CIL[DOC-MACRO purpose="The handler processes incoming requests based on the specified action and HTTP method, routing them to the appropriate function."]
|
|
1176
|
+
// CIL[DOC-RESPONSIBILITY responsibility="The handler processes incoming requests based on the specified action and HTTP method, routing them to the appropriate function. It serves as a centralized entry point for managing various administrative data operations."]
|
|
1177
|
+
// CIL[DOC-CONTEXT module="admin-data" layer="app-specific" related_files=".framework/functions/_shared/middleware,.framework/functions/_shared/permissions,.framework/functions/_shared/db,.framework/functions/_shared/principal,.framework/functions/_shared/resolve-ids,.framework/functions/_shared/trigger-engine,.framework/functions/_shared/logging,.framework/functions/_shared/access"]
|
|
1178
|
+
// CIL[DOC-CONTRACT inputs="none" outputs="none" errors="Error — Invalid action or method" side_effects="none dependencies="list, get, stats, create, update, remove"]
|
|
1179
|
+
// CIL[DOC-MICRO logic_summary="The handler processes incoming requests based on the specified action and HTTP method, routing them to the appropriate function. It serves as a centralized entry point for managing various administrative data operations." notable_decisions="none"]
|
|
1180
|
+
// CIL[DOC-CONFIDENCE pass="second" score="0.90" flags="none"]
|
|
1181
|
+
// CIL[DOC-STABILITY stability="stable"]
|
|
1182
|
+
/**
|
|
1183
|
+
* The handler processes incoming requests based on the specified action and HTTP method, routing them to the appropriate function. It serves as a centralized entry point for managing various administrative data operations.
|
|
1184
|
+
*
|
|
1185
|
+
* @throws Error — Invalid action or method
|
|
1186
|
+
* @sideEffects none
|
|
1187
|
+
* @stability stable
|
|
1188
|
+
* @calls list, get, stats, create, update, remove
|
|
1189
|
+
* @cil-generated
|
|
1190
|
+
*/
|
|
1191
|
+
// CIL[BEGIN stable_id="~/.framework/functions/admin-data.ts:handler:constant" type="constant" identity="handler" parent="~/.framework/functions/admin-data.ts"]
|
|
1192
|
+
// CIL[DOC-MACRO purpose="handler constant"]
|
|
1193
|
+
// CIL[DOC-RESPONSIBILITY responsibility="Implements the handler constant."]
|
|
1194
|
+
// CIL[DOC-CONTEXT module=".framework/functions/admin-data.ts" layer="app-specific" related_files=""]
|
|
1195
|
+
// CIL[DOC-CONTRACT inputs="none" outputs="none" errors="none" side_effects="none"]
|
|
1196
|
+
// CIL[DOC-MICRO logic_summary="Implements the handler constant." notable_decisions="[]"]
|
|
1197
|
+
// CIL[DOC-CONFIDENCE pass="first" score="0.8" flags="none"]
|
|
1198
|
+
// CIL[DOC-STABILITY stability="stable"]
|
|
782
1199
|
export const handler = createHandler(async (ctx, body) => {
|
|
783
1200
|
const { action } = ctx.query || {}
|
|
784
1201
|
const method = ctx.query?.method || 'GET'
|
|
@@ -818,4 +1235,10 @@ export const handler = createHandler(async (ctx, body) => {
|
|
|
818
1235
|
|
|
819
1236
|
throw new Error('Invalid action or method')
|
|
820
1237
|
})
|
|
821
|
-
// CIL[END
|
|
1238
|
+
// CIL[END stable_id="~/.framework/functions/admin-data.ts:handler:constant"]
|
|
1239
|
+
// CIL[DOC-VECTOR type="context" content="purpose='The handler processes incoming requests based on the specified action and HTTP method, routing them to the appropriate function.'; No verified external callers" status="ready"]
|
|
1240
|
+
// CIL[DOC-VECTOR type="blast_radius" content="No direct caller data from CIL graph; local impact only" status="ready"]
|
|
1241
|
+
// CIL[DOC-VECTOR type="configuration" content="No environment or build configuration dependencies identified" status="ready"]
|
|
1242
|
+
// CIL[DOC-VECTOR type="constraint" content="Standard runtime; no special invariants documented" status="ready"]
|
|
1243
|
+
// CIL[DOC-VECTOR type="implementation_pattern" content="" status="pending_human_input"]
|
|
1244
|
+
// CIL[DOC-VECTOR type="user_journey" content="" status="pending_human_input"]
|