@elevasis/core 0.22.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.
Files changed (112) hide show
  1. package/dist/index.d.ts +2330 -2391
  2. package/dist/index.js +2322 -1147
  3. package/dist/knowledge/index.d.ts +702 -1136
  4. package/dist/knowledge/index.js +9 -9
  5. package/dist/organization-model/index.d.ts +2330 -2391
  6. package/dist/organization-model/index.js +2322 -1147
  7. package/dist/test-utils/index.d.ts +703 -1106
  8. package/dist/test-utils/index.js +1735 -1089
  9. package/package.json +1 -1
  10. package/src/__tests__/template-core-compatibility.test.ts +11 -79
  11. package/src/_gen/__tests__/__snapshots__/contracts.md.snap +360 -98
  12. package/src/business/acquisition/api-schemas.test.ts +2 -2
  13. package/src/business/acquisition/api-schemas.ts +7 -9
  14. package/src/business/acquisition/build-templates.test.ts +4 -4
  15. package/src/business/acquisition/build-templates.ts +72 -30
  16. package/src/business/acquisition/crm-state-actions.test.ts +13 -11
  17. package/src/business/acquisition/types.ts +7 -3
  18. package/src/execution/engine/agent/core/types.ts +1 -1
  19. package/src/execution/engine/workflow/types.ts +2 -2
  20. package/src/knowledge/README.md +8 -7
  21. package/src/knowledge/__tests__/queries.test.ts +74 -73
  22. package/src/knowledge/format.ts +10 -9
  23. package/src/knowledge/index.ts +1 -1
  24. package/src/knowledge/published.ts +1 -1
  25. package/src/knowledge/queries.ts +26 -25
  26. package/src/organization-model/README.md +66 -26
  27. package/src/organization-model/__tests__/content-kinds-registry.test.ts +210 -0
  28. package/src/organization-model/__tests__/defaults.test.ts +72 -98
  29. package/src/organization-model/__tests__/domains/actions.test.ts +56 -0
  30. package/src/organization-model/__tests__/domains/customers.test.ts +299 -295
  31. package/src/organization-model/__tests__/domains/entities.test.ts +56 -0
  32. package/src/organization-model/__tests__/domains/goals.test.ts +493 -479
  33. package/src/organization-model/__tests__/domains/identity.test.ts +280 -279
  34. package/src/organization-model/__tests__/domains/navigation.test.ts +268 -212
  35. package/src/organization-model/__tests__/domains/offerings.test.ts +414 -419
  36. package/src/organization-model/__tests__/domains/policies.test.ts +323 -0
  37. package/src/organization-model/__tests__/domains/resource-mappings.test.ts +271 -271
  38. package/src/organization-model/__tests__/domains/resources.test.ts +159 -37
  39. package/src/organization-model/__tests__/domains/roles.test.ts +147 -86
  40. package/src/organization-model/__tests__/domains/statuses.test.ts +246 -243
  41. package/src/organization-model/__tests__/domains/systems.test.ts +67 -51
  42. package/src/organization-model/__tests__/flatten-additive-merge.test.ts +361 -0
  43. package/src/organization-model/__tests__/foundation.test.ts +74 -102
  44. package/src/organization-model/__tests__/get-resources-for-system.test.ts +144 -0
  45. package/src/organization-model/__tests__/graph.test.ts +899 -71
  46. package/src/organization-model/__tests__/knowledge.test.ts +173 -52
  47. package/src/organization-model/__tests__/lookup-helpers.test.ts +438 -0
  48. package/src/organization-model/__tests__/migration-helpers.test.ts +591 -0
  49. package/src/organization-model/__tests__/prospecting-ssot.test.ts +36 -27
  50. package/src/organization-model/__tests__/recursive-system-schema.test.ts +520 -0
  51. package/src/organization-model/__tests__/resolve.test.ts +174 -23
  52. package/src/organization-model/__tests__/schema.test.ts +291 -114
  53. package/src/organization-model/__tests__/surface-projection.test.ts +207 -97
  54. package/src/organization-model/catalogs/lead-gen.ts +144 -0
  55. package/src/organization-model/content-kinds/config.ts +36 -0
  56. package/src/organization-model/content-kinds/index.ts +74 -0
  57. package/src/organization-model/content-kinds/pipeline.ts +68 -0
  58. package/src/organization-model/content-kinds/registry.ts +44 -0
  59. package/src/organization-model/content-kinds/status.ts +71 -0
  60. package/src/organization-model/content-kinds/template.ts +83 -0
  61. package/src/organization-model/content-kinds/types.ts +117 -0
  62. package/src/organization-model/contracts.ts +13 -3
  63. package/src/organization-model/defaults.ts +488 -96
  64. package/src/organization-model/domains/actions.ts +239 -0
  65. package/src/organization-model/domains/customers.ts +78 -75
  66. package/src/organization-model/domains/entities.ts +144 -0
  67. package/src/organization-model/domains/goals.ts +83 -80
  68. package/src/organization-model/domains/knowledge.ts +74 -16
  69. package/src/organization-model/domains/navigation.ts +107 -384
  70. package/src/organization-model/domains/offerings.ts +71 -66
  71. package/src/organization-model/domains/policies.ts +102 -0
  72. package/src/organization-model/domains/projects.ts +14 -48
  73. package/src/organization-model/domains/prospecting.ts +62 -181
  74. package/src/organization-model/domains/resources.ts +81 -24
  75. package/src/organization-model/domains/roles.ts +13 -10
  76. package/src/organization-model/domains/sales.ts +10 -219
  77. package/src/organization-model/domains/shared.ts +57 -57
  78. package/src/organization-model/domains/statuses.ts +339 -130
  79. package/src/organization-model/domains/systems.ts +186 -29
  80. package/src/organization-model/foundation.ts +54 -67
  81. package/src/organization-model/graph/build.ts +682 -54
  82. package/src/organization-model/graph/link.ts +1 -1
  83. package/src/organization-model/graph/schema.ts +24 -9
  84. package/src/organization-model/graph/types.ts +20 -7
  85. package/src/organization-model/helpers.ts +231 -26
  86. package/src/organization-model/index.ts +116 -5
  87. package/src/organization-model/migration-helpers.ts +249 -0
  88. package/src/organization-model/organization-graph.mdx +16 -15
  89. package/src/organization-model/organization-model.mdx +89 -41
  90. package/src/organization-model/published.ts +120 -18
  91. package/src/organization-model/resolve.ts +117 -54
  92. package/src/organization-model/schema.ts +561 -140
  93. package/src/organization-model/surface-projection.ts +116 -122
  94. package/src/organization-model/types.ts +102 -21
  95. package/src/platform/constants/versions.ts +1 -1
  96. package/src/platform/registry/__tests__/command-view.test.ts +6 -8
  97. package/src/platform/registry/__tests__/resource-link.test.ts +13 -8
  98. package/src/platform/registry/__tests__/resource-registry.integration.test.ts +16 -31
  99. package/src/platform/registry/__tests__/resource-registry.nested-systems.test.ts +245 -0
  100. package/src/platform/registry/__tests__/resource-registry.test.ts +9 -7
  101. package/src/platform/registry/__tests__/validation.test.ts +15 -11
  102. package/src/platform/registry/resource-registry.ts +20 -8
  103. package/src/platform/registry/serialization.ts +7 -7
  104. package/src/platform/registry/types.ts +3 -3
  105. package/src/platform/registry/validation.ts +17 -15
  106. package/src/reference/_generated/contracts.md +362 -99
  107. package/src/reference/glossary.md +18 -18
  108. package/src/supabase/database.types.ts +60 -0
  109. package/src/test-utils/test-utils.test.ts +1 -6
  110. package/src/organization-model/__tests__/domains/operations.test.ts +0 -203
  111. package/src/organization-model/domains/features.ts +0 -31
  112. package/src/organization-model/domains/operations.ts +0 -85
