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.
Files changed (451) hide show
  1. package/.env.example +76 -0
  2. package/.framework/.spine-manifest.json +19 -0
  3. package/.framework/cli/commands/agents.ts +61 -33
  4. package/.framework/cli/commands/auth.ts +60 -28
  5. package/.framework/cli/commands/create-app.ts +212 -80
  6. package/.framework/cli/commands/dev.ts +184 -68
  7. package/.framework/cli/commands/doctor.ts +324 -152
  8. package/.framework/cli/commands/generate.ts +119 -68
  9. package/.framework/cli/commands/init.ts +141 -242
  10. package/.framework/cli/commands/install-app.ts +1336 -314
  11. package/.framework/cli/commands/items.ts +31 -29
  12. package/.framework/cli/commands/migrate.ts +299 -156
  13. package/.framework/cli/commands/migrations.ts +62 -30
  14. package/.framework/cli/commands/pipelines.ts +31 -29
  15. package/.framework/cli/commands/status.ts +105 -45
  16. package/.framework/cli/commands/system.ts +47 -42
  17. package/.framework/cli/commands/test.ts +161 -102
  18. package/.framework/cli/commands/upgrade.ts +260 -0
  19. package/.framework/cli/commands/validate-app.ts +517 -161
  20. package/.framework/cli/context.ts +117 -85
  21. package/.framework/cli/env-loader.ts +74 -43
  22. package/.framework/cli/index.ts +70 -46
  23. package/.framework/cli/lib/project-files.ts +404 -0
  24. package/.framework/docs/guides/testing-guide.md +1 -1
  25. package/.framework/docs/runtime-types.md +72 -72
  26. package/.framework/functions/_shared/access.ts +84 -0
  27. package/.framework/functions/_shared/agent-runner.ts +5051 -1026
  28. package/.framework/functions/_shared/app-manifest.ts +214 -94
  29. package/.framework/functions/_shared/ast.ts +214 -0
  30. package/.framework/functions/_shared/audit.ts +91 -55
  31. package/.framework/functions/_shared/cil.ts +368 -127
  32. package/.framework/functions/_shared/db.ts +337 -68
  33. package/.framework/functions/_shared/funnel.ts +228 -0
  34. package/.framework/functions/_shared/geo.ts +105 -0
  35. package/.framework/functions/_shared/hash-api-key.ts +94 -17
  36. package/.framework/functions/_shared/index.ts +22 -224
  37. package/.framework/functions/_shared/kb.ts +832 -58
  38. package/.framework/functions/_shared/llm.ts +118 -18
  39. package/.framework/functions/_shared/logging.ts +317 -19
  40. package/.framework/functions/_shared/middleware.ts +701 -131
  41. package/.framework/functions/_shared/notify.ts +70 -0
  42. package/.framework/functions/_shared/outcomes.ts +34 -19
  43. package/.framework/functions/_shared/permissions.ts +501 -315
  44. package/.framework/functions/_shared/pipeline-runner.ts +704 -155
  45. package/.framework/functions/_shared/principal.ts +436 -263
  46. package/.framework/functions/_shared/rate-limit.ts +233 -0
  47. package/.framework/functions/_shared/resolve-credentials.ts +86 -19
  48. package/.framework/functions/_shared/resolve-ids.ts +203 -139
  49. package/.framework/functions/_shared/retry-deliveries.ts +51 -16
  50. package/.framework/functions/_shared/schema-utils.ts +602 -521
  51. package/.framework/functions/_shared/security.ts +345 -0
  52. package/.framework/functions/_shared/testing.ts +197 -172
  53. package/.framework/functions/_shared/tracing.ts +351 -21
  54. package/.framework/functions/_shared/trigger-engine.ts +425 -136
  55. package/.framework/functions/_shared/webhook-registration.ts +71 -70
  56. package/.framework/functions/_shared/webhook-registry.ts +126 -83
  57. package/.framework/functions/account-nodes.ts +30 -30
  58. package/.framework/functions/adapters/generic-webhook-inbound.ts +49 -16
  59. package/.framework/functions/adapters/generic-webhook-outbound.ts +17 -17
  60. package/.framework/functions/adapters/openai-outbound.ts +15 -16
  61. package/.framework/functions/admin-data.ts +596 -173
  62. package/.framework/functions/admin-funnel.ts +64 -60
  63. package/.framework/functions/admin-install-funnel.ts +84 -66
  64. package/.framework/functions/admin-signals.ts +69 -51
  65. package/.framework/functions/ai-agents.ts +431 -106
  66. package/.framework/functions/ai-interactions.ts +186 -112
  67. package/.framework/functions/api-keys.ts +107 -107
  68. package/.framework/functions/apps.ts +154 -136
  69. package/.framework/functions/auth.ts +83 -65
  70. package/.framework/functions/cil-agent-ingest.ts +189 -232
  71. package/.framework/functions/cil-agent.ts +433 -177
  72. package/.framework/functions/cil-callmap.ts +642 -430
  73. package/.framework/functions/cil-config.ts +139 -135
  74. package/.framework/functions/cil-context.ts +214 -127
  75. package/.framework/functions/cil-doc.ts +587 -458
  76. package/.framework/functions/cil-embeddings.ts +453 -364
  77. package/.framework/functions/cil-graph.ts +427 -142
  78. package/.framework/functions/cil-ingest.ts +1418 -1154
  79. package/.framework/functions/cil-pipeline.ts +276 -21
  80. package/.framework/functions/cil-project.ts +659 -132
  81. package/.framework/functions/cil-validate.ts +198 -164
  82. package/.framework/functions/debug-auth.ts +57 -55
  83. package/.framework/functions/deliveries.ts +80 -21
  84. package/.framework/functions/embeddings.ts +1023 -318
  85. package/.framework/functions/eval-harness.ts +146 -108
  86. package/.framework/functions/integration-outbound.ts +205 -75
  87. package/.framework/functions/integration-routes.ts +128 -23
  88. package/.framework/functions/integrations.ts +125 -100
  89. package/.framework/functions/invites.ts +1095 -460
  90. package/.framework/functions/item-progress.ts +158 -102
  91. package/.framework/functions/kb.ts +34 -10
  92. package/.framework/functions/logs.ts +133 -133
  93. package/.framework/functions/observability.ts +152 -122
  94. package/.framework/functions/pipeline-executions.ts +147 -132
  95. package/.framework/functions/pipelines.ts +134 -119
  96. package/.framework/functions/prompt-configs.ts +96 -80
  97. package/.framework/functions/roles.ts +112 -82
  98. package/.framework/functions/security.ts +450 -0
  99. package/.framework/functions/system-cron.ts +117 -80
  100. package/.framework/functions/system.ts +158 -98
  101. package/.framework/functions/tests.ts +29 -29
  102. package/.framework/functions/timers.ts +94 -95
  103. package/.framework/functions/trigger-scheduler.ts +10 -0
  104. package/.framework/functions/triggers.ts +179 -149
  105. package/.framework/functions/types.ts +137 -125
  106. package/.framework/mcp/index.ts +133 -0
  107. package/.framework/mcp/load-env.ts +60 -0
  108. package/.framework/mcp/shared/app-manifest.ts +275 -0
  109. package/.framework/mcp/shared/db.ts +477 -0
  110. package/.framework/mcp/shared/kb.ts +118 -0
  111. package/.framework/mcp/tools/architect.ts +431 -0
  112. package/.framework/mcp/tools/cil/context.ts +345 -0
  113. package/.framework/mcp/tools/cil/graph.ts +242 -0
  114. package/.framework/mcp/tools/cil/ingest.ts +1217 -0
  115. package/.framework/mcp/tools/cil/pipeline-orchestrator.ts +693 -0
  116. package/.framework/mcp/tools/cil/pipeline.ts +767 -0
  117. package/.framework/mcp/tools/cil/project.ts +791 -0
  118. package/.framework/mcp/tools/cil/retrieval.ts +336 -0
  119. package/.framework/mcp/tools/cil/search-core.ts +454 -0
  120. package/.framework/mcp/tools/cil/search.ts +97 -0
  121. package/.framework/mcp/tools/cil/suggest.ts +186 -0
  122. package/.framework/mcp/tools/cil/validate.ts +1369 -0
  123. package/.framework/mcp/tools/kb/delete.ts +139 -0
  124. package/.framework/mcp/tools/kb/index.ts +52 -0
  125. package/.framework/mcp/tools/kb/ingest.ts +84 -0
  126. package/.framework/mcp/tools/kb/list-types.ts +102 -0
  127. package/.framework/mcp/tools/kb/publish.ts +100 -0
  128. package/.framework/mcp/tools/kb/reindex.ts +86 -0
  129. package/.framework/mcp/tools/kb/revoke.ts +85 -0
  130. package/.framework/mcp/tools/kb/search.ts +101 -0
  131. package/.framework/mcp/tools/kb/upsert.ts +125 -0
  132. package/.framework/mcp/tools/observability.ts +510 -0
  133. package/.framework/migrations/001_core_schema.sql +15 -0
  134. package/.framework/migrations/002_core_rls_and_functions.sql +15 -0
  135. package/.framework/migrations/003_core_system_data.sql +16 -1
  136. package/.framework/migrations/004_core_rpc_and_broker.sql +17 -1
  137. package/.framework/migrations/005_core_observability.sql +17 -1
  138. package/.framework/migrations/006_security_hardening_rls.sql +15 -0
  139. package/.framework/migrations/007_kb_article_list.sql +17 -1
  140. package/.framework/migrations/008_items_target.sql +15 -0
  141. package/.framework/migrations/009_roles_slug_unique.sql +15 -0
  142. package/.framework/migrations/010_auth_user_trigger.sql +15 -0
  143. package/.framework/migrations/011_spine_system_account.sql +16 -0
  144. package/.framework/migrations/012_service_role_grants.sql +16 -0
  145. package/.framework/migrations/013_get_account_apps_role_filter.sql +15 -0
  146. package/.framework/migrations/014_apps_required_roles.sql +16 -0
  147. package/.framework/migrations/015_types_kind_slug_unique.sql +15 -0
  148. package/.framework/migrations/016_cil_types.sql +281 -0
  149. package/.framework/migrations/017_cil_stable_ids.sql +37 -0
  150. package/.framework/migrations/018_runtime_tables.sql +129 -0
  151. package/.framework/migrations/019_agent_prompt_columns.sql +56 -0
  152. package/.framework/migrations/020_schema_reconciliation.sql +67 -0
  153. package/.framework/migrations/021_kb_embedding_lifecycle.sql +31 -0
  154. package/.framework/migrations/032_cil_status_migration.sql +73 -0
  155. package/.framework/migrations/033_cil_versioning.sql +73 -0
  156. package/.framework/migrations/034_match_embeddings_knn.sql +115 -0
  157. package/.framework/migrations/035_rate_limits.sql +55 -0
  158. package/.framework/migrations/036_demo_record_flags.sql +72 -0
  159. package/.framework/migrations/037_kb_types_canonical.sql +244 -0
  160. package/.framework/migrations/038_drop_demo_record_flags.sql +38 -0
  161. package/.framework/migrations/042_registration_hierarchy.sql +309 -0
  162. package/.framework/migrations/043_policy_actor_cleanup.sql +39 -0
  163. package/.framework/migrations/044_match_embeddings_filtered_knn.sql +151 -0
  164. package/.framework/migrations/045_security_critical_rls.sql +139 -0
  165. package/.framework/migrations/046_security_missing_rls.sql +79 -0
  166. package/.framework/migrations/047_people_updated_by.sql +27 -0
  167. package/.framework/migrations/048_watcher_last_seen_at.sql +24 -0
  168. package/.framework/migrations/049_security_blocklist.sql +148 -0
  169. package/.framework/migrations/050_notifications.sql +49 -0
  170. package/.framework/migrations/051_message_agent_fields.sql +74 -0
  171. package/.framework/migrations/052_registration_security.sql +421 -0
  172. package/.framework/migrations/053_builtin_action_seeds.sql +66 -0
  173. package/.framework/migrations/054_kb_ingest_lease.sql +157 -0
  174. package/.framework/migrations/055_type_id_drift_reconciliation.sql +33 -0
  175. package/.framework/migrations/056_slug_column_reconciliation.sql +38 -0
  176. package/.framework/migrations/057_pipelines_slug_identity.sql +14 -0
  177. package/.framework/migrations/058_account_data_field_declarations.sql +53 -0
  178. package/.framework/migrations/059_registration_placement_fixes.sql +269 -0
  179. package/.framework/migrations/060_account_person_record_permissions.sql +38 -0
  180. package/.framework/migrations/061_fk_dedup.sql +32 -0
  181. package/.framework/public/spine-logo.svg +10 -3
  182. package/.framework/scripts/app-install-cli.ts +190 -93
  183. package/.framework/scripts/assemble-frontend.sh +127 -44
  184. package/.framework/scripts/assemble-functions.sh +128 -30
  185. package/.framework/scripts/boundary-check.sh +6 -2
  186. package/.framework/scripts/build-manifest.sh +24 -68
  187. package/.framework/scripts/check-core-integrity.sh +15 -76
  188. package/.framework/scripts/checksum-manifest.mts +343 -0
  189. package/.framework/scripts/cil-migrate-markers.ts +403 -0
  190. package/.framework/scripts/fix-cil-markers.mjs +176 -0
  191. package/.framework/scripts/verify-integrity.sh +21 -57
  192. package/.framework/scripts/verify-manifest.mts +305 -0
  193. package/.framework/seeds/types/funnel_signal_use.json +74 -21
  194. package/.framework/seeds/types/spine_instance.json +73 -21
  195. package/.framework/src/App.tsx +118 -72
  196. package/.framework/src/apps/admin/index.tsx +855 -58
  197. package/.framework/src/components/AppWrapper.tsx +43 -45
  198. package/.framework/src/components/CustomAppLoader.tsx +160 -116
  199. package/.framework/src/components/admin/AdminListPage.tsx +46 -44
  200. package/.framework/src/components/admin/AdminSidebar.tsx +57 -47
  201. package/.framework/src/components/admin/AdminStatsCard.tsx +46 -44
  202. package/.framework/src/components/admin/PageInstructions.tsx +98 -2
  203. package/.framework/src/components/admin/SortableTableHeader.tsx +44 -45
  204. package/.framework/src/components/app-shell/GenericAppShell.tsx +64 -65
  205. package/.framework/src/components/app-shell/GenericDetailPage.tsx +44 -47
  206. package/.framework/src/components/app-shell/GenericListPage.tsx +45 -49
  207. package/.framework/src/components/app-sidebar.tsx +42 -45
  208. package/.framework/src/components/auth/ProtectedRoute.tsx +48 -41
  209. package/.framework/src/components/auth/TurnstileWidget.tsx +27 -0
  210. package/.framework/src/components/kb/KBArticleEditor.tsx +231 -22
  211. package/.framework/src/components/kb/KBArticleList.tsx +251 -10
  212. package/.framework/src/components/layout/AppShell.tsx +51 -45
  213. package/.framework/src/components/layout/Header.tsx +42 -43
  214. package/.framework/src/components/layout/Layout.tsx +46 -46
  215. package/.framework/src/components/layout/Sidebar.tsx +196 -96
  216. package/.framework/src/components/runtime/DataDetailHeader.tsx +55 -30
  217. package/.framework/src/components/runtime/DataDetailPage.tsx +31 -269
  218. package/.framework/src/components/runtime/DataFilters.tsx +49 -74
  219. package/.framework/src/components/runtime/DataHeader.tsx +53 -32
  220. package/.framework/src/components/runtime/DataListPage.tsx +51 -155
  221. package/.framework/src/components/runtime/DataStats.tsx +66 -44
  222. package/.framework/src/components/runtime/DataTable.tsx +49 -149
  223. package/.framework/src/components/runtime/SchemaDetailForm.tsx +45 -75
  224. package/.framework/src/components/runtime/index.ts +119 -16
  225. package/.framework/src/components/search-form.tsx +46 -29
  226. package/.framework/src/components/shared/AgentView.tsx +65 -48
  227. package/.framework/src/components/shared/FieldRenderer.tsx +144 -50
  228. package/.framework/src/components/shared/InviteManager.tsx +207 -97
  229. package/.framework/src/components/shared/MemberList.tsx +97 -0
  230. package/.framework/src/components/shared/SchemaFields.tsx +107 -86
  231. package/.framework/src/components/ui/DataTable.tsx +80 -68
  232. package/.framework/src/components/ui/Form.tsx +157 -146
  233. package/.framework/src/components/ui/ItemCard.tsx +74 -67
  234. package/.framework/src/components/ui/ItemListView.tsx +73 -68
  235. package/.framework/src/components/ui/LoadingSpinner.tsx +43 -48
  236. package/.framework/src/components/ui/Modal.tsx +78 -68
  237. package/.framework/src/components/ui/RichTextEditor.tsx +89 -69
  238. package/.framework/src/components/ui/accordion.tsx +85 -86
  239. package/.framework/src/components/ui/alert-dialog.tsx +197 -184
  240. package/.framework/src/components/ui/alert.tsx +105 -94
  241. package/.framework/src/components/ui/aspect-ratio.tsx +57 -43
  242. package/.framework/src/components/ui/avatar.tsx +122 -107
  243. package/.framework/src/components/ui/badge.tsx +60 -55
  244. package/.framework/src/components/ui/breadcrumb.tsx +127 -128
  245. package/.framework/src/components/ui/button-group.tsx +86 -72
  246. package/.framework/src/components/ui/button.tsx +71 -50
  247. package/.framework/src/components/ui/calendar.tsx +72 -57
  248. package/.framework/src/components/ui/card.tsx +136 -129
  249. package/.framework/src/components/ui/carousel.tsx +226 -107
  250. package/.framework/src/components/ui/chart.tsx +252 -147
  251. package/.framework/src/components/ui/checkbox.tsx +43 -44
  252. package/.framework/src/components/ui/collapsible.tsx +86 -71
  253. package/.framework/src/components/ui/combobox.tsx +282 -249
  254. package/.framework/src/components/ui/command.tsx +158 -146
  255. package/.framework/src/components/ui/context-menu.tsx +239 -240
  256. package/.framework/src/components/ui/dialog.tsx +174 -157
  257. package/.framework/src/components/ui/direction.tsx +72 -56
  258. package/.framework/src/components/ui/drawer.tsx +168 -169
  259. package/.framework/src/components/ui/dropdown-menu.tsx +254 -223
  260. package/.framework/src/components/ui/empty.tsx +131 -120
  261. package/.framework/src/components/ui/field.tsx +205 -173
  262. package/.framework/src/components/ui/hover-card.tsx +71 -72
  263. package/.framework/src/components/ui/input-group.tsx +148 -133
  264. package/.framework/src/components/ui/input-otp.tsx +99 -86
  265. package/.framework/src/components/ui/input.tsx +43 -41
  266. package/.framework/src/components/ui/item.tsx +207 -185
  267. package/.framework/src/components/ui/kbd.tsx +57 -56
  268. package/.framework/src/components/ui/label.tsx +45 -41
  269. package/.framework/src/components/ui/menubar.tsx +268 -236
  270. package/.framework/src/components/ui/native-select.tsx +85 -86
  271. package/.framework/src/components/ui/navigation-menu.tsx +166 -156
  272. package/.framework/src/components/ui/pagination.tsx +131 -141
  273. package/.framework/src/components/ui/popover.tsx +125 -128
  274. package/.framework/src/components/ui/progress.tsx +47 -44
  275. package/.framework/src/components/ui/radio-group.tsx +60 -55
  276. package/.framework/src/components/ui/resizable.tsx +85 -72
  277. package/.framework/src/components/ui/scroll-area.tsx +57 -58
  278. package/.framework/src/components/ui/select.tsx +182 -169
  279. package/.framework/src/components/ui/separator.tsx +42 -43
  280. package/.framework/src/components/ui/sheet.tsx +170 -159
  281. package/.framework/src/components/ui/sidebar.tsx +395 -398
  282. package/.framework/src/components/ui/skeleton.tsx +42 -43
  283. package/.framework/src/components/ui/slider.tsx +61 -44
  284. package/.framework/src/components/ui/sonner.tsx +44 -44
  285. package/.framework/src/components/ui/spinner.tsx +47 -42
  286. package/.framework/src/components/ui/switch.tsx +56 -42
  287. package/.framework/src/components/ui/table-primitives.tsx +272 -132
  288. package/.framework/src/components/ui/table.tsx +140 -142
  289. package/.framework/src/components/ui/tabs.tsx +110 -93
  290. package/.framework/src/components/ui/textarea.tsx +43 -44
  291. package/.framework/src/components/ui/toggle-group.tsx +87 -71
  292. package/.framework/src/components/ui/toggle.tsx +56 -56
  293. package/.framework/src/components/ui/tooltip.tsx +99 -85
  294. package/.framework/src/contexts/AppContext.tsx +166 -114
  295. package/.framework/src/contexts/AuthContext.tsx +232 -137
  296. package/.framework/src/hooks/use-mobile.ts +43 -44
  297. package/.framework/src/hooks/useApi.ts +185 -172
  298. package/.framework/src/hooks/useAppPath.ts +31 -29
  299. package/.framework/src/hooks/useApps.ts +77 -42
  300. package/.framework/src/hooks/useEntityList.ts +66 -29
  301. package/.framework/src/hooks/useEntityRecord.ts +76 -32
  302. package/.framework/src/hooks/useForm.ts +62 -30
  303. package/.framework/src/hooks/useListSchema.ts +60 -43
  304. package/.framework/src/hooks/useSchemaRecord.ts +115 -95
  305. package/.framework/src/lib/api.ts +258 -134
  306. package/.framework/src/lib/registration.ts +181 -0
  307. package/.framework/src/lib/supabase.ts +118 -81
  308. package/.framework/src/lib/utils.ts +266 -266
  309. package/.framework/src/main.tsx +43 -44
  310. package/.framework/src/pages/DashboardPage.tsx +44 -43
  311. package/.framework/src/pages/NoAppPage.tsx +50 -0
  312. package/.framework/src/pages/NotFoundPage.tsx +32 -29
  313. package/.framework/src/pages/SetupPage.tsx +34 -33
  314. package/.framework/src/pages/admin/AIAgentDetailPage.tsx +69 -58
  315. package/.framework/src/pages/admin/AIAgentsPage.tsx +43 -40
  316. package/.framework/src/pages/admin/APIKeyDetailPage.tsx +63 -55
  317. package/.framework/src/pages/admin/APIKeysPage.tsx +44 -42
  318. package/.framework/src/pages/admin/AlertsConfigPage.tsx +117 -94
  319. package/.framework/src/pages/admin/AppDetailPage.tsx +48 -42
  320. package/.framework/src/pages/admin/AppsPage.tsx +45 -42
  321. package/.framework/src/pages/admin/DeliveriesPage.tsx +49 -17
  322. package/.framework/src/pages/admin/DesignedPage.tsx +31 -30
  323. package/.framework/src/pages/admin/EmbeddingDetailPage.tsx +58 -0
  324. package/.framework/src/pages/admin/EmbeddingsPage.tsx +49 -0
  325. package/.framework/src/pages/admin/ExtendedShadcnTestPage.tsx +31 -29
  326. package/.framework/src/pages/admin/IncrementalShadcnTestPage.tsx +46 -29
  327. package/.framework/src/pages/admin/IntegratedDashboard.tsx +32 -29
  328. package/.framework/src/pages/admin/IntegrationDetailPage.tsx +68 -55
  329. package/.framework/src/pages/admin/IntegrationsPage.tsx +45 -42
  330. package/.framework/src/pages/admin/InvitesPage.tsx +60 -44
  331. package/.framework/src/pages/admin/LogsPage.tsx +87 -137
  332. package/.framework/src/pages/admin/MinimalShadcnTestPage.tsx +31 -29
  333. package/.framework/src/pages/admin/ObservabilityDashboard.tsx +150 -89
  334. package/.framework/src/pages/admin/PipelineDetailPage.tsx +77 -104
  335. package/.framework/src/pages/admin/PipelineExecutionsPage.tsx +44 -43
  336. package/.framework/src/pages/admin/PipelinesPage.tsx +59 -145
  337. package/.framework/src/pages/admin/PromptConfigDetailPage.tsx +53 -42
  338. package/.framework/src/pages/admin/PromptConfigsPage.tsx +47 -117
  339. package/.framework/src/pages/admin/ProperlyDesignedPage.tsx +31 -44
  340. package/.framework/src/pages/admin/RoleDetailPage.tsx +49 -92
  341. package/.framework/src/pages/admin/RolesPage.tsx +47 -164
  342. package/.framework/src/pages/admin/SecurityPage.tsx +310 -0
  343. package/.framework/src/pages/admin/SelectTestPage.tsx +30 -32
  344. package/.framework/src/pages/admin/ShadcnTestPage.tsx +37 -44
  345. package/.framework/src/pages/admin/SimpleDashboard.tsx +32 -44
  346. package/.framework/src/pages/admin/TestRunDetailPage.tsx +97 -44
  347. package/.framework/src/pages/admin/TestingDashboard.tsx +126 -71
  348. package/.framework/src/pages/admin/TimerDetailPage.tsx +67 -55
  349. package/.framework/src/pages/admin/TimersPage.tsx +44 -42
  350. package/.framework/src/pages/admin/TriggerDetailPage.tsx +47 -42
  351. package/.framework/src/pages/admin/TriggersPage.tsx +58 -57
  352. package/.framework/src/pages/admin/TypeDetailPage.tsx +91 -55
  353. package/.framework/src/pages/admin/TypesPage.tsx +45 -42
  354. package/.framework/src/pages/admin/cil/CILAgentPage.tsx +258 -128
  355. package/.framework/src/pages/admin/cil/CILChunkDetailPage.tsx +127 -123
  356. package/.framework/src/pages/admin/cil/CILDashboardPage.tsx +308 -235
  357. package/.framework/src/pages/admin/cil/CILFileListPage.tsx +159 -110
  358. package/.framework/src/pages/admin/cil/CILFileSelectPage.tsx +432 -0
  359. package/.framework/src/pages/admin/cil/CILGraphPage.tsx +200 -178
  360. package/.framework/src/pages/admin/cil/CILIngestionPage.tsx +286 -239
  361. package/.framework/src/pages/admin/cil/CILProjectsPage.tsx +211 -90
  362. package/.framework/src/pages/admin/cil/CILSearchPage.tsx +156 -143
  363. package/.framework/src/pages/admin/cil/CILSuggestionsPage.tsx +379 -0
  364. package/.framework/src/pages/admin/cil/CILVersionsPage.tsx +337 -0
  365. package/.framework/src/pages/admin/cil/FlexiblePipelinePage.tsx +219 -214
  366. package/.framework/src/pages/admin/kb/KBAdminPage.tsx +64 -0
  367. package/.framework/src/pages/auth/AuthConfirmPage.tsx +135 -65
  368. package/.framework/src/pages/auth/ForgotPasswordPage.tsx +39 -31
  369. package/.framework/src/pages/auth/LoginPage.tsx +38 -32
  370. package/.framework/src/pages/auth/PendingApprovalPage.tsx +31 -28
  371. package/.framework/src/pages/auth/RegisterPage.tsx +429 -155
  372. package/.framework/src/pages/spine-framework/APIPage.tsx +33 -30
  373. package/.framework/src/pages/spine-framework/CLIPage.tsx +32 -30
  374. package/.framework/src/types/auth.ts +101 -93
  375. package/.framework/src/types/types.ts +283 -262
  376. package/.framework/templates/project.json +87 -0
  377. package/.framework/templates/spine.config.neutral.json +7 -0
  378. package/.framework/tests/api/api-surface.test.ts +381 -0
  379. package/.framework/tests/fixtures/seed.ts +427 -0
  380. package/.framework/tests/fixtures/teardown.ts +228 -0
  381. package/.framework/tests/reporter.ts +351 -0
  382. package/.framework/tests/setup.ts +135 -0
  383. package/.framework/tests/ui/ui-sweep.ts +278 -0
  384. package/.framework/tests/unit/admin-data-logger.test.ts +310 -0
  385. package/.framework/tests/unit/agent-runner.test.ts +2389 -0
  386. package/.framework/tests/unit/ai-interactions.test.ts +81 -0
  387. package/.framework/tests/unit/app-manifest.test.ts +359 -0
  388. package/.framework/tests/unit/assembly-scripts.test.ts +172 -0
  389. package/.framework/tests/unit/cil-determinism.test.ts +85 -0
  390. package/.framework/tests/unit/core-isolation.test.ts +153 -0
  391. package/.framework/tests/unit/funnel-signals.test.ts +135 -0
  392. package/.framework/tests/unit/install-app.test.ts +1759 -0
  393. package/.framework/tests/unit/invites-security.test.ts +572 -0
  394. package/.framework/tests/unit/kb-ingest-lease.test.ts +287 -0
  395. package/.framework/tests/unit/kb-search.test.ts +119 -0
  396. package/.framework/tests/unit/migrate.test.ts +509 -0
  397. package/.framework/tests/unit/notify.test.ts +136 -0
  398. package/.framework/tests/unit/permissions.test.ts +269 -0
  399. package/.framework/tests/unit/pipeline-runner.test.ts +755 -0
  400. package/.framework/tests/unit/principal-cache.test.ts +138 -0
  401. package/.framework/tests/unit/retrieval-golden.test.ts +520 -0
  402. package/.framework/tests/unit/runtime-isolation.test.ts +642 -0
  403. package/.framework/tests/unit/schema-utils.test.ts +225 -0
  404. package/.framework/tests/unit/trigger-engine.test.ts +513 -0
  405. package/.framework/tests/unit/validate-app.test.ts +527 -0
  406. package/README.md +34 -3
  407. package/bin/spine-framework.cjs +1 -0
  408. package/config/tailwind.config.cjs +7 -0
  409. package/config/tsconfig.functions.json +42 -0
  410. package/config/tsconfig.json +37 -9
  411. package/config/vite.config.ts +31 -2
  412. package/netlify.toml +31 -3
  413. package/package.json +46 -29
  414. package/scripts/assemble-frontend.sh +127 -44
  415. package/scripts/assemble-functions.sh +127 -29
  416. package/scripts/boundary-check.sh +6 -2
  417. package/scripts/build-manifest.sh +24 -68
  418. package/scripts/checksum-manifest.mts +345 -0
  419. package/scripts/dev-clean.sh +86 -0
  420. package/scripts/dev-netlify.sh +49 -0
  421. package/scripts/netlify-dev-wrapper.sh +2 -0
  422. package/scripts/verify-install.ts +358 -0
  423. package/scripts/verify-integrity.sh +21 -57
  424. package/scripts/verify-manifest.mts +305 -0
  425. package/templates/project/gitignore +45 -0
  426. package/{config → templates/project}/package-lock.json +22335 -9366
  427. package/vitest.config.ts +46 -0
  428. package/.framework/public/spine.config.json +0 -91
  429. package/config/deno.lock +0 -108
  430. package/config/tsconfig.node.tsbuildinfo +0 -1
  431. package/config/tsconfig.tsbuildinfo +0 -1
  432. package/config/vite.config.d.ts +0 -2
  433. package/custom/.devin/AGENT.md +0 -357
  434. package/custom/.devin/skills/install-app/SKILL.md +0 -39
  435. package/custom/.devin/skills/spine-workbench-discovery/SKILL.md +0 -39
  436. package/custom/.devin/skills/spine-workbench-idea/SKILL.md +0 -36
  437. package/custom/.devin/skills/spine-workbench-implement/SKILL.md +0 -46
  438. package/custom/.devin/skills/spine-workbench-initiative/SKILL.md +0 -28
  439. package/custom/.devin/skills/spine-workbench-plan/SKILL.md +0 -38
  440. package/custom/.devin/workflows/app-install.yaml +0 -83
  441. package/custom/README.md +0 -79
  442. package/docs/README.md +0 -15
  443. package/scripts/app-install-cli.ts +0 -286
  444. package/scripts/check-core-integrity.sh +0 -82
  445. package/scripts/ingest-chunks.cjs +0 -202
  446. package/scripts/kb-chunk-parser.cjs +0 -312
  447. package/scripts/kb-chunk-parser.ts +0 -330
  448. package/scripts/kb-ingest-docs.ts +0 -203
  449. package/scripts/load-test-app-install.ts +0 -484
  450. package/scripts/test-login.js +0 -33
  451. package/spine.config.json +0 -91
