@elevasis/core 0.21.0 → 0.23.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/dist/index.d.ts +2518 -2169
- package/dist/index.js +2495 -1095
- package/dist/knowledge/index.d.ts +706 -1044
- package/dist/knowledge/index.js +9 -9
- package/dist/organization-model/index.d.ts +2518 -2169
- package/dist/organization-model/index.js +2495 -1095
- package/dist/test-utils/index.d.ts +826 -1014
- package/dist/test-utils/index.js +1894 -1032
- package/package.json +3 -3
- package/src/__tests__/template-core-compatibility.test.ts +11 -79
- package/src/_gen/__tests__/__snapshots__/contracts.md.snap +852 -397
- package/src/auth/multi-tenancy/permissions.ts +20 -8
- package/src/business/README.md +2 -2
- package/src/business/acquisition/api-schemas.test.ts +175 -2
- package/src/business/acquisition/api-schemas.ts +132 -16
- package/src/business/acquisition/build-templates.test.ts +4 -4
- package/src/business/acquisition/build-templates.ts +72 -30
- package/src/business/acquisition/crm-state-actions.test.ts +13 -11
- package/src/business/acquisition/index.ts +12 -0
- package/src/business/acquisition/types.ts +7 -3
- package/src/business/clients/api-schemas.test.ts +115 -0
- package/src/business/clients/api-schemas.ts +158 -0
- package/src/business/clients/index.ts +1 -0
- package/src/business/deals/api-schemas.ts +8 -0
- package/src/business/index.ts +5 -2
- package/src/business/projects/types.ts +19 -0
- package/src/execution/engine/__tests__/fixtures/test-agents.ts +10 -8
- package/src/execution/engine/agent/core/__tests__/agent.test.ts +16 -12
- package/src/execution/engine/agent/core/__tests__/error-passthrough.test.ts +4 -3
- package/src/execution/engine/agent/core/types.ts +25 -15
- package/src/execution/engine/agent/index.ts +6 -4
- package/src/execution/engine/agent/reasoning/__tests__/request-builder.test.ts +24 -18
- package/src/execution/engine/index.ts +3 -0
- package/src/execution/engine/workflow/types.ts +9 -2
- package/src/knowledge/README.md +8 -7
- package/src/knowledge/__tests__/queries.test.ts +74 -73
- package/src/knowledge/format.ts +10 -9
- package/src/knowledge/index.ts +1 -1
- package/src/knowledge/published.ts +1 -1
- package/src/knowledge/queries.ts +26 -25
- package/src/organization-model/README.md +73 -26
- package/src/organization-model/__tests__/content-kinds-registry.test.ts +210 -0
- package/src/organization-model/__tests__/defaults.test.ts +76 -96
- package/src/organization-model/__tests__/domains/actions.test.ts +56 -0
- package/src/organization-model/__tests__/domains/customers.test.ts +299 -295
- package/src/organization-model/__tests__/domains/entities.test.ts +56 -0
- package/src/organization-model/__tests__/domains/goals.test.ts +493 -479
- package/src/organization-model/__tests__/domains/identity.test.ts +280 -279
- package/src/organization-model/__tests__/domains/navigation.test.ts +268 -212
- package/src/organization-model/__tests__/domains/offerings.test.ts +414 -419
- package/src/organization-model/__tests__/domains/policies.test.ts +323 -0
- package/src/organization-model/__tests__/domains/resource-mappings.test.ts +271 -271
- package/src/organization-model/__tests__/domains/resources.test.ts +310 -0
- package/src/organization-model/__tests__/domains/roles.test.ts +463 -347
- package/src/organization-model/__tests__/domains/statuses.test.ts +246 -243
- package/src/organization-model/__tests__/domains/systems.test.ts +209 -0
- package/src/organization-model/__tests__/flatten-additive-merge.test.ts +361 -0
- package/src/organization-model/__tests__/foundation.test.ts +74 -102
- package/src/organization-model/__tests__/get-resources-for-system.test.ts +144 -0
- package/src/organization-model/__tests__/graph.test.ts +899 -71
- package/src/organization-model/__tests__/knowledge.test.ts +209 -49
- package/src/organization-model/__tests__/lookup-helpers.test.ts +438 -0
- package/src/organization-model/__tests__/migration-helpers.test.ts +591 -0
- package/src/organization-model/__tests__/prospecting-ssot.test.ts +36 -27
- package/src/organization-model/__tests__/recursive-system-schema.test.ts +520 -0
- package/src/organization-model/__tests__/resolve.test.ts +174 -23
- package/src/organization-model/__tests__/schema.test.ts +291 -114
- package/src/organization-model/__tests__/surface-projection.test.ts +207 -97
- package/src/organization-model/catalogs/lead-gen.ts +144 -0
- package/src/organization-model/content-kinds/config.ts +36 -0
- package/src/organization-model/content-kinds/index.ts +74 -0
- package/src/organization-model/content-kinds/pipeline.ts +68 -0
- package/src/organization-model/content-kinds/registry.ts +44 -0
- package/src/organization-model/content-kinds/status.ts +71 -0
- package/src/organization-model/content-kinds/template.ts +83 -0
- package/src/organization-model/content-kinds/types.ts +117 -0
- package/src/organization-model/contracts.ts +13 -3
- package/src/organization-model/defaults.ts +499 -86
- package/src/organization-model/domains/actions.ts +239 -0
- package/src/organization-model/domains/customers.ts +78 -75
- package/src/organization-model/domains/entities.ts +144 -0
- package/src/organization-model/domains/goals.ts +83 -80
- package/src/organization-model/domains/knowledge.ts +76 -17
- package/src/organization-model/domains/navigation.ts +107 -384
- package/src/organization-model/domains/offerings.ts +71 -66
- package/src/organization-model/domains/policies.ts +102 -0
- package/src/organization-model/domains/projects.ts +14 -48
- package/src/organization-model/domains/prospecting.ts +62 -181
- package/src/organization-model/domains/resources.ts +145 -0
- package/src/organization-model/domains/roles.ts +96 -55
- package/src/organization-model/domains/sales.ts +10 -219
- package/src/organization-model/domains/shared.ts +57 -57
- package/src/organization-model/domains/statuses.ts +339 -130
- package/src/organization-model/domains/systems.ts +203 -0
- package/src/organization-model/foundation.ts +54 -67
- package/src/organization-model/graph/build.ts +682 -54
- package/src/organization-model/graph/link.ts +1 -1
- package/src/organization-model/graph/schema.ts +24 -9
- package/src/organization-model/graph/types.ts +20 -7
- package/src/organization-model/helpers.ts +231 -26
- package/src/organization-model/icons.ts +1 -0
- package/src/organization-model/index.ts +118 -5
- package/src/organization-model/migration-helpers.ts +249 -0
- package/src/organization-model/organization-graph.mdx +16 -15
- package/src/organization-model/organization-model.mdx +111 -44
- package/src/organization-model/published.ts +172 -19
- package/src/organization-model/resolve.ts +117 -54
- package/src/organization-model/schema.ts +654 -112
- package/src/organization-model/surface-projection.ts +116 -122
- package/src/organization-model/types.ts +146 -20
- package/src/platform/api/types.ts +38 -35
- package/src/platform/constants/versions.ts +1 -1
- package/src/platform/registry/__tests__/command-view.test.ts +6 -8
- package/src/platform/registry/__tests__/resource-link.test.ts +13 -8
- package/src/platform/registry/__tests__/resource-registry.integration.test.ts +16 -31
- package/src/platform/registry/__tests__/resource-registry.nested-systems.test.ts +245 -0
- package/src/platform/registry/__tests__/resource-registry.test.ts +2053 -2005
- package/src/platform/registry/__tests__/validation.test.ts +1347 -1086
- package/src/platform/registry/index.ts +14 -0
- package/src/platform/registry/resource-registry.ts +52 -2
- package/src/platform/registry/serialization.ts +241 -202
- package/src/platform/registry/serialized-types.ts +1 -0
- package/src/platform/registry/types.ts +411 -361
- package/src/platform/registry/validation.ts +745 -513
- package/src/projects/api-schemas.ts +290 -267
- package/src/reference/_generated/contracts.md +853 -397
- package/src/reference/glossary.md +23 -18
- package/src/supabase/database.types.ts +181 -0
- package/src/test-utils/test-utils.test.ts +1 -6
- package/src/organization-model/__tests__/domains/operations.test.ts +0 -203
- package/src/organization-model/domains/features.ts +0 -31
- package/src/organization-model/domains/operations.ts +0 -85
|
@@ -11,41 +11,45 @@ description: Terminology disambiguation for Organization OS concepts used in the
|
|
|
11
11
|
|
|
12
12
|
**Contract** -- the publishable boundary a consumer depends on: Zod schemas, TypeScript types, provider props, resource definitions, or workflow I/O schemas.
|
|
13
13
|
|
|
14
|
-
**DeploymentSpec** --
|
|
14
|
+
**DeploymentSpec** -- runtime/deploy assembly for one organization: workflows, agents, triggers, integrations, relationships, external resources, and human checkpoints. It assembles executable behavior around Organization Model resource descriptors; it is not the source of resource identity.
|
|
15
15
|
|
|
16
|
-
**Feature** --
|
|
16
|
+
**Feature** -- legacy or UI-package wording for a platform capability area. In the current Organization Model, use **System** for semantic ownership and **navigation surface** for shell placement. Keep "feature" only when referring to existing UI package folders, exported manifest names, or legacy compatibility recipes.
|
|
17
17
|
|
|
18
|
-
**
|
|
18
|
+
**SystemGuard** -- route-level System gate from `@elevasis/ui/features/auth`.
|
|
19
19
|
|
|
20
|
-
**
|
|
20
|
+
**SystemModule** -- manifest contract a shell module provides to `ElevasisSystemsProvider`. Key fields are `key`, optional `systemId`, optional `routePrefixes`, optional `capabilityIds`, optional `icon`, optional `sidebar`, optional `sidebarWidth`, and optional graph bridge metadata.
|
|
21
21
|
|
|
22
|
-
**
|
|
22
|
+
**systemId** -- the `SystemModule` field that points to an `OrganizationModel.systems` entry. Navigation-only app modules may omit it and use route prefixes/surface metadata instead.
|
|
23
23
|
|
|
24
24
|
**Foundations** -- local adapter layer in external projects that exports `canonicalOrganizationModel`, `organizationModel`, and workflow I/O schemas.
|
|
25
25
|
|
|
26
|
-
**Graph node ID** -- kind-prefixed cross-collection identifier such as `
|
|
26
|
+
**Graph node ID** -- kind-prefixed cross-collection identifier such as `system:sales.crm`, `integration:instantly`, or `resource:lead-import`.
|
|
27
27
|
|
|
28
28
|
**Manifest** -- a runtime declaration for a feature or resource collection.
|
|
29
29
|
|
|
30
|
-
**MembershipFeatureConfig** -- per-member feature override config
|
|
30
|
+
**MembershipFeatureConfig** -- legacy per-member feature override config. Current System visibility is resolved through Organization Model lifecycle/access metadata and provider compatibility layers.
|
|
31
31
|
|
|
32
|
-
**OrganizationModel** -- top-level semantic contract for an organization. Current primary fields include `
|
|
32
|
+
**OrganizationModel** -- top-level semantic contract for an organization. Current primary fields include `version`, `domainMetadata`, `branding`, `navigation`, `sales`, `prospecting`, `projects`, `identity`, `customers`, `offerings`, `roles`, `goals`, `systems`, `resources`, `actions`, `entities`, `policies`, `statuses`, and `knowledge`.
|
|
33
33
|
|
|
34
|
-
**
|
|
34
|
+
**OrganizationModelSystemEntry** -- System node in `OrganizationModel.systems`. Fields include `id`, `label`, `description`, `parentSystemId`, `subsystems`, `lifecycle`, `ui`, `requiresAdmin`, `devOnly`, `responsibleRoleId`, `governedByKnowledge`, `drivesGoals`, `actions`, `content`, and `order`.
|
|
35
35
|
|
|
36
|
-
**Provider /
|
|
36
|
+
**Provider / ElevasisSystemsProvider** -- runtime that registers System modules, resolves System access against the org model, projects sidebar navigation, and exposes shell helpers through `useElevasisSystems()`.
|
|
37
37
|
|
|
38
|
-
**Resource** --
|
|
38
|
+
**Resource** -- governance-only descriptor in `OrganizationModel.resources` for a workflow, agent, integration, or script. Runtime code derives `resourceId` and kind from the descriptor, then attaches executable behavior in operations.
|
|
39
|
+
|
|
40
|
+
**Resource descriptor** -- OM entry with canonical `id`, required `systemPath`, governance `status`, and optional role ownership. Workflow descriptors may mirror `actionKey`; agent descriptors carry `agentKind`, `sessionCapable`, and optional `actsAsRoleId`; integration descriptors name a provider.
|
|
41
|
+
|
|
42
|
+
**System** -- tenant-defined bounded context in `OrganizationModel.systems.systems` that groups operational resources and carries governance metadata such as responsible role, governing knowledge, driven goals, kind, and status.
|
|
39
43
|
|
|
40
44
|
**ResourceCategory** -- resource metadata category: `production`, `diagnostic`, `internal`, or `testing`.
|
|
41
45
|
|
|
42
46
|
**ResourceLink** -- graph binding on resource metadata: `{ nodeId, kind }`.
|
|
43
47
|
|
|
44
|
-
**Settings asymmetry** --
|
|
48
|
+
**Settings asymmetry** -- Settings is a navigation/app surface whose individual pages are normally governed by admin checks rather than user-facing System toggles.
|
|
45
49
|
|
|
46
|
-
**Shell model** -- provider output used by sidebars and breadcrumbs. Includes `
|
|
50
|
+
**Shell model** -- provider output used by sidebars and breadcrumbs. Includes `systems`, `childrenOf`, `ancestorsOf`, `parentOf`, `topLevel`, `findByPath`, `requiresAdminFor`, and `devOnlyFor`.
|
|
47
51
|
|
|
48
|
-
**Subshell / Sidebar** --
|
|
52
|
+
**Subshell / Sidebar** -- System- or route-prefix-scoped UI region rendered when the current route matches a module whose manifest supplies a sidebar.
|
|
49
53
|
|
|
50
54
|
**Topology** -- runtime resource relationships declared in `DeploymentSpec.relationships`.
|
|
51
55
|
|
|
@@ -53,16 +57,17 @@ description: Terminology disambiguation for Organization OS concepts used in the
|
|
|
53
57
|
|
|
54
58
|
**`@elevasis/core`**
|
|
55
59
|
|
|
56
|
-
- `OrganizationModel`, `
|
|
60
|
+
- `OrganizationModel`, `OrganizationModelSystemEntry`
|
|
61
|
+
- `SystemEntry`, `ResourceEntry`
|
|
57
62
|
- `resolveOrganizationModel`, `defineOrganizationModel`, `DEFAULT_ORGANIZATION_MODEL`
|
|
58
63
|
- `MembershipFeatureConfig`
|
|
59
64
|
- `DeploymentSpec`, `ResourceLink`, `ResourceCategory`
|
|
60
65
|
|
|
61
66
|
**`@elevasis/ui`**
|
|
62
67
|
|
|
63
|
-
- `
|
|
64
|
-
- `
|
|
65
|
-
- `
|
|
68
|
+
- `SystemModule`
|
|
69
|
+
- `SystemGuard`, `AdminGuard`, `ProtectedRoute`
|
|
70
|
+
- `ElevasisSystemsProvider`, `ElevasisCoreProvider`, `useElevasisSystems`
|
|
66
71
|
|
|
67
72
|
**External project source**
|
|
68
73
|
|
|
@@ -66,6 +66,7 @@ export type Database = {
|
|
|
66
66
|
batch_id: string | null
|
|
67
67
|
category: string | null
|
|
68
68
|
category_pain: string | null
|
|
69
|
+
client_id: string | null
|
|
69
70
|
created_at: string
|
|
70
71
|
domain: string | null
|
|
71
72
|
enrichment_data: Json | null
|
|
@@ -92,6 +93,7 @@ export type Database = {
|
|
|
92
93
|
batch_id?: string | null
|
|
93
94
|
category?: string | null
|
|
94
95
|
category_pain?: string | null
|
|
96
|
+
client_id?: string | null
|
|
95
97
|
created_at?: string
|
|
96
98
|
domain?: string | null
|
|
97
99
|
enrichment_data?: Json | null
|
|
@@ -118,6 +120,7 @@ export type Database = {
|
|
|
118
120
|
batch_id?: string | null
|
|
119
121
|
category?: string | null
|
|
120
122
|
category_pain?: string | null
|
|
123
|
+
client_id?: string | null
|
|
121
124
|
created_at?: string
|
|
122
125
|
domain?: string | null
|
|
123
126
|
enrichment_data?: Json | null
|
|
@@ -141,6 +144,13 @@ export type Database = {
|
|
|
141
144
|
website?: string | null
|
|
142
145
|
}
|
|
143
146
|
Relationships: [
|
|
147
|
+
{
|
|
148
|
+
foreignKeyName: "acq_companies_client_id_fkey"
|
|
149
|
+
columns: ["client_id"]
|
|
150
|
+
isOneToOne: false
|
|
151
|
+
referencedRelation: "clients"
|
|
152
|
+
referencedColumns: ["id"]
|
|
153
|
+
},
|
|
144
154
|
{
|
|
145
155
|
foreignKeyName: "acq_companies_organization_id_fkey"
|
|
146
156
|
columns: ["organization_id"]
|
|
@@ -155,6 +165,7 @@ export type Database = {
|
|
|
155
165
|
batch_id: string | null
|
|
156
166
|
brochure_first_viewed_at: string | null
|
|
157
167
|
brochure_view_count: number
|
|
168
|
+
client_id: string | null
|
|
158
169
|
company_id: string | null
|
|
159
170
|
created_at: string
|
|
160
171
|
email: string
|
|
@@ -183,6 +194,7 @@ export type Database = {
|
|
|
183
194
|
batch_id?: string | null
|
|
184
195
|
brochure_first_viewed_at?: string | null
|
|
185
196
|
brochure_view_count?: number
|
|
197
|
+
client_id?: string | null
|
|
186
198
|
company_id?: string | null
|
|
187
199
|
created_at?: string
|
|
188
200
|
email: string
|
|
@@ -211,6 +223,7 @@ export type Database = {
|
|
|
211
223
|
batch_id?: string | null
|
|
212
224
|
brochure_first_viewed_at?: string | null
|
|
213
225
|
brochure_view_count?: number
|
|
226
|
+
client_id?: string | null
|
|
214
227
|
company_id?: string | null
|
|
215
228
|
created_at?: string
|
|
216
229
|
email?: string
|
|
@@ -236,6 +249,13 @@ export type Database = {
|
|
|
236
249
|
updated_at?: string
|
|
237
250
|
}
|
|
238
251
|
Relationships: [
|
|
252
|
+
{
|
|
253
|
+
foreignKeyName: "acq_contacts_client_id_fkey"
|
|
254
|
+
columns: ["client_id"]
|
|
255
|
+
isOneToOne: false
|
|
256
|
+
referencedRelation: "clients"
|
|
257
|
+
referencedColumns: ["id"]
|
|
258
|
+
},
|
|
239
259
|
{
|
|
240
260
|
foreignKeyName: "acq_contacts_company_id_fkey"
|
|
241
261
|
columns: ["company_id"]
|
|
@@ -479,8 +499,10 @@ export type Database = {
|
|
|
479
499
|
acq_deals: {
|
|
480
500
|
Row: {
|
|
481
501
|
activity_log: Json
|
|
502
|
+
client_id: string | null
|
|
482
503
|
closed_lost_at: string | null
|
|
483
504
|
closed_lost_reason: string | null
|
|
505
|
+
company_id: string | null
|
|
484
506
|
contact_email: string
|
|
485
507
|
contact_id: string | null
|
|
486
508
|
created_at: string
|
|
@@ -516,8 +538,10 @@ export type Database = {
|
|
|
516
538
|
}
|
|
517
539
|
Insert: {
|
|
518
540
|
activity_log?: Json
|
|
541
|
+
client_id?: string | null
|
|
519
542
|
closed_lost_at?: string | null
|
|
520
543
|
closed_lost_reason?: string | null
|
|
544
|
+
company_id?: string | null
|
|
521
545
|
contact_email: string
|
|
522
546
|
contact_id?: string | null
|
|
523
547
|
created_at?: string
|
|
@@ -553,8 +577,10 @@ export type Database = {
|
|
|
553
577
|
}
|
|
554
578
|
Update: {
|
|
555
579
|
activity_log?: Json
|
|
580
|
+
client_id?: string | null
|
|
556
581
|
closed_lost_at?: string | null
|
|
557
582
|
closed_lost_reason?: string | null
|
|
583
|
+
company_id?: string | null
|
|
558
584
|
contact_email?: string
|
|
559
585
|
contact_id?: string | null
|
|
560
586
|
created_at?: string
|
|
@@ -589,6 +615,20 @@ export type Database = {
|
|
|
589
615
|
updated_at?: string
|
|
590
616
|
}
|
|
591
617
|
Relationships: [
|
|
618
|
+
{
|
|
619
|
+
foreignKeyName: "acq_deals_client_id_fkey"
|
|
620
|
+
columns: ["client_id"]
|
|
621
|
+
isOneToOne: false
|
|
622
|
+
referencedRelation: "clients"
|
|
623
|
+
referencedColumns: ["id"]
|
|
624
|
+
},
|
|
625
|
+
{
|
|
626
|
+
foreignKeyName: "acq_deals_company_id_fkey"
|
|
627
|
+
columns: ["company_id"]
|
|
628
|
+
isOneToOne: false
|
|
629
|
+
referencedRelation: "acq_companies"
|
|
630
|
+
referencedColumns: ["id"]
|
|
631
|
+
},
|
|
592
632
|
{
|
|
593
633
|
foreignKeyName: "acq_deals_contact_id_fkey"
|
|
594
634
|
columns: ["contact_id"]
|
|
@@ -1206,6 +1246,77 @@ export type Database = {
|
|
|
1206
1246
|
},
|
|
1207
1247
|
]
|
|
1208
1248
|
}
|
|
1249
|
+
clients: {
|
|
1250
|
+
Row: {
|
|
1251
|
+
converted_at: string | null
|
|
1252
|
+
created_at: string
|
|
1253
|
+
id: string
|
|
1254
|
+
metadata: Json
|
|
1255
|
+
name: string
|
|
1256
|
+
organization_id: string
|
|
1257
|
+
primary_company_id: string | null
|
|
1258
|
+
primary_contact_id: string | null
|
|
1259
|
+
source_deal_id: string | null
|
|
1260
|
+
status: string
|
|
1261
|
+
updated_at: string
|
|
1262
|
+
}
|
|
1263
|
+
Insert: {
|
|
1264
|
+
converted_at?: string | null
|
|
1265
|
+
created_at?: string
|
|
1266
|
+
id?: string
|
|
1267
|
+
metadata?: Json
|
|
1268
|
+
name: string
|
|
1269
|
+
organization_id: string
|
|
1270
|
+
primary_company_id?: string | null
|
|
1271
|
+
primary_contact_id?: string | null
|
|
1272
|
+
source_deal_id?: string | null
|
|
1273
|
+
status?: string
|
|
1274
|
+
updated_at?: string
|
|
1275
|
+
}
|
|
1276
|
+
Update: {
|
|
1277
|
+
converted_at?: string | null
|
|
1278
|
+
created_at?: string
|
|
1279
|
+
id?: string
|
|
1280
|
+
metadata?: Json
|
|
1281
|
+
name?: string
|
|
1282
|
+
organization_id?: string
|
|
1283
|
+
primary_company_id?: string | null
|
|
1284
|
+
primary_contact_id?: string | null
|
|
1285
|
+
source_deal_id?: string | null
|
|
1286
|
+
status?: string
|
|
1287
|
+
updated_at?: string
|
|
1288
|
+
}
|
|
1289
|
+
Relationships: [
|
|
1290
|
+
{
|
|
1291
|
+
foreignKeyName: "clients_organization_id_fkey"
|
|
1292
|
+
columns: ["organization_id"]
|
|
1293
|
+
isOneToOne: false
|
|
1294
|
+
referencedRelation: "organizations"
|
|
1295
|
+
referencedColumns: ["id"]
|
|
1296
|
+
},
|
|
1297
|
+
{
|
|
1298
|
+
foreignKeyName: "clients_primary_company_id_fkey"
|
|
1299
|
+
columns: ["primary_company_id"]
|
|
1300
|
+
isOneToOne: false
|
|
1301
|
+
referencedRelation: "acq_companies"
|
|
1302
|
+
referencedColumns: ["id"]
|
|
1303
|
+
},
|
|
1304
|
+
{
|
|
1305
|
+
foreignKeyName: "clients_primary_contact_id_fkey"
|
|
1306
|
+
columns: ["primary_contact_id"]
|
|
1307
|
+
isOneToOne: false
|
|
1308
|
+
referencedRelation: "acq_contacts"
|
|
1309
|
+
referencedColumns: ["id"]
|
|
1310
|
+
},
|
|
1311
|
+
{
|
|
1312
|
+
foreignKeyName: "clients_source_deal_id_fkey"
|
|
1313
|
+
columns: ["source_deal_id"]
|
|
1314
|
+
isOneToOne: false
|
|
1315
|
+
referencedRelation: "acq_deals"
|
|
1316
|
+
referencedColumns: ["id"]
|
|
1317
|
+
},
|
|
1318
|
+
]
|
|
1319
|
+
}
|
|
1209
1320
|
command_queue: {
|
|
1210
1321
|
Row: {
|
|
1211
1322
|
action_payload: Json | null
|
|
@@ -2175,6 +2286,7 @@ export type Database = {
|
|
|
2175
2286
|
Row: {
|
|
2176
2287
|
actual_end_date: string | null
|
|
2177
2288
|
client_company_id: string | null
|
|
2289
|
+
client_id: string | null
|
|
2178
2290
|
contract_value: number | null
|
|
2179
2291
|
created_at: string
|
|
2180
2292
|
deal_id: string | null
|
|
@@ -2192,6 +2304,7 @@ export type Database = {
|
|
|
2192
2304
|
Insert: {
|
|
2193
2305
|
actual_end_date?: string | null
|
|
2194
2306
|
client_company_id?: string | null
|
|
2307
|
+
client_id?: string | null
|
|
2195
2308
|
contract_value?: number | null
|
|
2196
2309
|
created_at?: string
|
|
2197
2310
|
deal_id?: string | null
|
|
@@ -2209,6 +2322,7 @@ export type Database = {
|
|
|
2209
2322
|
Update: {
|
|
2210
2323
|
actual_end_date?: string | null
|
|
2211
2324
|
client_company_id?: string | null
|
|
2325
|
+
client_id?: string | null
|
|
2212
2326
|
contract_value?: number | null
|
|
2213
2327
|
created_at?: string
|
|
2214
2328
|
deal_id?: string | null
|
|
@@ -2245,6 +2359,13 @@ export type Database = {
|
|
|
2245
2359
|
referencedRelation: "acq_companies"
|
|
2246
2360
|
referencedColumns: ["id"]
|
|
2247
2361
|
},
|
|
2362
|
+
{
|
|
2363
|
+
foreignKeyName: "prj_projects_client_id_fkey"
|
|
2364
|
+
columns: ["client_id"]
|
|
2365
|
+
isOneToOne: false
|
|
2366
|
+
referencedRelation: "clients"
|
|
2367
|
+
referencedColumns: ["id"]
|
|
2368
|
+
},
|
|
2248
2369
|
{
|
|
2249
2370
|
foreignKeyName: "prj_projects_deal_id_fkey"
|
|
2250
2371
|
columns: ["deal_id"]
|
|
@@ -2649,6 +2770,66 @@ export type Database = {
|
|
|
2649
2770
|
},
|
|
2650
2771
|
]
|
|
2651
2772
|
}
|
|
2773
|
+
user_notes: {
|
|
2774
|
+
Row: {
|
|
2775
|
+
content: string
|
|
2776
|
+
created_at: string
|
|
2777
|
+
created_by: string
|
|
2778
|
+
id: string
|
|
2779
|
+
metadata: Json
|
|
2780
|
+
organization_id: string | null
|
|
2781
|
+
pinned: boolean
|
|
2782
|
+
priority: string
|
|
2783
|
+
source: string | null
|
|
2784
|
+
title: string | null
|
|
2785
|
+
updated_at: string
|
|
2786
|
+
user_id: string
|
|
2787
|
+
}
|
|
2788
|
+
Insert: {
|
|
2789
|
+
content: string
|
|
2790
|
+
created_at?: string
|
|
2791
|
+
created_by?: string
|
|
2792
|
+
id?: string
|
|
2793
|
+
metadata?: Json
|
|
2794
|
+
organization_id?: string | null
|
|
2795
|
+
pinned?: boolean
|
|
2796
|
+
priority?: string
|
|
2797
|
+
source?: string | null
|
|
2798
|
+
title?: string | null
|
|
2799
|
+
updated_at?: string
|
|
2800
|
+
user_id: string
|
|
2801
|
+
}
|
|
2802
|
+
Update: {
|
|
2803
|
+
content?: string
|
|
2804
|
+
created_at?: string
|
|
2805
|
+
created_by?: string
|
|
2806
|
+
id?: string
|
|
2807
|
+
metadata?: Json
|
|
2808
|
+
organization_id?: string | null
|
|
2809
|
+
pinned?: boolean
|
|
2810
|
+
priority?: string
|
|
2811
|
+
source?: string | null
|
|
2812
|
+
title?: string | null
|
|
2813
|
+
updated_at?: string
|
|
2814
|
+
user_id?: string
|
|
2815
|
+
}
|
|
2816
|
+
Relationships: [
|
|
2817
|
+
{
|
|
2818
|
+
foreignKeyName: "user_notes_organization_id_fkey"
|
|
2819
|
+
columns: ["organization_id"]
|
|
2820
|
+
isOneToOne: false
|
|
2821
|
+
referencedRelation: "organizations"
|
|
2822
|
+
referencedColumns: ["id"]
|
|
2823
|
+
},
|
|
2824
|
+
{
|
|
2825
|
+
foreignKeyName: "user_notes_user_id_fkey"
|
|
2826
|
+
columns: ["user_id"]
|
|
2827
|
+
isOneToOne: false
|
|
2828
|
+
referencedRelation: "users"
|
|
2829
|
+
referencedColumns: ["id"]
|
|
2830
|
+
},
|
|
2831
|
+
]
|
|
2832
|
+
}
|
|
2652
2833
|
users: {
|
|
2653
2834
|
Row: {
|
|
2654
2835
|
config: Json
|
|
@@ -1,6 +1,5 @@
|
|
|
1
1
|
import { describe, expect, it } from 'vitest'
|
|
2
2
|
import { BaseProjectSchema, BaseTaskSchema } from '../business/base-entities'
|
|
3
|
-
import { DEFAULT_ORGANIZATION_MODEL } from '../organization-model'
|
|
4
3
|
import {
|
|
5
4
|
makeInitializationState,
|
|
6
5
|
makeOrganizationModel,
|
|
@@ -28,16 +27,12 @@ describe('published test-utils factories', () => {
|
|
|
28
27
|
|
|
29
28
|
it('creates organization model and initialization fixtures', () => {
|
|
30
29
|
const model = makeOrganizationModel({
|
|
31
|
-
branding: { organizationName: 'Test Brand' }
|
|
32
|
-
features: DEFAULT_ORGANIZATION_MODEL.features.map((feature) =>
|
|
33
|
-
feature.id === 'seo' ? { ...feature, enabled: true } : feature
|
|
34
|
-
)
|
|
30
|
+
branding: { organizationName: 'Test Brand' }
|
|
35
31
|
})
|
|
36
32
|
const profile = makeUserProfile({ id: TEST_USERS.admin.id, email: TEST_USERS.admin.email })
|
|
37
33
|
const state = makeInitializationState({ profile, organizationReady: false, allReady: false })
|
|
38
34
|
|
|
39
35
|
expect(model.branding.organizationName).toBe('Test Brand')
|
|
40
|
-
expect(model.features.find((feature) => feature.id === 'seo')?.enabled).toBe(true)
|
|
41
36
|
expect(state.profile?.email).toBe(TEST_USERS.admin.email)
|
|
42
37
|
expect(state.organizationReady).toBe(false)
|
|
43
38
|
})
|
|
@@ -1,203 +0,0 @@
|
|
|
1
|
-
import { describe, expect, it } from 'vitest'
|
|
2
|
-
import {
|
|
3
|
-
DEFAULT_ORGANIZATION_MODEL_OPERATIONS,
|
|
4
|
-
OperationEntrySchema,
|
|
5
|
-
OperationsDomainSchema,
|
|
6
|
-
OperationSemanticClassSchema
|
|
7
|
-
} from '../../domains/operations'
|
|
8
|
-
|
|
9
|
-
// ---------------------------------------------------------------------------
|
|
10
|
-
// Group 1: OperationEntrySchema — positive parse
|
|
11
|
-
// ---------------------------------------------------------------------------
|
|
12
|
-
|
|
13
|
-
describe('OperationEntrySchema — positive parse', () => {
|
|
14
|
-
it('accepts a fully-specified entry (id, label, semanticClass, featureId, supportedStatusSemanticClass)', () => {
|
|
15
|
-
const result = OperationEntrySchema.safeParse({
|
|
16
|
-
id: 'operations.queue',
|
|
17
|
-
label: 'HITL Queue',
|
|
18
|
-
semanticClass: 'queue',
|
|
19
|
-
featureId: 'operations',
|
|
20
|
-
supportedStatusSemanticClass: ['queue']
|
|
21
|
-
})
|
|
22
|
-
expect(result.success).toBe(true)
|
|
23
|
-
})
|
|
24
|
-
|
|
25
|
-
it('accepts a minimal entry without optional fields', () => {
|
|
26
|
-
const result = OperationEntrySchema.safeParse({
|
|
27
|
-
id: 'operations.sessions',
|
|
28
|
-
label: 'Sessions',
|
|
29
|
-
semanticClass: 'sessions'
|
|
30
|
-
})
|
|
31
|
-
expect(result.success).toBe(true)
|
|
32
|
-
if (result.success) {
|
|
33
|
-
expect(result.data.featureId).toBeUndefined()
|
|
34
|
-
expect(result.data.supportedStatusSemanticClass).toBeUndefined()
|
|
35
|
-
}
|
|
36
|
-
})
|
|
37
|
-
|
|
38
|
-
it('trims whitespace from id and label', () => {
|
|
39
|
-
const result = OperationEntrySchema.safeParse({
|
|
40
|
-
id: ' trimmed-id ',
|
|
41
|
-
label: ' Trimmed Label ',
|
|
42
|
-
semanticClass: 'executions'
|
|
43
|
-
})
|
|
44
|
-
expect(result.success).toBe(true)
|
|
45
|
-
if (result.success) {
|
|
46
|
-
expect(result.data.id).toBe('trimmed-id')
|
|
47
|
-
expect(result.data.label).toBe('Trimmed Label')
|
|
48
|
-
}
|
|
49
|
-
})
|
|
50
|
-
})
|
|
51
|
-
|
|
52
|
-
// ---------------------------------------------------------------------------
|
|
53
|
-
// Group 2: OperationEntrySchema — negative parse
|
|
54
|
-
// ---------------------------------------------------------------------------
|
|
55
|
-
|
|
56
|
-
describe('OperationEntrySchema — negative parse', () => {
|
|
57
|
-
it('rejects a missing id field', () => {
|
|
58
|
-
const result = OperationEntrySchema.safeParse({
|
|
59
|
-
label: 'No ID',
|
|
60
|
-
semanticClass: 'queue'
|
|
61
|
-
})
|
|
62
|
-
expect(result.success).toBe(false)
|
|
63
|
-
})
|
|
64
|
-
|
|
65
|
-
it('rejects a missing label field', () => {
|
|
66
|
-
const result = OperationEntrySchema.safeParse({
|
|
67
|
-
id: 'operations.queue',
|
|
68
|
-
semanticClass: 'queue'
|
|
69
|
-
})
|
|
70
|
-
expect(result.success).toBe(false)
|
|
71
|
-
})
|
|
72
|
-
|
|
73
|
-
it('rejects a missing semanticClass field', () => {
|
|
74
|
-
const result = OperationEntrySchema.safeParse({
|
|
75
|
-
id: 'operations.queue',
|
|
76
|
-
label: 'HITL Queue'
|
|
77
|
-
})
|
|
78
|
-
expect(result.success).toBe(false)
|
|
79
|
-
})
|
|
80
|
-
|
|
81
|
-
it('rejects an unknown semanticClass value', () => {
|
|
82
|
-
const result = OperationEntrySchema.safeParse({
|
|
83
|
-
id: 'some.entry',
|
|
84
|
-
label: 'Some Entry',
|
|
85
|
-
semanticClass: 'not-a-real-class'
|
|
86
|
-
})
|
|
87
|
-
expect(result.success).toBe(false)
|
|
88
|
-
})
|
|
89
|
-
|
|
90
|
-
it('rejects a non-string id (number)', () => {
|
|
91
|
-
const result = OperationEntrySchema.safeParse({
|
|
92
|
-
id: 42,
|
|
93
|
-
label: 'Label',
|
|
94
|
-
semanticClass: 'queue'
|
|
95
|
-
})
|
|
96
|
-
expect(result.success).toBe(false)
|
|
97
|
-
})
|
|
98
|
-
|
|
99
|
-
it('rejects an empty string label (min length 1 after trim)', () => {
|
|
100
|
-
const result = OperationEntrySchema.safeParse({
|
|
101
|
-
id: 'some.entry',
|
|
102
|
-
label: ' ',
|
|
103
|
-
semanticClass: 'queue'
|
|
104
|
-
})
|
|
105
|
-
expect(result.success).toBe(false)
|
|
106
|
-
})
|
|
107
|
-
})
|
|
108
|
-
|
|
109
|
-
// ---------------------------------------------------------------------------
|
|
110
|
-
// Group 3: OperationsDomainSchema — structural tests
|
|
111
|
-
// ---------------------------------------------------------------------------
|
|
112
|
-
|
|
113
|
-
describe('OperationsDomainSchema — structural tests', () => {
|
|
114
|
-
it('accepts an entries-empty domain object', () => {
|
|
115
|
-
const result = OperationsDomainSchema.safeParse({ entries: [] })
|
|
116
|
-
expect(result.success).toBe(true)
|
|
117
|
-
})
|
|
118
|
-
|
|
119
|
-
it('applies an empty-array default when entries is omitted', () => {
|
|
120
|
-
const result = OperationsDomainSchema.safeParse({})
|
|
121
|
-
expect(result.success).toBe(true)
|
|
122
|
-
if (result.success) {
|
|
123
|
-
expect(result.data.entries).toEqual([])
|
|
124
|
-
}
|
|
125
|
-
})
|
|
126
|
-
})
|
|
127
|
-
|
|
128
|
-
// ---------------------------------------------------------------------------
|
|
129
|
-
// Group 4: Semantic class enum — all 5 values declared
|
|
130
|
-
// ---------------------------------------------------------------------------
|
|
131
|
-
|
|
132
|
-
describe('OperationSemanticClassSchema — enum coverage', () => {
|
|
133
|
-
const expectedClasses = ['queue', 'executions', 'sessions', 'notifications', 'schedules'] as const
|
|
134
|
-
|
|
135
|
-
it('enum exposes exactly 5 semantic classes', () => {
|
|
136
|
-
expect(OperationSemanticClassSchema.options).toHaveLength(5)
|
|
137
|
-
})
|
|
138
|
-
|
|
139
|
-
it.each(expectedClasses)('"%s" is a valid semanticClass value', (cls) => {
|
|
140
|
-
const result = OperationSemanticClassSchema.safeParse(cls)
|
|
141
|
-
expect(result.success).toBe(true)
|
|
142
|
-
})
|
|
143
|
-
|
|
144
|
-
it('every entry in the seed uses one of the 5 known semanticClass values', () => {
|
|
145
|
-
const valid = new Set<string>(OperationSemanticClassSchema.options)
|
|
146
|
-
for (const entry of DEFAULT_ORGANIZATION_MODEL_OPERATIONS.entries) {
|
|
147
|
-
expect(
|
|
148
|
-
valid.has(entry.semanticClass),
|
|
149
|
-
`Unexpected semanticClass "${entry.semanticClass}" on entry "${entry.id}"`
|
|
150
|
-
).toBe(true)
|
|
151
|
-
}
|
|
152
|
-
})
|
|
153
|
-
|
|
154
|
-
it('all 5 semanticClass values have exactly one seed entry', () => {
|
|
155
|
-
const presentClasses = new Set(DEFAULT_ORGANIZATION_MODEL_OPERATIONS.entries.map((e) => e.semanticClass))
|
|
156
|
-
for (const cls of OperationSemanticClassSchema.options) {
|
|
157
|
-
expect(presentClasses.has(cls), `No seed entry found for semanticClass "${cls}"`).toBe(true)
|
|
158
|
-
}
|
|
159
|
-
})
|
|
160
|
-
})
|
|
161
|
-
|
|
162
|
-
// ---------------------------------------------------------------------------
|
|
163
|
-
// Group 5: Seed completeness
|
|
164
|
-
// ---------------------------------------------------------------------------
|
|
165
|
-
|
|
166
|
-
describe('DEFAULT_ORGANIZATION_MODEL_OPERATIONS seed — completeness', () => {
|
|
167
|
-
it('has exactly 5 entries (one per entity category)', () => {
|
|
168
|
-
expect(DEFAULT_ORGANIZATION_MODEL_OPERATIONS.entries).toHaveLength(5)
|
|
169
|
-
})
|
|
170
|
-
|
|
171
|
-
it('all entry ids are unique', () => {
|
|
172
|
-
const ids = DEFAULT_ORGANIZATION_MODEL_OPERATIONS.entries.map((e) => e.id)
|
|
173
|
-
const uniqueIds = new Set(ids)
|
|
174
|
-
expect(uniqueIds.size).toBe(ids.length)
|
|
175
|
-
})
|
|
176
|
-
|
|
177
|
-
it('every entry has a non-empty id, label, and semanticClass', () => {
|
|
178
|
-
for (const entry of DEFAULT_ORGANIZATION_MODEL_OPERATIONS.entries) {
|
|
179
|
-
expect(entry.id.length).toBeGreaterThan(0)
|
|
180
|
-
expect(entry.label.length).toBeGreaterThan(0)
|
|
181
|
-
expect(entry.semanticClass.length).toBeGreaterThan(0)
|
|
182
|
-
}
|
|
183
|
-
})
|
|
184
|
-
|
|
185
|
-
it('queue entry references queue status semantic class', () => {
|
|
186
|
-
const queueEntry = DEFAULT_ORGANIZATION_MODEL_OPERATIONS.entries.find((e) => e.semanticClass === 'queue')
|
|
187
|
-
expect(queueEntry).toBeDefined()
|
|
188
|
-
expect(queueEntry?.supportedStatusSemanticClass).toContain('queue')
|
|
189
|
-
})
|
|
190
|
-
|
|
191
|
-
it('executions entry references execution status semantic class', () => {
|
|
192
|
-
const execEntry = DEFAULT_ORGANIZATION_MODEL_OPERATIONS.entries.find((e) => e.semanticClass === 'executions')
|
|
193
|
-
expect(execEntry).toBeDefined()
|
|
194
|
-
expect(execEntry?.supportedStatusSemanticClass).toContain('execution')
|
|
195
|
-
})
|
|
196
|
-
|
|
197
|
-
it('schedules entry references schedule and schedule.run status semantic classes', () => {
|
|
198
|
-
const schedEntry = DEFAULT_ORGANIZATION_MODEL_OPERATIONS.entries.find((e) => e.semanticClass === 'schedules')
|
|
199
|
-
expect(schedEntry).toBeDefined()
|
|
200
|
-
expect(schedEntry?.supportedStatusSemanticClass).toContain('schedule')
|
|
201
|
-
expect(schedEntry?.supportedStatusSemanticClass).toContain('schedule.run')
|
|
202
|
-
})
|
|
203
|
-
})
|
|
@@ -1,31 +0,0 @@
|
|
|
1
|
-
import { z } from 'zod'
|
|
2
|
-
import { ColorTokenSchema, DescriptionSchema, IconNameSchema, LabelSchema, PathSchema } from './shared'
|
|
3
|
-
|
|
4
|
-
export const NodeIdPathSchema = z
|
|
5
|
-
.string()
|
|
6
|
-
.trim()
|
|
7
|
-
.min(1)
|
|
8
|
-
.max(100)
|
|
9
|
-
.regex(/^([a-z0-9-]+)(\.[a-z0-9-]+)*$/, 'Node IDs must be lowercase dotted paths')
|
|
10
|
-
|
|
11
|
-
export const NodeIdStringSchema = z
|
|
12
|
-
.string()
|
|
13
|
-
.trim()
|
|
14
|
-
.min(1)
|
|
15
|
-
.max(200)
|
|
16
|
-
.regex(/^[a-z]+:([a-z0-9-]+)(\.[a-z0-9-]+)*$/, 'Node references must use kind:dotted-path')
|
|
17
|
-
|
|
18
|
-
export const UiPositionSchema = z.enum(['sidebar-primary', 'sidebar-bottom'])
|
|
19
|
-
|
|
20
|
-
export const FeatureSchema = z.object({
|
|
21
|
-
id: NodeIdPathSchema,
|
|
22
|
-
label: LabelSchema,
|
|
23
|
-
description: DescriptionSchema.optional(),
|
|
24
|
-
enabled: z.boolean().default(true),
|
|
25
|
-
path: PathSchema.optional(),
|
|
26
|
-
icon: IconNameSchema.optional(),
|
|
27
|
-
color: ColorTokenSchema.optional(),
|
|
28
|
-
uiPosition: UiPositionSchema.optional(),
|
|
29
|
-
requiresAdmin: z.boolean().optional(),
|
|
30
|
-
devOnly: z.boolean().optional()
|
|
31
|
-
})
|