@elevasis/sdk 1.18.0 → 1.20.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 (58) hide show
  1. package/dist/cli.cjs +1915 -70
  2. package/dist/index.d.ts +825 -16
  3. package/dist/index.js +714 -63
  4. package/dist/node/index.d.ts +1 -0
  5. package/dist/node/index.js +213 -2
  6. package/dist/test-utils/index.d.ts +479 -14
  7. package/dist/test-utils/index.js +660 -54
  8. package/dist/worker/index.js +516 -54
  9. package/package.json +4 -4
  10. package/reference/_navigation.md +2 -1
  11. package/reference/_reference-manifest.json +14 -0
  12. package/reference/claude-config/registries/graph-skills.json +4 -0
  13. package/reference/claude-config/rules/agent-start-here.md +5 -5
  14. package/reference/claude-config/rules/deployment.md +4 -3
  15. package/reference/claude-config/rules/frontend.md +2 -2
  16. package/reference/claude-config/rules/operations.md +17 -13
  17. package/reference/claude-config/rules/organization-model.md +7 -5
  18. package/reference/claude-config/rules/organization-os.md +13 -11
  19. package/reference/claude-config/rules/ui.md +3 -3
  20. package/reference/claude-config/rules/vibe.md +4 -4
  21. package/reference/claude-config/skills/explore/SKILL.md +4 -4
  22. package/reference/claude-config/skills/knowledge/SKILL.md +17 -16
  23. package/reference/claude-config/skills/knowledge/operations/codify-level-a.md +7 -7
  24. package/reference/claude-config/skills/knowledge/operations/codify-level-b.md +13 -13
  25. package/reference/claude-config/skills/knowledge/operations/customers.md +1 -1
  26. package/reference/claude-config/skills/knowledge/operations/goals.md +1 -1
  27. package/reference/claude-config/skills/knowledge/operations/identity.md +1 -1
  28. package/reference/claude-config/skills/knowledge/operations/offerings.md +1 -1
  29. package/reference/claude-config/skills/knowledge/operations/roles.md +1 -1
  30. package/reference/claude-config/skills/knowledge/operations/techStack.md +19 -91
  31. package/reference/claude-config/skills/project/SKILL.md +73 -13
  32. package/reference/claude-config/skills/save/SKILL.md +5 -5
  33. package/reference/claude-config/skills/tutorial/technical.md +11 -14
  34. package/reference/claude-config/sync-notes/2026-05-06-crm-spine.md +60 -0
  35. package/reference/claude-config/sync-notes/2026-05-07-sdk-changes-release-train.md +34 -0
  36. package/reference/claude-config/sync-notes/2026-05-08-resource-governance-scaffold-guidance.md +38 -0
  37. package/reference/claude-config/sync-notes/2026-05-09-clients-domain.md +32 -0
  38. package/reference/claude-config/sync-notes/2026-05-09-command-system.md +33 -0
  39. package/reference/claude-config/sync-notes/2026-05-09-resource-governance-and-misc.md +69 -0
  40. package/reference/examples/organization-model.ts +17 -5
  41. package/reference/framework/index.mdx +1 -1
  42. package/reference/framework/project-structure.mdx +10 -8
  43. package/reference/packages/core/src/business/README.md +2 -2
  44. package/reference/packages/core/src/organization-model/README.md +10 -3
  45. package/reference/resources/index.mdx +27 -17
  46. package/reference/scaffold/core/organization-model.mdx +33 -14
  47. package/reference/scaffold/operations/workflow-recipes.md +35 -29
  48. package/reference/scaffold/recipes/add-a-feature.md +18 -3
  49. package/reference/scaffold/recipes/add-a-resource.md +50 -10
  50. package/reference/scaffold/recipes/customize-crm-actions.md +12 -6
  51. package/reference/scaffold/recipes/customize-organization-model.md +18 -3
  52. package/reference/scaffold/recipes/extend-crm.md +17 -19
  53. package/reference/scaffold/recipes/extend-lead-gen.md +31 -31
  54. package/reference/scaffold/recipes/index.md +1 -1
  55. package/reference/scaffold/reference/contracts.md +512 -307
  56. package/reference/scaffold/reference/feature-registry.md +1 -1
  57. package/reference/scaffold/reference/glossary.md +8 -3
  58. package/reference/scaffold/ui/recipes.md +21 -6