@@ -0,0 +1,102 @@
1
+ import { z } from 'zod'
2
+ import { DescriptionSchema, LabelSchema, ModelIdSchema } from './shared'
3
+ import { EventIdSchema } from './resources'
4
+
5
+ export const PolicyIdSchema = ModelIdSchema
6
+
7
+ export const PolicyApplicabilitySchema = z.object({
8
+ systemIds: z.array(ModelIdSchema.meta({ ref: 'system' })).default([]),
9
+ actionIds: z.array(ModelIdSchema.meta({ ref: 'action' })).default([]),
10
+ resourceIds: z.array(ModelIdSchema.meta({ ref: 'resource' })).default([]),
11
+ roleIds: z.array(ModelIdSchema.meta({ ref: 'role' })).default([])
12
+ })
13
+
14
+ export const PolicyTriggerSchema = z.discriminatedUnion('kind', [
15
+ z.object({
16
+ kind: z.literal('event'),
17
+ eventId: EventIdSchema.meta({ ref: 'event' })
18
+ }),
19
+ z.object({
20
+ kind: z.literal('action-invocation'),
21
+ actionId: ModelIdSchema.meta({ ref: 'action' })
22
+ }),
23
+ z.object({
24
+ kind: z.literal('schedule'),
25
+ cron: z.string().trim().min(1).max(120)
26
+ }),
27
+ z.object({
28
+ kind: z.literal('manual')
29
+ })
30
+ ])
31
+
32
+ export const PolicyPredicateSchema = z.discriminatedUnion('kind', [
33
+ z.object({
34
+ kind: z.literal('always')
35
+ }),
36
+ z.object({
37
+ kind: z.literal('expression'),
38
+ expression: z.string().trim().min(1).max(2000)
39
+ }),
40
+ z.object({
41
+ kind: z.literal('threshold'),
42
+ metric: ModelIdSchema,
43
+ operator: z.enum(['lt', 'lte', 'eq', 'gte', 'gt']).meta({ label: 'Operator' }),
44
+ value: z.number()
45
+ })
46
+ ])
47
+
48
+ export const PolicyEffectSchema = z.discriminatedUnion('kind', [
49
+ z.object({
50
+ kind: z.literal('require-approval'),
51
+ roleId: ModelIdSchema.meta({ ref: 'role' }).optional()
52
+ }),
53
+ z.object({
54
+ kind: z.literal('invoke-action'),
55
+ actionId: ModelIdSchema.meta({ ref: 'action' })
56
+ }),
57
+ z.object({
58
+ kind: z.literal('notify-role'),
59
+ roleId: ModelIdSchema.meta({ ref: 'role' })
60
+ }),
61
+ z.object({
62
+ kind: z.literal('block')
63
+ })
64
+ ])
65
+
66
+ export const PolicySchema = z.object({
67
+ id: PolicyIdSchema,
68
+ /** Domain-map iteration order. Convention: multiples of 10 (10, 20, 30, ...) to allow easy insertion. */
69
+ order: z.number(),
70
+ label: LabelSchema,
71
+ description: DescriptionSchema.optional(),
72
+ trigger: PolicyTriggerSchema,
73
+ predicate: PolicyPredicateSchema.default({ kind: 'always' }),
74
+ actions: z.array(PolicyEffectSchema).min(1),
75
+ appliesTo: PolicyApplicabilitySchema.default({
76
+ systemIds: [],
77
+ actionIds: [],
78
+ resourceIds: [],
79
+ roleIds: []
80
+ }),
81
+ lifecycle: z
82
+ .enum(['draft', 'beta', 'active', 'deprecated', 'archived'])
83
+ .meta({ label: 'Lifecycle', color: 'teal' })
84
+ .default('active')
85
+ })
86
+
87
+ export const PoliciesDomainSchema = z
88
+ .record(z.string(), PolicySchema)
89
+ .refine((record) => Object.entries(record).every(([key, entry]) => entry.id === key), {
90
+ message: 'Each policy entry id must match its map key'
91
+ })
92
+ .default({})
93
+
94
+ export const DEFAULT_ORGANIZATION_MODEL_POLICIES: z.infer<typeof PoliciesDomainSchema> = {}
95
+
96
+ export type PolicyId = z.infer<typeof PolicyIdSchema>
97
+ export type PolicyApplicability = z.infer<typeof PolicyApplicabilitySchema>
98
+ export type PolicyTrigger = z.infer<typeof PolicyTriggerSchema>
99
+ export type PolicyPredicate = z.infer<typeof PolicyPredicateSchema>
100
+ export type PolicyEffect = z.infer<typeof PolicyEffectSchema>
101
+ export type Policy = z.infer<typeof PolicySchema>
102
+ export type PoliciesDomain = z.infer<typeof PoliciesDomainSchema>
@@ -1,48 +1,14 @@
1
- import { z } from 'zod'
2
- import { DisplayMetadataSchema, ModelIdSchema } from './shared'
3
-
4
- export const ProjectsDomainStateSchema = DisplayMetadataSchema.extend({
5
- id: ModelIdSchema,
6
- order: z.number().int().min(0)
7
- })
8
-
9
- export const OrganizationModelProjectsSchema = z.object({
10
- projectEntityId: ModelIdSchema,
11
- milestoneEntityId: ModelIdSchema,
12
- taskEntityId: ModelIdSchema,
13
- projectStatuses: z.array(ProjectsDomainStateSchema).min(1),
14
- milestoneStatuses: z.array(ProjectsDomainStateSchema).min(1),
15
- taskStatuses: z.array(ProjectsDomainStateSchema).min(1)
16
- })
17
-
18
- export const DEFAULT_ORGANIZATION_MODEL_PROJECTS: z.infer<typeof OrganizationModelProjectsSchema> = {
19
- projectEntityId: 'delivery.project',
20
- milestoneEntityId: 'delivery.milestone',
21
- taskEntityId: 'delivery.task',
22
- projectStatuses: [
23
- { id: 'active', label: 'Active', order: 1 },
24
- { id: 'on_track', label: 'On Track', order: 2 },
25
- { id: 'at_risk', label: 'At Risk', order: 3 },
26
- { id: 'blocked', label: 'Blocked', order: 4 },
27
- { id: 'paused', label: 'Paused', order: 5 },
28
- { id: 'completed', label: 'Completed', order: 6 }
29
- ],
30
- milestoneStatuses: [
31
- { id: 'upcoming', label: 'Upcoming', order: 1 },
32
- { id: 'in_progress', label: 'In Progress', order: 2 },
33
- { id: 'blocked', label: 'Blocked', order: 3 },
34
- { id: 'overdue', label: 'Overdue', order: 4 },
35
- { id: 'completed', label: 'Completed', order: 5 }
36
- ],
37
- taskStatuses: [
38
- { id: 'planned', label: 'Planned', order: 1 },
39
- { id: 'in_progress', label: 'In Progress', order: 2 },
40
- { id: 'blocked', label: 'Blocked', order: 3 },
41
- { id: 'submitted', label: 'Submitted', order: 4 },
42
- { id: 'approved', label: 'Approved', order: 5 },
43
- { id: 'revision_requested', label: 'Revision Requested', order: 6 },
44
- { id: 'rejected', label: 'Rejected', order: 7 },
45
- { id: 'cancelled', label: 'Cancelled', order: 8 },
46
- { id: 'completed', label: 'Completed', order: 9 }
47
- ]
48
- }
1
+ import { z } from 'zod'
2
+ import { DisplayMetadataSchema, ModelIdSchema } from './shared'
3
+
4
+ export const ProjectsDomainStateSchema = DisplayMetadataSchema.extend({
5
+ id: ModelIdSchema,
6
+ order: z.number().int().min(0)
7
+ })
8
+
9
+ // Phase 4 cut: OrganizationModelProjectsSchema and DEFAULT_ORGANIZATION_MODEL_PROJECTS removed.
10
+ // Project/milestone/task status data moved into system.content as (schema:status-flow) and
11
+ // (schema:status) content nodes on the owning system. Use getAllProjectStatuses() from
12
+ // migration-helpers to read status data portably.
13
+ //
14
+ // ProjectsDomainStateSchema is retained as the payload shape type for individual status entries.
@@ -1,6 +1,6 @@
1
1
  import { z } from 'zod'