@@ -0,0 +1,269 @@
1
+ // CIL[BEGIN stable_id="~/.framework/tests/unit/permissions.test.ts:module_header:module_header" type="module_header" identity="module_header" parent="none"]
2
+ // CIL[DOC-MACRO purpose="Test setup and imports for permission tests"]
3
+ // CIL[DOC-RESPONSIBILITY responsibility="Configure test environment and mock dependencies"]
4
+ // CIL[DOC-CONTEXT module="tests/unit/permissions" layer="test-unit" related_files=".framework/functions/_shared/principal.ts"]
5
+ // CIL[DOC-CONTRACT inputs="none" outputs="configured test mocks" errors="none" side_effects="Mocks database and middleware modules"]
6
+ // CIL[DOC-MICRO logic_summary="Imports vitest, mocks db and middleware, imports Principal type" notable_decisions="[]"]
7
+ // CIL[DOC-CONFIDENCE pass="second" score="0.90" flags="none"]
8
+ // CIL[DOC-STABILITY stability="stable"]
9
+ // CIL[DOC-AUDIENCE audience="test-engineers"]
10
+ import { describe, it, expect, vi, beforeEach } from 'vitest'
11
+
12
+ vi.mock('../../functions/_shared/db.ts', () => ({
13
+ adminDb: {
14
+ from: vi.fn().mockReturnThis(),
15
+ select: vi.fn().mockReturnThis(),
16
+ eq: vi.fn().mockReturnThis(),
17
+ single: vi.fn()
18
+ }
19
+ }))
20
+
21
+ vi.mock('../../functions/_shared/middleware.ts', async (importOriginal) => {
22
+ const actual = await importOriginal<typeof import('../../functions/_shared/middleware.ts')>()
23
+ return { ...actual }
24
+ })
25
+
26
+ import type { Principal } from '../../functions/_shared/principal.ts'
27
+ // CIL[DOC-VECTOR type="context" content="purpose='Test setup and imports for permission tests'; No verified external callers; imports: .framework/functions/_shared/principal.ts"]
28
+ // CIL[DOC-VECTOR type="blast_radius" content="No direct caller data from CIL graph; local impact only"]
29
+ // CIL[DOC-VECTOR type="configuration" content="No environment or build configuration dependencies identified"]
30
+ // CIL[DOC-VECTOR type="constraint" content="Standard runtime; no special invariants documented"]
31
+ // CIL[DOC-VECTOR type="implementation_pattern" content="" status="pending_human_input"]
32
+ // CIL[DOC-VECTOR type="user_journey" content="" status="pending_human_input"]
33
+ // CIL[END stable_id="~/.framework/tests/unit/permissions.test.ts:module_header:module_header"]
34
+
35
+ // CIL[BEGIN stable_id="~/.framework/tests/unit/permissions.test.ts:makePrincipal:function" type="function" identity="makePrincipal" parent="none"]
36
+ // CIL[DOC-MACRO purpose="Create test principal with default values"]
37
+ // CIL[DOC-RESPONSIBILITY responsibility="Generate test principal objects"]
38
+ // CIL[DOC-CONTEXT module="tests/unit/permissions" layer="test-unit" related_files=".framework/functions/_shared/principal.ts,.framework/tests/unit/permissions.test.ts"]
39
+ // CIL[DOC-CONTRACT inputs="overrides: Partial<Principal>" outputs="Principal object" errors="none" side_effects="none"]
40
+ // CIL[DOC-MICRO logic_summary="Returns default human principal with overrides applied" notable_decisions="[]"]
41
+ // CIL[DOC-CONFIDENCE pass="second" score="0.90" flags="none"]
42
+ // CIL[DOC-STABILITY stability="stable"]
43
+ function makePrincipal(overrides: Partial<Principal> = {}): Principal {
44
+ return {
45
+ id: 'user-123',
46
+ type: 'human',
47
+ accountId: 'account-123',
48
+ roles: ['member'],
49
+ provenance: {
50
+ sourceType: 'jwt',
51
+ createdBy: 'user-123',
52
+ invokedAt: new Date().toISOString()
53
+ },
54
+ ...overrides
55
+ }
56
+ }
57
+ // CIL[DOC-VECTOR type="context" content="purpose='Create test principal with default values'; No verified external callers; imports: .framework/functions/_shared/principal.ts"]
58
+ // CIL[DOC-VECTOR type="blast_radius" content="No direct caller data from CIL graph; local impact only"]
59
+ // CIL[DOC-VECTOR type="configuration" content="No environment or build configuration dependencies identified"]
60
+ // CIL[DOC-VECTOR type="constraint" content="Standard runtime; no special invariants documented"]
61
+ // CIL[DOC-VECTOR type="implementation_pattern" content="" status="pending_human_input"]
62
+ // CIL[DOC-VECTOR type="user_journey" content="" status="pending_human_input"]
63
+ // CIL[END stable_id="~/.framework/tests/unit/permissions.test.ts:makePrincipal:function"]
64
+
65
+ // CIL[BEGIN stable_id="~/.framework/tests/unit/permissions.test.ts:makeCtx:function" type="function" identity="makeCtx" parent="none"]
66
+ // CIL[DOC-MACRO purpose="Create test context from principal"]
67
+ // CIL[DOC-RESPONSIBILITY responsibility="Generate test context objects"]
68
+ // CIL[DOC-CONTEXT module="tests/unit/permissions" layer="test-unit" related_files=".framework/functions/_shared/principal.ts,.framework/tests/unit/permissions.test.ts"]
69
+ // CIL[DOC-CONTRACT inputs="principal: Principal" outputs="CoreContext object" errors="none" side_effects="none"]
70
+ // CIL[DOC-MICRO logic_summary="Creates context with principal, accountId, empty db, and requestId" notable_decisions="[]"]
71
+ // CIL[DOC-CONFIDENCE pass="second" score="0.90" flags="none"]
72
+ // CIL[DOC-STABILITY stability="stable"]
73
+ function makeCtx(principal: Principal) {
74
+ return {
75
+ principal,
76
+ accountId: principal.accountId,
77
+ db: {},
78
+ requestId: 'test-req-id'
79
+ }
80
+ }
81
+ // CIL[DOC-VECTOR type="context" content="purpose='Create test context from principal'; No verified external callers; imports: .framework/functions/_shared/principal.ts"]
82
+ // CIL[DOC-VECTOR type="blast_radius" content="No direct caller data from CIL graph; local impact only"]
83
+ // CIL[DOC-VECTOR type="configuration" content="No environment or build configuration dependencies identified"]
84
+ // CIL[DOC-VECTOR type="constraint" content="Standard runtime; no special invariants documented"]
85
+ // CIL[DOC-VECTOR type="implementation_pattern" content="" status="pending_human_input"]
86
+ // CIL[DOC-VECTOR type="user_journey" content="" status="pending_human_input"]
87
+ // CIL[END stable_id="~/.framework/tests/unit/permissions.test.ts:makeCtx:function"]
88
+
89
+ // CIL[BEGIN stable_id="~/.framework/tests/unit/permissions.test.ts:describe_isSystemAdmin:block" type="block" identity="describe_isSystemAdmin" parent="none"]
90
+ // CIL[DOC-MACRO purpose="Test isSystemAdmin permission function"]
91
+ // CIL[DOC-RESPONSIBILITY responsibility="Verify system admin role detection"]
92
+ // CIL[DOC-CONTEXT module="tests/unit/permissions" layer="test-unit" related_files=".framework/functions/_shared/principal.ts,.framework/tests/unit/permissions.test.ts"]
93
+ // CIL[DOC-CONTRACT inputs="none" outputs="test assertions" errors="none" side_effects="Tests principal.ts module"]
94
+ // CIL[DOC-MICRO logic_summary="Tests system_admin role detection for humans and machines" notable_decisions="[]"]
95
+ // CIL[DOC-CONFIDENCE pass="second" score="0.90" flags="none"]
96
+ // CIL[DOC-STABILITY stability="stable"]
97
+ describe('isSystemAdmin', () => {
98
+ it('returns true for system_admin role', async () => {
99
+ const { isSystemAdmin } = await import('../../functions/_shared/principal.ts')
100
+ const principal = makePrincipal({ roles: ['admin', 'system_admin'] })
101
+ expect(isSystemAdmin(principal)).toBe(true)
102
+ })
103
+
104
+ it('returns false for non-admin roles', async () => {
105
+ const { isSystemAdmin } = await import('../../functions/_shared/principal.ts')
106
+ const principal = makePrincipal({ roles: ['admin', 'member'] })
107
+ expect(isSystemAdmin(principal)).toBe(false)
108
+ })
109
+
110
+ it('returns false for machine principals', async () => {
111
+ const { isSystemAdmin } = await import('../../functions/_shared/principal.ts')
112
+ const principal = makePrincipal({
113
+ type: 'machine',
114
+ roles: undefined,
115
+ scopes: ['*:*']
116
+ })
117
+ expect(isSystemAdmin(principal)).toBe(false)
118
+ })
119
+ })
120
+ // CIL[DOC-VECTOR type="context" content="purpose='Test isSystemAdmin permission function'; No verified external callers; imports: .framework/functions/_shared/principal.ts"]
121
+ // CIL[DOC-VECTOR type="blast_radius" content="No direct caller data from CIL graph; local impact only"]
122
+ // CIL[DOC-VECTOR type="configuration" content="No environment or build configuration dependencies identified"]
123
+ // CIL[DOC-VECTOR type="constraint" content="Standard runtime; no special invariants documented"]
124
+ // CIL[DOC-VECTOR type="implementation_pattern" content="" status="pending_human_input"]
125
+ // CIL[DOC-VECTOR type="user_journey" content="" status="pending_human_input"]
126
+ // CIL[END stable_id="~/.framework/tests/unit/permissions.test.ts:describe_isSystemAdmin:block"]
127
+
128
+ // CIL[BEGIN stable_id="~/.framework/tests/unit/permissions.test.ts:describe_machineHasScope:block" type="block" identity="describe_machineHasScope" parent="none"]
129
+ // CIL[DOC-MACRO purpose="Test machineHasScope permission function"]
130
+ // CIL[DOC-RESPONSIBILITY responsibility="Verify machine principal scope matching"]
131
+ // CIL[DOC-CONTEXT module="tests/unit/permissions" layer="test-unit" related_files=".framework/functions/_shared/principal.ts,.framework/tests/unit/permissions.test.ts"]
132
+ // CIL[DOC-CONTRACT inputs="none" outputs="test assertions" errors="none" side_effects="Tests principal.ts module"]
133
+ // CIL[DOC-MICRO logic_summary="Tests exact, wildcard, and global scope matching for machines" notable_decisions="[]"]
134
+ // CIL[DOC-CONFIDENCE pass="second" score="0.90" flags="none"]
135
+ // CIL[DOC-STABILITY stability="stable"]
136
+ describe('machineHasScope', () => {
137
+ it('matches exact scope', async () => {
138
+ const { machineHasScope } = await import('../../functions/_shared/principal.ts')
139
+ const principal = makePrincipal({ type: 'machine', scopes: ['items:read', 'people:write'] })
140
+ expect(machineHasScope(principal, 'items:read')).toBe(true)
141
+ expect(machineHasScope(principal, 'items:write')).toBe(false)
142
+ })
143
+
144
+ it('matches wildcard resource scope', async () => {
145
+ const { machineHasScope } = await import('../../functions/_shared/principal.ts')
146
+ const principal = makePrincipal({ type: 'machine', scopes: ['items:*'] })
147
+ expect(machineHasScope(principal, 'items:read')).toBe(true)
148
+ expect(machineHasScope(principal, 'items:write')).toBe(true)
149
+ expect(machineHasScope(principal, 'people:read')).toBe(false)
150
+ })
151
+
152
+ it('matches global wildcard *:*', async () => {
153
+ const { machineHasScope } = await import('../../functions/_shared/principal.ts')
154
+ const principal = makePrincipal({ type: 'machine', scopes: ['*:*'] })
155
+ expect(machineHasScope(principal, 'items:read')).toBe(true)
156
+ expect(machineHasScope(principal, 'anything:anything')).toBe(true)
157
+ })
158
+
159
+ it('returns false for human principals', async () => {
160
+ const { machineHasScope } = await import('../../functions/_shared/principal.ts')
161
+ const principal = makePrincipal({ type: 'human', scopes: ['items:read'] })
162
+ expect(machineHasScope(principal, 'items:read')).toBe(false)
163
+ })
164
+
165
+ it('returns false when no scopes assigned', async () => {
166
+ const { machineHasScope } = await import('../../functions/_shared/principal.ts')
167
+ const principal = makePrincipal({ type: 'machine', scopes: [] })
168
+ expect(machineHasScope(principal, 'items:read')).toBe(false)
169
+ })
170
+ })
171
+ // CIL[DOC-VECTOR type="context" content="purpose='Test machineHasScope permission function'; No verified external callers; imports: .framework/functions/_shared/principal.ts"]
172
+ // CIL[DOC-VECTOR type="blast_radius" content="No direct caller data from CIL graph; local impact only"]
173
+ // CIL[DOC-VECTOR type="configuration" content="No environment or build configuration dependencies identified"]
174
+ // CIL[DOC-VECTOR type="constraint" content="Standard runtime; no special invariants documented"]
175
+ // CIL[DOC-VECTOR type="implementation_pattern" content="" status="pending_human_input"]
176
+ // CIL[DOC-VECTOR type="user_journey" content="" status="pending_human_input"]
177
+ // CIL[END stable_id="~/.framework/tests/unit/permissions.test.ts:describe_machineHasScope:block"]
178
+
179
+ // CIL[BEGIN stable_id="~/.framework/tests/unit/permissions.test.ts:describe_humanHasRole:block" type="block" identity="describe_humanHasRole" parent="none"]
180
+ // CIL[DOC-MACRO purpose="Test humanHasRole permission function"]
181
+ // CIL[DOC-RESPONSIBILITY responsibility="Verify human principal role checking"]
182
+ // CIL[DOC-CONTEXT module="tests/unit/permissions" layer="test-unit" related_files=".framework/functions/_shared/principal.ts,.framework/tests/unit/permissions.test.ts"]
183
+ // CIL[DOC-CONTRACT inputs="none" outputs="test assertions" errors="none" side_effects="Tests principal.ts module"]
184
+ // CIL[DOC-MICRO logic_summary="Tests role presence checking for human principals" notable_decisions="[]"]
185
+ // CIL[DOC-CONFIDENCE pass="second" score="0.90" flags="none"]
186
+ // CIL[DOC-STABILITY stability="stable"]
187
+ describe('humanHasRole', () => {
188
+ it('returns true when role is present', async () => {
189
+ const { humanHasRole } = await import('../../functions/_shared/principal.ts')
190
+ const principal = makePrincipal({ roles: ['admin', 'member'] })
191
+ expect(humanHasRole(principal, 'admin')).toBe(true)
192
+ })
193
+
194
+ it('returns false when role is absent', async () => {
195
+ const { humanHasRole } = await import('../../functions/_shared/principal.ts')
196
+ const principal = makePrincipal({ roles: ['member'] })
197
+ expect(humanHasRole(principal, 'admin')).toBe(false)
198
+ })
199
+
200
+ it('returns false for machine principals', async () => {
201
+ const { humanHasRole } = await import('../../functions/_shared/principal.ts')
202
+ const principal = makePrincipal({ type: 'machine' })
203
+ expect(humanHasRole(principal, 'admin')).toBe(false)
204
+ })
205
+ })
206
+ // CIL[DOC-VECTOR type="context" content="purpose='Test humanHasRole permission function'; No verified external callers; imports: .framework/functions/_shared/principal.ts"]
207
+ // CIL[DOC-VECTOR type="blast_radius" content="No direct caller data from CIL graph; local impact only"]
208
+ // CIL[DOC-VECTOR type="configuration" content="No environment or build configuration dependencies identified"]
209
+ // CIL[DOC-VECTOR type="constraint" content="Standard runtime; no special invariants documented"]
210
+ // CIL[DOC-VECTOR type="implementation_pattern" content="" status="pending_human_input"]
211
+ // CIL[DOC-VECTOR type="user_journey" content="" status="pending_human_input"]
212
+ // CIL[END stable_id="~/.framework/tests/unit/permissions.test.ts:describe_humanHasRole:block"]
213
+
214
+ // CIL[BEGIN stable_id="~/.framework/tests/unit/permissions.test.ts:describe_sanitizeRecordData:block" type="block" identity="describe_sanitizeRecordData" parent="none"]
215
+ // CIL[DOC-MACRO purpose="Test sanitizeRecordData permission function"]
216
+ // CIL[DOC-RESPONSIBILITY responsibility="Verify record data sanitization by role"]
217
+ // CIL[DOC-CONTEXT module="tests/unit/permissions" layer="test-unit" related_files=".framework/functions/_shared/principal.ts,.framework/tests/unit/permissions.test.ts"]
218
+ // CIL[DOC-CONTRACT inputs="none" outputs="test assertions" errors="none" side_effects="Tests permissions.ts module"]
219
+ // CIL[DOC-MICRO logic_summary="Tests config record sanitization for different user types" notable_decisions="[]"]
220
+ // CIL[DOC-CONFIDENCE pass="second" score="0.90" flags="none"]
221
+ // CIL[DOC-STABILITY stability="stable"]
222
+ describe('sanitizeRecordData — second surface (config objects)', () => {
223
+ const configRecord = {
224
+ id: 'cfg-1',
225
+ slug: 'my-type',
226
+ name: 'My Type',
227
+ kind: 'item',
228
+ created_at: '2024-01-01T00:00:00Z',
229
+ updated_at: '2024-01-01T00:00:00Z',
230
+ _table: 'types'
231
+ }
232
+
233
+ it('system_admin receives full config record', async () => {
234
+ const { sanitizeRecordData } = await import('../../functions/_shared/permissions.ts')
235
+ const principal = makePrincipal({ roles: ['system_admin'] })
236
+ const ctx = makeCtx(principal)
237
+ const result = await sanitizeRecordData(ctx, configRecord, 'types')
238
+ expect(result).toHaveProperty('slug')
239
+ expect(result).toHaveProperty('name')
240
+ expect(result).toHaveProperty('kind')
241
+ })
242
+
243
+ it('machine principal with *:* receives full config record', async () => {
244
+ const { sanitizeRecordData } = await import('../../functions/_shared/permissions.ts')
245
+ const principal = makePrincipal({ type: 'machine', scopes: ['*:*'] })
246
+ const ctx = makeCtx(principal)
247
+ const result = await sanitizeRecordData(ctx, configRecord, 'types')
248
+ expect(result).toHaveProperty('id')
249
+ expect(result).toHaveProperty('slug')
250
+ })
251
+
252
+ it('non-admin human receives minimal stub from config record', async () => {
253
+ const { sanitizeRecordData } = await import('../../functions/_shared/permissions.ts')
254
+ const principal = makePrincipal({ roles: ['member'] })
255
+ const ctx = makeCtx(principal)
256
+ const result = await sanitizeRecordData(ctx, configRecord, 'types')
257
+ expect(result).toHaveProperty('id')
258
+ expect(result).toHaveProperty('created_at')
259
+ expect(result).not.toHaveProperty('kind')
260
+ expect(result).not.toHaveProperty('slug')
261
+ })
262
+ })
263
+ // CIL[DOC-VECTOR type="context" content="purpose='Test sanitizeRecordData permission function'; No verified external callers; imports: .framework/functions/_shared/principal.ts"]
264
+ // CIL[DOC-VECTOR type="blast_radius" content="No direct caller data from CIL graph; local impact only"]
265
+ // CIL[DOC-VECTOR type="configuration" content="No environment or build configuration dependencies identified"]
266
+ // CIL[DOC-VECTOR type="constraint" content="Standard runtime; no special invariants documented"]
267
+ // CIL[DOC-VECTOR type="implementation_pattern" content="" status="pending_human_input"]
268
+ // CIL[DOC-VECTOR type="user_journey" content="" status="pending_human_input"]
269
+ // CIL[END stable_id="~/.framework/tests/unit/permissions.test.ts:describe_sanitizeRecordData:block"]