@@ -82,13 +82,28 @@ function AnalyticsLayout() {
82
82
 
83
83
  ## 4. Add backing resources
84
84
 
85
- For workflows or agents that power the feature, declare graph links on the resource metadata:
85
+ For workflows or agents that power the feature, author an OM Resource descriptor first, then derive runtime metadata from it:
86
86
 
87
87
  ```ts
88
+ // core/config/organization-model.ts
89
+ import { defineResources } from '@elevasis/core/organization-model'
90
+
91
+ export const resourceDescriptors = defineResources({
92
+ analyticsRefresh: {
93
+ id: 'analytics-refresh',
94
+ kind: 'workflow',
95
+ systemId: 'sys.analytics',
96
+ ownerRoleId: 'role-ops-lead',
97
+ status: 'active'
98
+ }
99
+ })
100
+
101
+ // operations/src/analytics-refresh/index.ts
88
102
  config: {
89
- resourceId: 'analytics-refresh',
103
+ resource: resourceDescriptors.analyticsRefresh,
104
+ resourceId: resourceDescriptors.analyticsRefresh.id,
90
105
  name: 'Analytics Refresh',
91
- type: 'workflow',
106
+ type: resourceDescriptors.analyticsRefresh.kind,
92
107
  version: '1.0.0',
93
108
  status: 'prod',
94
109
  links: [{ nodeId: 'feature:analytics', kind: 'operates-on' }],
@@ -1,6 +1,6 @@
1
1
  ---
2
2
  title: Add a Resource
3
- description: Add a workflow or agent with resource metadata, graph links, and deployment verification.
3
+ description: Add an OM-owned workflow or agent descriptor, bind executable behavior in operations, and verify descriptor-backed deployment.
4
4
  ---
5
5
  <!-- @generated by packages/sdk/scripts/copy-reference-docs.mjs -- DO NOT EDIT -->
6
6
  <!-- Regenerate: pnpm scaffold:sync -->
@@ -8,18 +8,58 @@ description: Add a workflow or agent with resource metadata, graph links, and de
8
8
 
9
9
  # Add a Resource
10
10
 
11
- Resources are workflows, agents, triggers, integrations, external systems, or human checkpoints collected in a `DeploymentSpec`. They link into the Organization Model graph through resource metadata, not through `OrganizationModel` mapping tables.
11
+ Resources are governed descriptors in the Organization Model. The OM owns resource identity, System membership, owner role, and lifecycle status. Operations code imports those descriptors, attaches executable workflow or agent behavior, and exports a `DeploymentSpec` for deployment.
12
12
 
13
- ## 1. Author the resource
13
+ Do not keep a second identity catalog in operations. `DeploymentSpec` is the runtime/deploy assembly artifact; it should not be the place where a workflow ID is invented.
14
+
15
+ ## 1. Author the OM descriptor
16
+
17
+ Add the descriptor in `core/config/organization-model.ts`:
18
+
19
+ ```ts
20
+ import { defineResources } from '@elevasis/core/organization-model'
21
+
22
+ export const resourceDescriptors = defineResources({
23
+ myWorkflow: {
24
+ id: 'my-workflow',
25
+ kind: 'workflow',
26
+ systemId: 'sys.operations',
27
+ ownerRoleId: 'role-ops-lead',
28
+ status: 'active',
29
+ capabilityKey: 'operations.my-workflow'
30
+ }
31
+ })
32
+ ```
33
+
34
+ Then expose the descriptor catalog through the Organization Model:
35
+
36
+ ```ts
37
+ export const resourceGovernanceModel = {
38
+ systems: {
39
+ systems
40
+ },
41
+ resources: {
42
+ entries: Object.values(resourceDescriptors)
43
+ }
44
+ } as const
45
+ ```
46
+
47
+ Use `organizationModel.resources.entries` as the Resources descriptor catalog. `links[].nodeId` still uses the kind-prefixed graph grammar, such as `feature:sales.crm`, `integration:instantly`, or `capability:operations.queue.review`, when a runtime resource needs semantic graph binding.
48
+
49
+ ## 2. Author executable behavior
50
+
51
+ Operations code owns schemas, steps, handlers, triggers, and UI execution metadata. Import the descriptor and derive runtime identity from it at the binding boundary:
14
52
 
15
53
  ```ts
16
54
  import type { WorkflowDefinition } from '@elevasis/sdk'
55
+ import { resourceDescriptors } from '@core/config/organization-model'
17
56
 
18
57
  export const myWorkflow: WorkflowDefinition = {
19
58
  config: {
20
- resourceId: 'my-workflow',
59
+ resource: resourceDescriptors.myWorkflow,
60
+ resourceId: resourceDescriptors.myWorkflow.id,
21
61
  name: 'My Workflow',
22
- type: 'workflow',
62
+ type: resourceDescriptors.myWorkflow.kind,
23
63
  version: '1.0.0',
24
64
  status: 'dev',
25
65
  links: [{ nodeId: 'feature:operations', kind: 'operates-on' }],
@@ -46,17 +86,17 @@ export const myWorkflow: WorkflowDefinition = {
46
86
  }
47
87
  ```
48
88
 
49
- `links[].nodeId` uses the kind-prefixed graph grammar, such as `feature:sales.crm`, `integration:instantly`, or `capability:operations.queue.review`.
50
-
51
89
  `category` is one of `production`, `diagnostic`, `internal`, or `testing`.
52
90
 
53
- ## 2. Register in the deployment spec
91
+ ## 3. Register in the deployment spec
54
92
 
55
93
  ```ts
94
+ import { resourceGovernanceModel } from '@core/config/organization-model'
56
95
  import { myWorkflow } from './my-workflow/index.js'
57
96
 
58
97
  export const org = {
59
98
  version: '0.1.0',
99
+ organizationModel: resourceGovernanceModel,
60
100
  workflows: [myWorkflow],
61
101
  agents: []
62
102
  }
@@ -64,7 +104,7 @@ export const org = {
64
104
 
65
105
  Use `.js` extensions in TypeScript source imports for ESM compatibility.
66
106
 
67
- ## 3. Declare runtime relationships
107
+ ## 4. Declare runtime relationships
68
108
 
69
109
  Use `DeploymentSpec.relationships` for execution topology:
70
110
 
@@ -79,7 +119,7 @@ relationships: {
79
119
 
80
120
  Use `config.links` for semantic graph binding and `relationships` for runtime execution relationships.
81
121
 
82
- ## 4. Verify
122
+ ## 5. Verify
83
123
 
84
124
  ```bash
85
125
  pnpm -C operations check
@@ -84,13 +84,15 @@ The canonical transition workflow (see `packages/elevasis-operations/src/sales/c
84
84
  // operations/src/sales/crm/actions/move-to-proposal.ts
85
85
  import type { WorkflowDefinition } from '@elevasis/sdk'
86
86
  import { acqDb } from '@elevasis/sdk/worker'
87
+ import { resourceDescriptors } from '@core/config/organization-model'
87
88
  import { ActionWorkflowInputSchema, ActionWorkflowOutputSchema } from '../shared/action-workflow-schemas.js'
88
89
 
89
90
  export const moveToProposalWorkflow: WorkflowDefinition = {
90
91
  config: {
91
- resourceId: 'move_to_proposal-workflow',
92
+ resource: resourceDescriptors.moveToProposal,
93
+ resourceId: resourceDescriptors.moveToProposal.id,
92
94
  name: 'Move to Proposal',
93
- type: 'workflow',
95
+ type: resourceDescriptors.moveToProposal.kind,
94
96
  version: '1.0.0',
95
97
  status: 'prod',
96
98
  category: 'internal',
@@ -119,7 +121,7 @@ export const moveToProposalWorkflow: WorkflowDefinition = {
119
121
  }
120
122
  ```
121
123
 
122
- To add side effects (create a task, send a Slack message, log a deal activity), extend the handler before the `return`. The `resourceId` must match the action's `workflowId` in `DEFAULT_CRM_ACTIONS` from `@elevasis/sdk` exactly.
124
+ To add side effects (create a task, send a Slack message, log a deal activity), extend the handler before the `return`. The OM descriptor ID must match the action's `workflowId` in `DEFAULT_CRM_ACTIONS` from `@elevasis/sdk` exactly.
123
125
 
124
126
  Register the workflow in the operations manifest:
125
127
 
@@ -232,6 +234,7 @@ export type SendQuoteOutput = z.infer<typeof sendQuoteOutputSchema>
232
234
  // operations/src/sales/send-quote.ts
233
235
  import type { WorkflowDefinition } from '@elevasis/sdk'
234
236
  import { acqDb, createResendAdapter } from '@elevasis/sdk/worker'
237
+ import { resourceDescriptors } from '@core/config/organization-model'
235
238
  import {
236
239
  sendQuoteInputSchema,
237
240
  sendQuoteOutputSchema
@@ -239,9 +242,10 @@ import {
239
242
 
240
243
  export const sendQuoteWorkflow: WorkflowDefinition = {
241
244
  config: {
242
- resourceId: 'send-quote-workflow',
245
+ resource: resourceDescriptors.sendQuote,
246
+ resourceId: resourceDescriptors.sendQuote.id,
243
247
  name: 'Send Quote',
244
- type: 'workflow',
248
+ type: resourceDescriptors.sendQuote.kind,
245
249
  version: '1.0.0',
246
250
  status: 'dev',
247
251
  category: 'internal',
@@ -315,9 +319,11 @@ A custom `ActionDef` entry with `workflowId: 'send-quote-workflow'` can be rende
315
319
  import { Button } from '@mantine/core'
316
320
  import { useMutation } from '@tanstack/react-query'
317
321
  import { useElevasisServices } from '@elevasis/ui/provider'
322
+ import { resourceDescriptors } from '@core/config/organization-model'
318
323
 
319
324
  export function SendQuoteButton({ dealId }: { dealId: string }) {
320
325
  const { apiRequest, organizationId } = useElevasisServices()
326
+ const resourceId = resourceDescriptors.sendQuote.id
321
327
 
322
328
  const sendQuote = useMutation({
323
329
  mutationFn: async () => {
@@ -327,7 +333,7 @@ export function SendQuoteButton({ dealId }: { dealId: string }) {
327
333
  method: 'POST',
328
334
  body: JSON.stringify({
329
335
  resourceType: 'workflow',
330
- resourceId: 'send-quote-workflow',
336
+ resourceId,
331
337
  input: { dealId, organizationId }
332
338
  })
333
339
  })
@@ -78,13 +78,28 @@ Feature field reference:
78
78
 
79
79
  ## Resource Binding
80
80
 
81
- Resources do not live in `OrganizationModel`. Workflows, agents, triggers, integrations, and external resources declare semantic graph links in their resource metadata.
81
+ Resource identity and governance metadata live in `OrganizationModel` under `resources.entries`. Workflows, agents, and integrations import those descriptors and derive runtime `resourceId` / `type` from them while still declaring semantic graph links in resource metadata.
82
82
 
83
83
  ```ts
84
+ // core/config/organization-model.ts
85
+ import { defineResources } from '@elevasis/core/organization-model'
86
+
87
+ export const resourceDescriptors = defineResources({
88
+ leadImport: {
89
+ id: 'lead-import',
90
+ kind: 'workflow',
91
+ systemId: 'sys.prospecting',
92
+ ownerRoleId: 'role-ops-lead',
93
+ status: 'active'
94
+ }
95
+ })
96
+
97
+ // operations/src/lead-import/index.ts
84
98
  config: {
85
- resourceId: 'lead-import',
99
+ resource: resourceDescriptors.leadImport,
100
+ resourceId: resourceDescriptors.leadImport.id,
86
101
  name: 'Lead Import',
87
- type: 'workflow',
102
+ type: resourceDescriptors.leadImport.kind,
88
103
  version: '1.0.0',
89
104
  status: 'prod',
90
105
  links: [{ nodeId: 'feature:sales.lead-gen', kind: 'operates-on' }],
@@ -31,7 +31,7 @@ CRM is a layered platform surface, not one component:
31
31
 
32
32
  | User wants | Start here | Notes |
33
33
  | --- | --- | --- |
34
- | Change CRM feature availability, labels, or pipeline stages | `core/config/organization-model.ts` plus `core/config/organization-model.examples.ts` | Treat this as Organization OS work. Use the project's configure ceremony if available. |
34
+ | Change CRM feature availability, labels, pipeline stages, or resource descriptors | `core/config/organization-model.ts` | Treat this as Organization OS work. Use the project's configure ceremony if available. |
35
35
  | Add CRM sidebar nav or a CRM route | `@elevasis/ui/features/crm` and `node_modules/@elevasis/sdk/reference/scaffold/ui/customization.md` | Prefer manifest/sidebar composition. Do not fork shared source first. |
36
36
  | Wrap a shared CRM page with project chrome | `DealsListPage`, `DealDetailPage`, `CrmOverview` from `@elevasis/ui/features/crm` | Keep route files thin and put project-specific logic in local feature modules. |
37
37
  | Build a custom deal page | `useDealDetail`, `useDealNotes`, `useDealTasks`, `useExecuteAction` from `@elevasis/ui/hooks` | Use hooks for platform data and compose your own UI. |
@@ -164,9 +164,10 @@ Inside deployed workflows, use worker adapters instead of browser hooks or direc
164
164
 
165
165
  ```ts
166
166
  // operations/src/sales/follow-up-stale-deals.ts
167
- import type { WorkflowDefinition } from '@elevasis/sdk'
168
- import { crm } from '@elevasis/sdk/worker'
169
- import { z } from 'zod'
167
+ import type { WorkflowDefinition } from '@elevasis/sdk'
168
+ import { crm } from '@elevasis/sdk/worker'
169
+ import { resourceDescriptors } from '@core/config/organization-model'
170
+ import { z } from 'zod'
170
171
 
171
172
  const inputSchema = z.object({
172
173
  stage: z.string().default('proposal')
@@ -176,14 +177,15 @@ const outputSchema = z.object({
176
177
  touched: z.number()
177
178
  })
178
179
 
179
- export const followUpStaleDealsWorkflow: WorkflowDefinition = {
180
- config: {
181
- resourceId: 'follow-up-stale-deals',
182
- name: 'Follow Up Stale Deals',
183
- type: 'workflow',
184
- version: '1.0.0',
185
- status: 'dev',
186
- links: [{ nodeId: 'feature:sales.crm', kind: 'operates-on' }]
180
+ export const followUpStaleDealsWorkflow: WorkflowDefinition = {
181
+ config: {
182
+ resource: resourceDescriptors.followUpStaleDeals,
183
+ resourceId: resourceDescriptors.followUpStaleDeals.id,
184
+ name: 'Follow Up Stale Deals',
185
+ type: resourceDescriptors.followUpStaleDeals.kind,
186
+ version: '1.0.0',
187
+ status: 'dev',
188
+ links: [{ nodeId: 'feature:sales.crm', kind: 'operates-on' }]
187
189
  },
188
190
  contract: { inputSchema, outputSchema },
189
191
  steps: {
@@ -226,13 +228,9 @@ Use `crm` for focused CRM deal reads, notes, tasks, activity, and cleanup. Use `
226
228
 
227
229
  CRM feature identity remains `sales.crm`, but the organization-model domain is `sales`.
228
230
 
229
- For stage labels or stage sets, start from the project reference file:
230
-
231
- `core/config/organization-model.examples.ts`
232
-
233
- Then update the project model:
234
-
235
- `core/config/organization-model.ts`
231
+ For stage labels or stage sets, update the project model:
232
+
233
+ `core/config/organization-model.ts`
236
234
 
237
235
  Keep these boundaries straight:
238
236
 
@@ -30,31 +30,31 @@ Lead gen is a layered platform surface, not one component:
30
30
 
31
31
  ## Decision Table
32
32
 
33
- | User wants | Start here | Notes |
34
- | --------------------------------------------------------------------------------- | ----------------------------------------------------------------------------------------------------------------------------------------------- | --------------------------------------------------------------------------------------------------------------- |
35
- | Change lead-gen feature availability, labels, quick access, or pipeline semantics | `core/config/organization-model.ts` plus `core/config/organization-model.examples.ts` | Treat this as Organization OS work. Use the project's configure ceremony if available. |
36
- | Add lead-gen sidebar nav or a lead-gen route | `@elevasis/ui/features/lead-gen` and `node_modules/@elevasis/sdk/reference/scaffold/ui/customization.md` | Prefer manifest/sidebar composition. Do not fork shared source first. |
37
- | Wrap a shared lead-gen page with project chrome | `LeadGenOverviewPage`, `LeadGenListsPage`, `LeadGenListDetailPage`, `ListBuilderPage`, `LeadGenCompaniesPage`, `LeadGenContactsPage` | Keep route files thin and put project-specific behavior in local feature modules. |
38
- | Build a custom campaign/list workspace | `ListBuilderPage`, `useLists`, `useList`, `useListProgress`, `useListExecutions`, `useWorkflowExecution`, `useExecutionSSE` from `@elevasis/ui` | Use the shared builder when possible; otherwise compose hooks for platform data and workflow execution. |
39
- | Render artifacts or list-member detail | `LeadGenListDetailPage`, `useArtifacts`, `useCreateArtifact`, `useListMember` | Artifacts are a substrate primitive. Keep vertical-specific rendering local until there are repeated use cases. |
40
- | Read or mutate lead-gen data inside a workflow | `acqDb` or `list` from `@elevasis/sdk/worker` | `organizationId` is injected server-side by the platform dispatcher. Do not pass it from workflow code. |
41
- | Add a new persisted lead-gen field, artifact kind, or transition API | Platform/API migration work, not just scaffold work | Update DB, core schemas/types, API service/handlers, hooks, docs, and scaffold contracts together. |
33
+ | User wants | Start here | Notes |
34
+ | ------------------------------------------------------------------------------------------------------- | ----------------------------------------------------------------------------------------------------------------------------------------------- | --------------------------------------------------------------------------------------------------------------- |
35
+ | Change lead-gen feature availability, labels, quick access, pipeline semantics, or resource descriptors | `core/config/organization-model.ts` | Treat this as Organization OS work. Use the project's configure ceremony if available. |
36
+ | Add lead-gen sidebar nav or a lead-gen route | `@elevasis/ui/features/lead-gen` and `node_modules/@elevasis/sdk/reference/scaffold/ui/customization.md` | Prefer manifest/sidebar composition. Do not fork shared source first. |
37
+ | Wrap a shared lead-gen page with project chrome | `LeadGenOverviewPage`, `LeadGenListsPage`, `LeadGenListDetailPage`, `ListBuilderPage`, `LeadGenCompaniesPage`, `LeadGenContactsPage` | Keep route files thin and put project-specific behavior in local feature modules. |
38
+ | Build a custom campaign/list workspace | `ListBuilderPage`, `useLists`, `useList`, `useListProgress`, `useListExecutions`, `useWorkflowExecution`, `useExecutionSSE` from `@elevasis/ui` | Use the shared builder when possible; otherwise compose hooks for platform data and workflow execution. |
39
+ | Render artifacts or list-member detail | `LeadGenListDetailPage`, `useArtifacts`, `useCreateArtifact`, `useListMember` | Artifacts are a substrate primitive. Keep vertical-specific rendering local until there are repeated use cases. |
40
+ | Read or mutate lead-gen data inside a workflow | `acqDb` or `list` from `@elevasis/sdk/worker` | `organizationId` is injected server-side by the platform dispatcher. Do not pass it from workflow code. |
41
+ | Add a new persisted lead-gen field, artifact kind, or transition API | Platform/API migration work, not just scaffold work | Update DB, core schemas/types, API service/handlers, hooks, docs, and scaffold contracts together. |
42
42
 
43
43
  ## Published Lead-Gen Surfaces
44
44
 
45
- | Surface | Import from | Use for |
46
- | ------------------------------------------------------------------------------------------------------------------------------------------------------------ | -------------------------------- | ------------------------------------------------------------------------------------------- |
47
- | `leadGenManifest`, `LEAD_GEN_ITEMS`, `LeadGenSidebar`, `LeadGenSidebarTop`, `LeadGenSidebarMiddle` | `@elevasis/ui/features/lead-gen` | Feature registration and sidebar composition |
48
- | `LeadGenOverviewPage`, `LeadGenListsPage`, `LeadGenListDetailPage`, `ListBuilderPage`, `LeadGenCompaniesPage`, `LeadGenContactsPage` | `@elevasis/ui/features/lead-gen` | Shared lead-gen pages you can route to or wrap |
49
- | `ListActionsProvider`, `useListActions`, `ListBuilderWorkflow`, `ListBuilderRegistry`, `LeadGenCapabilityKey` | `@elevasis/ui/features/lead-gen` | List Builder workflow registry, slot-based field contracts, and project-owned action wiring |
50
- | `LeadGenRouteShell`, `CompanyDetailModal`, `ContactDetailModal`, `LIST_TEMPLATE_OPTIONS`, `buildListConfig` | `@elevasis/ui/features/lead-gen` | Route shell helpers, detail modals, and list creation config helpers |
51
- | `useLists`, `useList`, `useListsTelemetry`, `useListProgress`, `useListExecutions`, `useCreateList`, `useUpdateList`, `useUpdateListConfig`, `useDeleteList` | `@elevasis/ui/hooks` | Headless list and telemetry data access |
52
- | `useWorkflowExecution`, `useExecutionSSE`, `useAddCompaniesToList`, `useRemoveCompaniesFromList`, `useAddContactsToList` | `@elevasis/ui/hooks` | List Builder workflow triggering, live execution tailing, and list membership mutations |
53
- | `useCompanies`, `useCompany`, `useContacts`, `useContact` | `@elevasis/ui/hooks` | Acquisition company/contact data access |
54
- | `useArtifacts`, `useCreateArtifact`, `useListMembers`, `useListMember` | `@elevasis/ui/hooks` | Lead-gen substrate data access |
55
- | `useTransitionList`, `useTransitionListMember`, `useTransitionListCompany`, `useDeriveActions` | `@elevasis/ui/hooks` | Stateful transition mutations and contextual action derivation |
56
- | `ElevasisUIProvider`, `ElevasisCoreProvider`, `useElevasisServices` | `@elevasis/ui/provider` | Provider setup, API access, organization context, and `listActions` registry injection |
57
- | `acqDb`, `list` | `@elevasis/sdk/worker` | Workflow-side acquisition and list-scoped platform adapters |
45
+ | Surface | Import from | Use for |
46
+ | ------------------------------------------------------------------------------------------------------------------------------------------------------------ | -------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
47
+ | `leadGenManifest`, `LEAD_GEN_ITEMS`, `LeadGenSidebar`, `LeadGenSidebarTop`, `LeadGenSidebarMiddle` | `@elevasis/ui/features/lead-gen` | Feature registration and sidebar composition |
48
+ | `LeadGenOverviewPage`, `LeadGenListsPage`, `LeadGenListDetailPage`, `ListBuilderPage`, `LeadGenCompaniesPage`, `LeadGenContactsPage` | `@elevasis/ui/features/lead-gen` | Shared lead-gen pages you can route to or wrap |
49
+ | `ListActionsProvider`, `useListActions`, `ListBuilderWorkflow`, `ListBuilderRegistry`, `LeadGenCapabilityKey` | `@elevasis/ui/features/lead-gen` | List Builder workflow registry, slot-based field contracts, and project-owned action wiring |
50
+ | `LeadGenRouteShell`, `LIST_TEMPLATE_OPTIONS`, `buildListConfig` | `@elevasis/ui/features/lead-gen` | Route shell helpers and list creation config helpers (contact/company detail surfaces are now `ContactDetailPage` / `CompanyDetailPage` from `@elevasis/ui/features/crm`) |
51
+ | `useLists`, `useList`, `useListsTelemetry`, `useListProgress`, `useListExecutions`, `useCreateList`, `useUpdateList`, `useUpdateListConfig`, `useDeleteList` | `@elevasis/ui/hooks` | Headless list and telemetry data access |
52
+ | `useWorkflowExecution`, `useExecutionSSE`, `useAddCompaniesToList`, `useRemoveCompaniesFromList`, `useAddContactsToList` | `@elevasis/ui/hooks` | List Builder workflow triggering, live execution tailing, and list membership mutations |
53
+ | `useCompanies`, `useCompany`, `useContacts`, `useContact` | `@elevasis/ui/hooks` | Acquisition company/contact data access |
54
+ | `useArtifacts`, `useCreateArtifact`, `useListMembers`, `useListMember` | `@elevasis/ui/hooks` | Lead-gen substrate data access |
55
+ | `useTransitionList`, `useTransitionListMember`, `useTransitionListCompany`, `useDeriveActions` | `@elevasis/ui/hooks` | Stateful transition mutations and contextual action derivation |
56
+ | `ElevasisUIProvider`, `ElevasisCoreProvider`, `useElevasisServices` | `@elevasis/ui/provider` | Provider setup, API access, organization context, and `listActions` registry injection |
57
+ | `acqDb`, `list` | `@elevasis/sdk/worker` | Workflow-side acquisition and list-scoped platform adapters |
58
58
 
59
59
  Read the generated contracts before changing typed boundaries:
60
60
 
@@ -164,6 +164,7 @@ import * as z from 'zod'
164
164
  import { type ListBuilderRegistry } from '@elevasis/ui/features/lead-gen'
165
165
  import type { StepConfigLayout } from '@elevasis/ui/components/forms'
166
166
  import { ElevasisUIProvider } from '@elevasis/ui/provider'
167
+ import { resourceDescriptors } from '@core/config/organization-model'
167
168
 
168
169
  const companyCleanupInputSchema = z.object({
169
170
  listId: z.string().uuid(),
@@ -174,6 +175,7 @@ const companyCleanupInputSchema = z.object({
174
175
  })
175
176
 
176
177
  type CompanyCleanupInput = z.infer<typeof companyCleanupInputSchema>
178
+ const companyCleanupResource = resourceDescriptors.companyCleanup
177
179
 
178
180
  const companyCleanupLayout: StepConfigLayout<CompanyCleanupInput> = {
179
181
  sections: [
@@ -209,8 +211,8 @@ const companyCleanupLayout: StepConfigLayout<CompanyCleanupInput> = {
209
211
 
210
212
  const listActions: ListBuilderRegistry = [
211
213
  {
212
- resourceId: 'lgn-company-cleanup-workflow',
213
- workflowId: 'lgn-company-cleanup-workflow',
214
+ resourceId: companyCleanupResource.id,
215
+ workflowId: companyCleanupResource.id,
214
216
  capabilityKey: 'lead-gen.company.cleanup',
215
217
  label: 'Company Cleanup',
216
218
  description: 'Normalize and clean company records for the list.',
@@ -310,12 +312,14 @@ External projects should define workflow input/output schemas in `@shared/types`
310
312
  import type { WorkflowDefinition } from '@elevasis/sdk'
311
313
  import { acqDb, list } from '@elevasis/sdk/worker'
312
314
  import { qualifyListInputSchema, qualifyListOutputSchema } from '@shared/types'
315
+ import { resourceDescriptors } from '@core/config/organization-model'
313
316
 
314
317
  export const qualifyListWorkflow: WorkflowDefinition = {
315
318
  config: {
316
- resourceId: 'qualify-list',
319
+ resource: resourceDescriptors.qualifyList,
320
+ resourceId: resourceDescriptors.qualifyList.id,
317
321
  name: 'Qualify List',
318
- type: 'workflow',
322
+ type: resourceDescriptors.qualifyList.kind,
319
323
  version: '1.0.0',
320
324
  status: 'dev',
321
325
  links: [{ nodeId: 'feature:sales.lead-gen', kind: 'operates-on' }]
@@ -368,11 +372,7 @@ Keep these boundaries straight:
368
372
 
369
373
  The lead-gen shell feature key is `lead-gen`, the Organization OS feature id is `sales.lead-gen`, and the capability currently used by the shared manifest is `leadgen.lists.manage`.
370
374
 
371
- For feature toggles, labels, or lifecycle semantics, start from the project reference file:
372
-
373
- `core/config/organization-model.examples.ts`
374
-
375
- Then update the project model:
375
+ For feature toggles, labels, lifecycle semantics, or resource descriptors, update the project model:
376
376
 
377
377
  `core/config/organization-model.ts`
378
378
 
@@ -20,7 +20,7 @@ Before starting, read [glossary.md](../reference/glossary.md) to disambiguate ov
20
20
  You want a new shell feature (e.g., `analytics`) with its own nav entry, sidebar, routes, and org-model gate. Covers adding a feature object to the org model, `FeatureModule` manifest authoring, route creation, and gating.
21
21
 
22
22
  **[Add a Resource](add-a-resource.md)**
23
- You want a new workflow or agent deployed to the platform. Covers `WorkflowDefinition` authoring, `DeploymentSpec` registration, relationship declarations, domain mapping, and CLI verification.
23
+ You want a new workflow or agent deployed to the platform. Covers OM Resource descriptor authoring, descriptor-backed `WorkflowDefinition` binding, `DeploymentSpec` assembly, relationship declarations, and CLI verification.
24
24
 
25
25
  **[Gate by Feature or Admin](gate-by-feature-or-admin.md)**
26
26
  You want to restrict a route, nav item, or UI element by feature flag or admin role. Covers the decision table, `FeatureGuard`, `AdminGuard`, nav-entry visibility fields, per-member `MembershipFeatureConfig` overrides, and the settings-asymmetry gotcha.