2
- import { LEAD_GEN_STAGE_CATALOG, type LeadGenStageCatalogEntry } from './sales'
3
- import { DescriptionSchema, DisplayMetadataSchema, ModelIdSchema } from './shared'
2
+ import { findOrganizationActionById, LEAD_GEN_ACTION_ENTRIES, type Action as TopLevelAction } from './actions'
3
+ import { DisplayMetadataSchema, ModelIdSchema } from './shared'
4
4
 
5
5
  export const ProspectingLifecycleStageSchema = DisplayMetadataSchema.extend({
6
6
  id: ModelIdSchema,
@@ -46,7 +46,7 @@ export const ProspectingBuildTemplateStepSchema = DisplayMetadataSchema.extend({
46
46
  recordSourceStageKey: ModelIdSchema.optional(),
47
47
  dependsOn: z.array(ModelIdSchema).optional(),
48
48
  dependencyMode: z.literal('per-record-eligibility'),
49
- capabilityKey: ModelIdSchema,
49
+ actionKey: ModelIdSchema,
50
50
  defaultBatchSize: z.number().int().positive(),
51
51
  maxBatchSize: z.number().int().positive(),
52
52
  recordColumns: RecordColumnsConfigSchema.optional(),
@@ -91,8 +91,18 @@ const DTC_RECORD_COLUMNS = {
91
91
  { key: 'domain', label: 'Domain', path: 'company.domain' },
92
92
  { key: 'description', label: 'Description', path: 'company.enrichmentData.websiteCrawl.companyDescription' },
93
93
  { key: 'services', label: 'Services', path: 'company.enrichmentData.websiteCrawl.services', renderType: 'json' },
94
- { key: 'automation-gaps', label: 'Automation gaps', path: 'company.enrichmentData.websiteCrawl.automationGaps', renderType: 'json' },
95
- { key: 'contact-count', label: 'Contacts', path: 'company.enrichmentData.websiteCrawl.emailCount', renderType: 'count' }
94
+ {
95
+ key: 'automation-gaps',
96
+ label: 'Automation gaps',
97
+ path: 'company.enrichmentData.websiteCrawl.automationGaps',
98
+ renderType: 'json'
99
+ },
100
+ {
101
+ key: 'contact-count',
102
+ label: 'Contacts',
103
+ path: 'company.enrichmentData.websiteCrawl.emailCount',
104
+ renderType: 'count'
105
+ }
96
106
  ]
97
107
  },
98
108
  qualified: {
@@ -101,7 +111,11 @@ const DTC_RECORD_COLUMNS = {
101
111
  { key: 'domain', label: 'Domain', path: 'company.domain' },
102
112
  { key: 'score', label: 'Score', path: 'company.qualificationScore', renderType: 'badge', badgeColor: 'green' },
103
113
  { key: 'signals', label: 'Signals', path: 'company.qualificationSignals', renderType: 'json' },
104
- { key: 'disqualified-reason', label: 'Disqualified reason', path: 'processingState.qualified.data.disqualifiedReason' }
114
+ {
115
+ key: 'disqualified-reason',
116
+ label: 'Disqualified reason',
117
+ path: 'processingState.qualified.data.disqualifiedReason'
118
+ }
105
119
  ]
106
120
  },
107
121
  decisionMakers: {
@@ -110,114 +124,41 @@ const DTC_RECORD_COLUMNS = {
110
124
  { key: 'title', label: 'Title', path: 'contact.title' },
111
125
  { key: 'email', label: 'Email', path: 'contact.email' },
112
126
  { key: 'linkedin', label: 'LinkedIn', path: 'contact.linkedinUrl' },
113
- { key: 'priority-score', label: 'Priority', path: 'contact.enrichmentData.apollo.priorityScore', renderType: 'badge' }
127
+ {
128
+ key: 'priority-score',
129
+ label: 'Priority',
130
+ path: 'contact.enrichmentData.apollo.priorityScore',
131
+ renderType: 'badge'
132
+ }
114
133
  ]
115
134
  },
116
135
  uploaded: {
117
136
  company: [
118
137
  { key: 'name', label: 'Company', path: 'company.name' },
119
138
  { key: 'domain', label: 'Domain', path: 'company.domain' },
120
- { key: 'contacts', label: 'Contacts', path: 'company.enrichmentData.approvedLeadListExport.contacts', renderType: 'json' },
139
+ {
140
+ key: 'contacts',
141
+ label: 'Contacts',
142
+ path: 'company.enrichmentData.approvedLeadListExport.contacts',
143
+ renderType: 'json'
144
+ },
121
145
  { key: 'score', label: 'Score', path: 'company.qualificationScore', renderType: 'badge', badgeColor: 'green' },
122
- { key: 'approval', label: 'Approval', path: 'company.enrichmentData.approvedLeadListExport.approvalStatus', renderType: 'badge' }
146
+ {
147
+ key: 'approval',
148
+ label: 'Approval',
149
+ path: 'company.enrichmentData.approvedLeadListExport.approvalStatus',
150
+ renderType: 'badge'
151
+ }
123
152
  ]
124
153
  }
125
154
  } as const satisfies Record<string, z.infer<typeof RecordColumnsConfigSchema>>
126
155
 
127
- export const CapabilitySchema = z.object({
128
- id: ModelIdSchema,
129
- label: z.string(),
130
- description: z.string(),
131
- resourceId: ModelIdSchema
132
- })
156
+ export type ActionRegistry = TopLevelAction[]
133
157
 
134
- export type Capability = z.infer<typeof CapabilitySchema>
135
- export type CapabilityRegistry = Capability[]
136
-
137
- export const CAPABILITY_REGISTRY: CapabilityRegistry = [
138
- {
139
- id: 'lead-gen.company.source',
140
- label: 'Source companies',
141
- description: 'Import source companies from a list provider.',
142
- resourceId: 'lgn-import-workflow'
143
- },
144
- {
145
- id: 'lead-gen.company.apollo-import',
146
- label: 'Import from Apollo',
147
- description: 'Pull companies and seed contact data from an Apollo search or list.',
148
- resourceId: 'lgn-01c-apollo-import-workflow'
149
- },
150
- {
151
- id: 'lead-gen.contact.discover',
152
- label: 'Discover contact emails',
153
- description: 'Find email addresses for contacts at qualified companies.',
154
- resourceId: 'lgn-04-email-discovery-workflow'
155
- },
156
- {
157
- id: 'lead-gen.contact.verify-email',
158
- label: 'Verify emails',
159
- description: 'Check email deliverability before outreach.',
160
- resourceId: 'lgn-05-email-verification-workflow'
161
- },
162
- {
163
- id: 'lead-gen.company.apify-crawl',
164
- label: 'Crawl websites',
165
- description:
166
- 'Crawl company websites via Apify and store raw page markdown in enrichmentData.websiteCrawl.pages for downstream LLM analysis.',
167
- resourceId: 'lgn-02a-apify-website-crawl-workflow'
168
- },
169
- {
170
- id: 'lead-gen.company.website-extract',
171
- label: 'Extract website signals',
172
- description: 'Scrape and analyze company websites for qualification signals.',
173
- resourceId: 'lgn-02-website-extract-workflow'
174
- },
175
- {
176
- id: 'lead-gen.company.qualify',
177
- label: 'Qualify companies',
178
- description: 'Score and filter companies against the ICP rubric.',
179
- resourceId: 'lgn-03-company-qualification-workflow'
180
- },
181
- {
182
- id: 'lead-gen.company.dtc-subscription-qualify',
183
- label: 'Qualify DTC subscription fit',
184
- description: 'Classify subscription potential and consumable-product fit for DTC brands.',
185
- resourceId: 'lgn-03b-dtc-subscription-score-workflow'
186
- },
187
- {
188
- id: 'lead-gen.contact.apollo-decision-maker-enrich',
189
- label: 'Enrich decision-makers',
190
- description: 'Find and enrich qualified contacts at qualified companies via Apollo.',
191
- resourceId: 'lgn-04b-apollo-decision-maker-enrich-workflow'
192
- },
193
- {
194
- id: 'lead-gen.contact.personalize',
195
- label: 'Personalize outreach',
196
- description: 'Generate personalized opening lines for each contact.',
197
- resourceId: 'ist-personalization-workflow'
198
- },
199
- {
200
- id: 'lead-gen.review.outreach-ready',
201
- label: 'Upload to outreach',
202
- description: 'Upload approved contacts to the outreach sequence after QC review.',
203
- resourceId: 'ist-upload-contacts-workflow'
204
- },
205
- {
206
- id: 'lead-gen.export.list',
207
- label: 'Export lead list',
208
- description: 'Export approved leads as a downloadable lead list.',
209
- resourceId: 'lgn-06-export-list-workflow'
210
- },
211
- {
212
- id: 'lead-gen.company.cleanup',
213
- label: 'Clean up companies',
214
- description: 'Remove disqualified or duplicate companies from the list.',
215
- resourceId: 'lgn-company-cleanup-workflow'
216
- }
217
- ]
158
+ export const ACTION_REGISTRY: ActionRegistry = Object.values(LEAD_GEN_ACTION_ENTRIES)
218
159
 
219
- export function findCapabilityById(id: string): Capability | undefined {
220
- return CAPABILITY_REGISTRY.find((c) => c.id === id)
160
+ export function findActionById(id: string): TopLevelAction | undefined {
161
+ return findOrganizationActionById(id)
221
162
  }
222
163
 
223
164
  export const PROSPECTING_STEPS = {
@@ -229,7 +170,7 @@ export const PROSPECTING_STEPS = {
229
170
  outputs: ['company'],
230
171
  stageKey: 'populated',
231
172
  dependencyMode: 'per-record-eligibility',
232
- capabilityKey: 'lead-gen.company.source',
173
+ actionKey: 'lead-gen.company.source',
233
174
  defaultBatchSize: 100,
234
175
  maxBatchSize: 250
235
176
  },
@@ -241,7 +182,7 @@ export const PROSPECTING_STEPS = {
241
182
  stageKey: 'extracted',
242
183
  dependsOn: ['source-companies'],
243
184
  dependencyMode: 'per-record-eligibility',
244
- capabilityKey: 'lead-gen.company.website-extract',
185
+ actionKey: 'lead-gen.company.website-extract',
245
186
  defaultBatchSize: 50,
246
187
  maxBatchSize: 100
247
188
  },
@@ -253,7 +194,7 @@ export const PROSPECTING_STEPS = {
253
194
  stageKey: 'qualified',
254
195
  dependsOn: ['analyze-websites'],
255
196
  dependencyMode: 'per-record-eligibility',
256
- capabilityKey: 'lead-gen.company.qualify',
197
+ actionKey: 'lead-gen.company.qualify',
257
198
  defaultBatchSize: 100,
258
199
  maxBatchSize: 250
259
200
  },
@@ -265,7 +206,7 @@ export const PROSPECTING_STEPS = {
265
206
  stageKey: 'discovered',
266
207
  dependsOn: ['qualify-companies'],
267
208
  dependencyMode: 'per-record-eligibility',
268
- capabilityKey: 'lead-gen.contact.discover',
209
+ actionKey: 'lead-gen.contact.discover',
269
210
  defaultBatchSize: 50,
270
211
  maxBatchSize: 100
271
212
  },
@@ -277,7 +218,7 @@ export const PROSPECTING_STEPS = {
277
218
  stageKey: 'verified',
278
219
  dependsOn: ['find-contacts'],
279
220
  dependencyMode: 'per-record-eligibility',
280
- capabilityKey: 'lead-gen.contact.verify-email',
221
+ actionKey: 'lead-gen.contact.verify-email',
281
222
  defaultBatchSize: 100,
282
223
  maxBatchSize: 500
283
224
  },
@@ -289,7 +230,7 @@ export const PROSPECTING_STEPS = {
289
230
  stageKey: 'personalized',
290
231
  dependsOn: ['verify-emails'],
291
232
  dependencyMode: 'per-record-eligibility',
292
- capabilityKey: 'lead-gen.contact.personalize',
233
+ actionKey: 'lead-gen.contact.personalize',
293
234
  defaultBatchSize: 25,
294
235
  maxBatchSize: 100
295
236
  },
@@ -301,7 +242,7 @@ export const PROSPECTING_STEPS = {
301
242
  stageKey: 'uploaded',
302
243
  dependsOn: ['personalize'],
303
244
  dependencyMode: 'per-record-eligibility',
304
- capabilityKey: 'lead-gen.review.outreach-ready',
245
+ actionKey: 'lead-gen.review.outreach-ready',
305
246
  defaultBatchSize: 25,
306
247
  maxBatchSize: 100
307
248
  }
@@ -315,7 +256,7 @@ export const PROSPECTING_STEPS = {
315
256
  outputs: ['company', 'contact'],
316
257
  stageKey: 'populated',
317
258
  dependencyMode: 'per-record-eligibility',
318
- capabilityKey: 'lead-gen.company.apollo-import',
259
+ actionKey: 'lead-gen.company.apollo-import',
319
260
  defaultBatchSize: 250,
320
261
  maxBatchSize: 1000,
321
262
  recordColumns: DTC_RECORD_COLUMNS.populated,
@@ -341,7 +282,7 @@ export const PROSPECTING_STEPS = {
341
282
  stageKey: 'crawled',
342
283
  dependsOn: ['import-apollo-search'],
343
284
  dependencyMode: 'per-record-eligibility',
344
- capabilityKey: 'lead-gen.company.apify-crawl',
285
+ actionKey: 'lead-gen.company.apify-crawl',
345
286
  defaultBatchSize: 50,
346
287
  maxBatchSize: 100,
347
288
  recordColumns: DTC_RECORD_COLUMNS.crawled,
@@ -367,7 +308,7 @@ export const PROSPECTING_STEPS = {
367
308
  stageKey: 'extracted',
368
309
  dependsOn: ['apify-crawl'],
369
310
  dependencyMode: 'per-record-eligibility',
370
- capabilityKey: 'lead-gen.company.website-extract',
311
+ actionKey: 'lead-gen.company.website-extract',
371
312
  defaultBatchSize: 50,
372
313
  maxBatchSize: 100,
373
314
  recordColumns: DTC_RECORD_COLUMNS.extracted
@@ -381,7 +322,7 @@ export const PROSPECTING_STEPS = {
381
322
  stageKey: 'qualified',
382
323
  dependsOn: ['analyze-websites'],
383
324
  dependencyMode: 'per-record-eligibility',
384
- capabilityKey: 'lead-gen.company.dtc-subscription-qualify',
325
+ actionKey: 'lead-gen.company.dtc-subscription-qualify',
385
326
  defaultBatchSize: 100,
386
327
  maxBatchSize: 250,
387
328
  recordColumns: DTC_RECORD_COLUMNS.qualified
@@ -397,7 +338,7 @@ export const PROSPECTING_STEPS = {
397
338
  recordEntity: 'contact',
398
339
  dependsOn: ['score-dtc-fit'],
399
340
  dependencyMode: 'per-record-eligibility',
400
- capabilityKey: 'lead-gen.contact.apollo-decision-maker-enrich',
341
+ actionKey: 'lead-gen.contact.apollo-decision-maker-enrich',
401
342
  defaultBatchSize: 100,
402
343
  maxBatchSize: 250,
403
344
  recordColumns: DTC_RECORD_COLUMNS.decisionMakers,
@@ -425,7 +366,7 @@ export const PROSPECTING_STEPS = {
425
366
  recordSourceStageKey: 'qualified',
426
367
  dependsOn: ['enrich-decision-makers'],
427
368
  dependencyMode: 'per-record-eligibility',
428
- capabilityKey: 'lead-gen.export.list',
369
+ actionKey: 'lead-gen.export.list',
429
370
  defaultBatchSize: 100,
430
371
  maxBatchSize: 250,
431
372
  recordColumns: DTC_RECORD_COLUMNS.uploaded,
@@ -445,70 +386,10 @@ export const PROSPECTING_STEPS = {
445
386
  }
446
387
  } as const satisfies Record<TemplateName, Record<StepName, ListBuilderStep>>
447
388
 
448
- export const OrganizationModelProspectingSchema = z.object({
449
- listEntityId: ModelIdSchema,
450
- companyEntityId: ModelIdSchema,
451
- contactEntityId: ModelIdSchema,
452
- description: DescriptionSchema.optional(),
453
- companyStages: z.array(ProspectingLifecycleStageSchema).min(1),
454
- contactStages: z.array(ProspectingLifecycleStageSchema).min(1),
455
- defaultBuildTemplateId: ModelIdSchema,
456
- buildTemplates: z.array(ProspectingBuildTemplateSchema).min(1)
457
- })
458
-
459
- function toProspectingLifecycleStage(stage: LeadGenStageCatalogEntry): z.infer<typeof ProspectingLifecycleStageSchema> {
460
- return {
461
- id: stage.key,
462
- label: stage.label,
463
- order: stage.order
464
- }
465
- }
466
-
467
- function leadGenStagesForEntity(
468
- entity: LeadGenStageCatalogEntry['entity']
469
- ): z.infer<typeof ProspectingLifecycleStageSchema>[] {
470
- return Object.values(LEAD_GEN_STAGE_CATALOG)
471
- .filter((stage) => stage.entity === entity || stage.additionalEntities?.includes(entity))
472
- .sort((a, b) => a.order - b.order)
473
- .map(toProspectingLifecycleStage)
474
- }
475
-
476
- export const DEFAULT_ORGANIZATION_MODEL_PROSPECTING: z.infer<typeof OrganizationModelProspectingSchema> = {
477
- listEntityId: 'leadgen.list',
478
- companyEntityId: 'leadgen.company',
479
- contactEntityId: 'leadgen.contact',
480
- companyStages: leadGenStagesForEntity('company'),
481
- contactStages: leadGenStagesForEntity('contact'),
482
- defaultBuildTemplateId: 'local-services',
483
- buildTemplates: [
484
- {
485
- id: 'local-services',
486
- label: 'Local Services Prospecting',
487
- description:
488
- 'Curated local-services list build using company sourcing, website analysis, qualification, contact discovery, verification, personalization, and review.',
489
- steps: [
490
- PROSPECTING_STEPS.localServices.sourceCompanies,
491
- PROSPECTING_STEPS.localServices.analyzeWebsites,
492
- PROSPECTING_STEPS.localServices.qualifyCompanies,
493
- PROSPECTING_STEPS.localServices.findContacts,
494
- PROSPECTING_STEPS.localServices.verifyEmails,
495
- PROSPECTING_STEPS.localServices.personalize,
496
- PROSPECTING_STEPS.localServices.review
497
- ]
498
- },
499
- {
500
- id: 'dtc-subscription-apollo-clickup',
501
- label: 'DTC Subscription Apollo Export',
502
- description:
503
- 'Prospecting pipeline for DTC subscription or subscription-ready brands where Apollo is the source and contact-enrichment layer, Elevasis handles company research and fit scoring, and approved leads export as an approved lead list.',
504
- steps: [
505
- PROSPECTING_STEPS.dtcApolloClickup.importApolloSearch,
506
- PROSPECTING_STEPS.dtcApolloClickup.apifyCrawl,
507
- PROSPECTING_STEPS.dtcApolloClickup.analyzeWebsites,
508
- PROSPECTING_STEPS.dtcApolloClickup.scoreDtcFit,
509
- PROSPECTING_STEPS.dtcApolloClickup.enrichDecisionMakers,
510
- PROSPECTING_STEPS.dtcApolloClickup.reviewAndExport
511
- ]
512
- }
513
- ]
514
- }
389
+ // Phase 4 cut: OrganizationModelProspectingSchema and DEFAULT_ORGANIZATION_MODEL_PROSPECTING removed.
390
+ // Build-template/stage data moved into system.content as (schema:template), (schema:template-step),
391
+ // and (schema:stage) content nodes. Use getAllBuildTemplates() / getAllProspectingStages()
392
+ // from migration-helpers to read prospecting data portably.
393
+ //
394
+ // ProspectingBuildTemplateSchema, ProspectingBuildTemplateStepSchema, ProspectingLifecycleStageSchema,
395
+ // PROSPECTING_STEPS, and ACTION_REGISTRY are retained for use by business logic and UI.