@elevasis/sdk 1.20.2 → 1.22.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 (164) hide show
  1. package/dist/cli.cjs +4220 -1583
  2. package/dist/index.d.ts +1035 -481
  3. package/dist/index.js +7381 -4187
  4. package/dist/node/index.d.ts +1 -3
  5. package/dist/node/index.js +40 -49
  6. package/dist/test-utils/index.d.ts +699 -123
  7. package/dist/test-utils/index.js +3826 -630
  8. package/dist/worker/index.js +3616 -442
  9. package/package.json +3 -3
  10. package/reference/_navigation.md +9 -7
  11. package/reference/_reference-manifest.json +1 -1
  12. package/reference/claude-config/hooks/post-edit-validate.mjs +98 -98
  13. package/reference/claude-config/hooks/scaffold-registry-reminder.mjs +188 -188
  14. package/reference/claude-config/hooks/tool-failure-recovery.mjs +73 -73
  15. package/reference/claude-config/registries/graph-skills.json +4 -4
  16. package/reference/claude-config/registries/knowledge-flags.json +0 -2
  17. package/reference/claude-config/rules/active-change-index.md +80 -80
  18. package/reference/claude-config/rules/agent-start-here.md +277 -273
  19. package/reference/claude-config/rules/deployment.md +57 -57
  20. package/reference/claude-config/rules/error-handling.md +56 -56
  21. package/reference/claude-config/rules/execution.md +40 -40
  22. package/reference/claude-config/rules/frontend.md +4 -4
  23. package/reference/claude-config/rules/observability.md +31 -31
  24. package/reference/claude-config/rules/operations.md +29 -17
  25. package/reference/claude-config/rules/organization-model.md +108 -40
  26. package/reference/claude-config/rules/organization-os.md +115 -113
  27. package/reference/claude-config/rules/package-taxonomy.md +33 -33
  28. package/reference/claude-config/rules/platform.md +42 -42
  29. package/reference/claude-config/rules/shared-types.md +49 -46
  30. package/reference/claude-config/rules/task-tracking.md +47 -47
  31. package/reference/claude-config/rules/ui.md +200 -200
  32. package/reference/claude-config/rules/vibe.md +235 -231
  33. package/reference/claude-config/scripts/statusline-command.js +18 -18
  34. package/reference/claude-config/settings.json +34 -34
  35. package/reference/claude-config/skills/deploy/{SKILL.md → skill.md} +156 -156
  36. package/reference/claude-config/skills/dsp/SKILL.md +66 -66
  37. package/reference/claude-config/skills/elevasis/SKILL.md +235 -235
  38. package/reference/claude-config/skills/explore/SKILL.md +6 -6
  39. package/reference/claude-config/skills/git-sync/SKILL.md +126 -126
  40. package/reference/claude-config/skills/knowledge/SKILL.md +330 -271
  41. package/reference/claude-config/skills/knowledge/operations/codify-level-a.md +100 -100
  42. package/reference/claude-config/skills/knowledge/operations/codify-level-b.md +159 -158
  43. package/reference/claude-config/skills/knowledge/operations/customers.md +109 -109
  44. package/reference/claude-config/skills/knowledge/operations/features.md +76 -113
  45. package/reference/claude-config/skills/knowledge/operations/goals.md +118 -118
  46. package/reference/claude-config/skills/knowledge/operations/identity.md +93 -93
  47. package/reference/claude-config/skills/knowledge/operations/labels.md +94 -89
  48. package/reference/claude-config/skills/knowledge/operations/offerings.md +109 -109
  49. package/reference/claude-config/skills/knowledge/operations/roles.md +99 -99
  50. package/reference/claude-config/skills/knowledge/operations/techStack.md +30 -30
  51. package/reference/claude-config/skills/project/SKILL.md +1088 -1088
  52. package/reference/claude-config/skills/run-ui/SKILL.md +73 -73
  53. package/reference/claude-config/skills/save/SKILL.md +3 -3
  54. package/reference/claude-config/skills/setup/SKILL.md +275 -275
  55. package/reference/claude-config/skills/status/SKILL.md +59 -59
  56. package/reference/claude-config/skills/submit-request/SKILL.md +180 -180
  57. package/reference/claude-config/skills/sync/SKILL.md +47 -47
  58. package/reference/claude-config/skills/tutorial/SKILL.md +259 -259
  59. package/reference/claude-config/skills/tutorial/progress-template.md +74 -74
  60. package/reference/claude-config/skills/tutorial/technical.md +1303 -1306
  61. package/reference/claude-config/skills/tutorial/vibe-coder.md +890 -890
  62. package/reference/claude-config/sync-notes/2026-04-22-git-sync-and-sync-notes.md +27 -27
  63. package/reference/claude-config/sync-notes/2026-04-22-lead-gen-deliverability-removal.md +30 -30
  64. package/reference/claude-config/sync-notes/2026-04-24-test-utils-and-template-tests.md +73 -73
  65. package/reference/claude-config/sync-notes/2026-04-24-ui-consolidation-and-sdk-cli-train.md +86 -86
  66. package/reference/claude-config/sync-notes/2026-04-25-auth-role-system-and-settings-roles.md +55 -55
  67. package/reference/claude-config/sync-notes/2026-04-27-crm-hitl-action-layer-cutover.md +97 -97
  68. package/reference/claude-config/sync-notes/2026-04-27-lead-gen-substrate-train.md +112 -112
  69. package/reference/claude-config/sync-notes/2026-04-29-crm-state-and-lead-gen-processing-status.md +93 -93
  70. package/reference/claude-config/sync-notes/2026-05-02-crm-ownership-next-action.md +58 -58
  71. package/reference/claude-config/sync-notes/2026-05-02-template-hardcode-workos-config.md +56 -56
  72. package/reference/claude-config/sync-notes/2026-05-04-elevasis-workspace.md +71 -71
  73. package/reference/claude-config/sync-notes/2026-05-04-knowledge-bundle.md +83 -83
  74. package/reference/claude-config/sync-notes/2026-05-04-template-skills-run-ui-and-tutorial.md +59 -59
  75. package/reference/claude-config/sync-notes/2026-05-05-list-builder.md +42 -42
  76. package/reference/claude-config/sync-notes/2026-05-06-crm-spine.md +60 -60
  77. package/reference/claude-config/sync-notes/2026-05-06-sdk-changes-release-train.md +37 -37
  78. package/reference/claude-config/sync-notes/2026-05-07-sdk-changes-release-train.md +34 -34
  79. package/reference/claude-config/sync-notes/2026-05-08-resource-governance-scaffold-guidance.md +38 -38
  80. package/reference/claude-config/sync-notes/2026-05-09-clients-domain.md +32 -32
  81. package/reference/claude-config/sync-notes/2026-05-09-command-system.md +33 -33
  82. package/reference/claude-config/sync-notes/2026-05-09-resource-governance-and-misc.md +69 -69
  83. package/reference/claude-config/sync-notes/2026-05-12-sdk-ready-release-train.md +30 -0
  84. package/reference/claude-config/sync-notes/2026-05-14-organization-model-ontology-refactor.md +42 -0
  85. package/reference/claude-config/sync-notes/README.md +43 -43
  86. package/reference/cli.mdx +808 -668
  87. package/reference/concepts.mdx +146 -146
  88. package/reference/deployment/api.mdx +297 -297
  89. package/reference/deployment/command-center.mdx +209 -209
  90. package/reference/deployment/index.mdx +195 -195
  91. package/reference/deployment/provided-features.mdx +107 -93
  92. package/reference/deployment/ui-execution.mdx +250 -250
  93. package/reference/examples/organization-model.ts +147 -84
  94. package/reference/framework/agent.mdx +156 -156
  95. package/reference/framework/index.mdx +195 -195
  96. package/reference/framework/interaction-guidance.mdx +182 -182
  97. package/reference/framework/memory.mdx +326 -326
  98. package/reference/framework/project-structure.mdx +282 -282
  99. package/reference/framework/tutorial-system.mdx +135 -135
  100. package/reference/getting-started.mdx +142 -142
  101. package/reference/index.mdx +106 -106
  102. package/reference/packages/core/src/README.md +14 -14
  103. package/reference/packages/core/src/business/README.md +2 -2
  104. package/reference/packages/core/src/knowledge/README.md +33 -32
  105. package/reference/packages/core/src/organization-model/README.md +149 -109
  106. package/reference/packages/core/src/test-utils/README.md +37 -37
  107. package/reference/packages/ui/src/api/README.md +18 -18
  108. package/reference/packages/ui/src/app/README.md +24 -24
  109. package/reference/packages/ui/src/auth/README.md +18 -18
  110. package/reference/packages/ui/src/components/README.md +24 -24
  111. package/reference/packages/ui/src/execution/README.md +16 -16
  112. package/reference/packages/ui/src/features/README.md +28 -28
  113. package/reference/packages/ui/src/graph/README.md +16 -16
  114. package/reference/packages/ui/src/hooks/README.md +23 -23
  115. package/reference/packages/ui/src/initialization/README.md +19 -19
  116. package/reference/packages/ui/src/knowledge/README.md +31 -31
  117. package/reference/packages/ui/src/organization/README.md +18 -18
  118. package/reference/packages/ui/src/profile/README.md +19 -19
  119. package/reference/packages/ui/src/provider/README.md +32 -32
  120. package/reference/packages/ui/src/router/README.md +18 -18
  121. package/reference/packages/ui/src/sse/README.md +13 -13
  122. package/reference/packages/ui/src/test-utils/README.md +7 -7
  123. package/reference/packages/ui/src/theme/README.md +23 -23
  124. package/reference/packages/ui/src/theme/presets/README.md +19 -19
  125. package/reference/packages/ui/src/types/README.md +16 -16
  126. package/reference/packages/ui/src/utils/README.md +18 -18
  127. package/reference/packages/ui/src/zustand/README.md +18 -18
  128. package/reference/platform-tools/adapters-integration.mdx +301 -301
  129. package/reference/platform-tools/adapters-platform.mdx +553 -553
  130. package/reference/platform-tools/index.mdx +217 -217
  131. package/reference/platform-tools/type-safety.mdx +82 -82
  132. package/reference/resources/index.mdx +349 -349
  133. package/reference/resources/patterns.mdx +449 -449
  134. package/reference/resources/types.mdx +116 -116
  135. package/reference/roadmap.mdx +165 -165
  136. package/reference/runtime.mdx +173 -173
  137. package/reference/scaffold/core/organization-graph.mdx +110 -89
  138. package/reference/scaffold/core/organization-model.mdx +226 -171
  139. package/reference/scaffold/index.mdx +67 -67
  140. package/reference/scaffold/operations/propagation-pipeline.md +77 -77
  141. package/reference/scaffold/operations/scaffold-maintenance.md +10 -10
  142. package/reference/scaffold/operations/workflow-recipes.md +138 -138
  143. package/reference/scaffold/recipes/add-a-feature.md +310 -88
  144. package/reference/scaffold/recipes/add-a-resource.md +137 -117
  145. package/reference/scaffold/recipes/customize-crm-actions.md +439 -439
  146. package/reference/scaffold/recipes/customize-knowledge-browser.md +384 -0
  147. package/reference/scaffold/recipes/customize-organization-model.md +281 -118
  148. package/reference/scaffold/recipes/extend-a-base-entity.md +8 -8
  149. package/reference/scaffold/recipes/extend-crm.md +40 -39
  150. package/reference/scaffold/recipes/extend-lead-gen.md +400 -401
  151. package/reference/scaffold/recipes/gate-by-feature-or-admin.md +118 -114
  152. package/reference/scaffold/recipes/index.md +47 -46
  153. package/reference/scaffold/recipes/query-the-knowledge-graph.md +227 -0
  154. package/reference/scaffold/reference/contracts.md +2389 -2121
  155. package/reference/scaffold/reference/feature-registry.md +9 -20
  156. package/reference/scaffold/reference/glossary.md +76 -76
  157. package/reference/scaffold/ui/composition-extensibility.mdx +233 -233
  158. package/reference/scaffold/ui/customization.md +243 -243
  159. package/reference/scaffold/ui/feature-flags-and-gating.md +46 -46
  160. package/reference/scaffold/ui/feature-shell.mdx +72 -72
  161. package/reference/scaffold/ui/recipes.md +221 -213
  162. package/reference/spine/spine-primer.md +96 -96
  163. package/reference/templates/index.mdx +47 -47
  164. package/reference/troubleshooting.mdx +223 -223
@@ -1,246 +1,246 @@
1
- ---
2
- title: Customizing Features
3
- description: One pattern for customizing feature sidebars and pages -- set manifest.sidebar to a component composing the feature's published pieces. Decision tree + three worked examples.
4
- ---
1
+ ---
2
+ title: Customizing Systems
3
+ description: One pattern for customizing system sidebars and pages -- set manifest.sidebar to a component composing the system's published pieces. Decision tree + three worked examples.
4
+ ---
5
5
  <!-- @generated by packages/sdk/scripts/copy-reference-docs.mjs -- DO NOT EDIT -->
6
6
  <!-- Regenerate: pnpm scaffold:sync -->
7
7
 
8
-
9
- # Customizing Features
10
-
11
- **Status:** 🟢 Stable
12
-
13
- > **Requires `@elevasis/ui` >= 2.8.1.**
14
-
15
- There is one pattern for customizing a feature's sidebar or pages: set `sidebar` on your manifest override to a component that composes the feature's published pieces. Pass custom `items` to swap the nav array, or compose `SidebarTop` + `SidebarMiddle` + exported panels directly for structural changes. Never fork a source file as a first resort -- if you copy source you own upstream drift forever.
16
-
17
- ## Decision Tree
18
-
19
- **Adding or changing nav items?** Extend the exported item array and pass to `<*SidebarMiddle items={...}>`. This covers the vast majority of sidebar customization needs.
20
-
21
- **Structural changes (injecting panels, reordering sections, wrapping sections)?** Compose `SidebarTop`, `SidebarMiddle`, and exported panels (`MyTasksPanel`, `QuickCreateActions`) directly into your own component and assign it to the manifest's `sidebar` field.
22
-
23
- **Wrapping pages?** Import the feature's page component and wrap with custom chrome in a route file.
24
-
25
- **Neither fits?** The missing export is a bug in `@elevasis/ui` -- file an issue. Copying source is physically possible but unsupported. You own upstream drift forever.
26
-
27
- ## Worked Example 1: Sidebar Nav Extension
28
-
29
- Extend CRM's nav by spreading `CRM_ITEMS` and appending a Reports entry. Pass the extended array to `CrmSidebarMiddle`.
30
-
31
- Wire the override in `ui/src/routes/__root.tsx`, where feature manifests are assembled before being passed to `ElevasisFeaturesProvider`.
32
-
33
- ```tsx
34
- // ui/src/routes/__root.tsx (excerpt -- add after existing imports)
35
-
36
- import { crmManifest, CrmSidebar, CrmSidebarMiddle, CRM_ITEMS } from '@elevasis/ui/features/crm'
37
- import { IconFileText } from '@tabler/icons-react'
38
- import type { NavItem } from '@elevasis/ui/layout'
39
-
40
- // Extend the published CRM nav array with a project-specific Reports entry.
41
- const customCrmItems: NavItem[] = [
42
- ...CRM_ITEMS,
43
- { label: 'Reports', to: '/crm/reports', icon: IconFileText, exact: false }
44
- ]
45
-
46
- // Compose CrmSidebar (Top + Middle) with the extended item list.
47
- const MyCrmSidebar = () => (
48
- <CrmSidebar>
49
- <CrmSidebarMiddle items={customCrmItems} />
50
- </CrmSidebar>
51
- )
52
-
53
- // Override the manifest's sidebar, keeping every other field unchanged.
54
- const customCrmManifest = { ...crmManifest, sidebar: MyCrmSidebar }
55
- ```
56
-
57
- Then swap `crmManifest` for `customCrmManifest` in the `FEATURE_MANIFESTS` array:
58
-
59
- ```tsx
60
- // In the FEATURE_MANIFESTS array (same file)
61
- const FEATURE_MANIFESTS: FeatureModule[] = [
62
- leadGenManifest,
63
- customCrmManifest, // <-- replaces crmManifest
64
- deliveryManifest,
65
- operationsManifest,
66
- monitoringManifest,
67
- settingsManifest
68
- ]
69
- ```
70
-
71
- Your new `/crm/reports` route file still needs to be created in `ui/src/routes/crm/` -- the nav item just controls the link.
72
-
73
- ## Worked Example 2: Sidebar with Injected Panel
74
-
75
- Inject a custom panel between the nav list and the My Tasks section. Compose the parts explicitly rather than relying on `CrmSidebarMiddle`'s default layout.
76
-
77
- ```tsx
78
- // ui/src/routes/__root.tsx (excerpt)
79
-
80
- import {
81
- crmManifest,
82
- CrmSidebar,
83
- CrmSidebarMiddle,
84
- CrmSidebarTop,
85
- MyTasksPanel,
86
- QuickCreateActions,
87
- CRM_ITEMS
88
- } from '@elevasis/ui/features/crm'
89
- import { SubshellNavList, SubshellSidebarSection } from '@elevasis/ui/layout'
90
- import { Stack } from '@mantine/core'
91
- import { IconChartBar } from '@tabler/icons-react'
92
-
93
- // Custom middle that inserts a Pipeline Health panel between nav and My Tasks.
94
- const MyCrmMiddle = () => (
95
- <Stack gap={0} style={{ flex: 1, overflowY: 'auto' }}>
96
- <Stack gap={0} p="sm">
97
- <SubshellNavList items={CRM_ITEMS} />
98
- </Stack>
99
- {/* Inject custom panel here */}
100
- <SubshellSidebarSection icon={IconChartBar} label="Pipeline Health" withTopBorder />
101
- <Stack gap={0} p="sm">
102
- <PipelineHealthWidget />
103
- </Stack>
104
- {/* Preserve the My Tasks section from the default middle */}
105
- <MyTasksPanel footer={<QuickCreateActions showSectionLabel={false} />} showSectionLabel />
106
- </Stack>
107
- )
108
-
109
- // Full sidebar: Top stays unchanged, Middle is replaced.
110
- const MyCrmSidebar = () => (
111
- <CrmSidebar>
112
- <MyCrmMiddle />
113
- </CrmSidebar>
114
- )
115
-
116
- const customCrmManifest = { ...crmManifest, sidebar: MyCrmSidebar }
117
- ```
118
-
119
- `PipelineHealthWidget` is a component you define in `ui/src/features/crm/` or `ui/src/lib/components/`. Keep route files and `__root.tsx` thin -- push component logic into feature modules.
120
-
121
- ## Worked Example 3: Page Wrapping
122
-
123
- Import a feature's page component and wrap it with custom chrome in a route file. This keeps the feature's business logic intact while adding project-specific framing (banners, secondary nav, analytics context, etc.).
124
-
125
- The exported CRM page components are `DealsListPage` and `DealDetailPage`:
126
-
127
- ```tsx
128
- // ui/src/routes/crm/deals.index.tsx
129
-
130
- import { createFileRoute } from '@tanstack/react-router'
131
- import { DealsListPage } from '@elevasis/ui/features/crm'
132
- import { ProtectedRoute } from '@/features/auth'
133
- import { ProjectAnnouncementBanner } from '@/lib/components/ProjectAnnouncementBanner'
134
- import { Stack } from '@mantine/core'
135
-
136
- export const Route = createFileRoute('/crm/deals/')({
137
- component: DealsListPageGuarded
138
- })
139
-
140
- function DealsListPageGuarded() {
141
- return (
142
- <ProtectedRoute>
143
- <Stack gap={0}>
144
- <ProjectAnnouncementBanner context="crm-deals" />
145
- <DealsListPage />
146
- </Stack>
147
- </ProtectedRoute>
148
- )
149
- }
150
- ```
151
-
152
- The pattern is identical for `DealDetailPage`. Import the published component, wrap it in your chrome, export as the route component. No forking, no copying source.
153
-
154
- ## Delivery: Three-Section Sidebar
155
-
156
- Delivery keeps three named sections (Projects, Work, Communication). It exports three separate arrays and `ProjectsSidebarMiddle` accepts three matching optional props -- one per section. There is no single `items` prop.
157
-
158
- ```tsx
159
- // Adding items to an existing delivery section
160
- import {
161
- deliveryManifest,
162
- ProjectsSidebar,
163
- ProjectsSidebarMiddle,
164
- DELIVERY_PROJECT_ITEMS,
165
- DELIVERY_WORK_ITEMS,
166
- DELIVERY_COMMUNICATION_ITEMS
167
- } from '@elevasis/ui/features/delivery'
168
- import type { NavItem } from '@elevasis/ui/layout'
169
- import { IconChartBar } from '@tabler/icons-react'
170
-
171
- const customProjectItems: NavItem[] = [
172
- ...DELIVERY_PROJECT_ITEMS,
173
- { label: 'Analytics', to: '/projects/analytics', icon: IconChartBar, exact: false }
174
- ]
175
-
176
- const MyDeliverySidebar = () => (
177
- <ProjectsSidebar>
178
- <ProjectsSidebarMiddle
179
- projectItems={customProjectItems}
180
- workItems={DELIVERY_WORK_ITEMS}
181
- communicationItems={DELIVERY_COMMUNICATION_ITEMS}
182
- />
183
- </ProjectsSidebar>
184
- )
185
-
186
- const customDeliveryManifest = { ...deliveryManifest, sidebar: MyDeliverySidebar }
187
- ```
188
-
189
- **Adding a new section** (not extending an existing one) requires composing from primitives. Use `SubshellSidebarSection` as the section header and `SubshellNavList` to render items inside it:
190
-
191
- ```tsx
192
- import {
193
- ProjectsSidebar,
194
- DELIVERY_PROJECT_ITEMS,
195
- DELIVERY_WORK_ITEMS,
196
- DELIVERY_COMMUNICATION_ITEMS
197
- } from '@elevasis/ui/features/delivery'
198
- import { SubshellSidebarSection, SubshellNavList } from '@elevasis/ui/layout'
199
- import { Stack } from '@mantine/core'
200
- import { IconChartBar, IconListCheck, IconMessageCircle, IconBriefcase } from '@tabler/icons-react'
201
- import type { NavItem } from '@elevasis/ui/layout'
202
-
203
- const ANALYTICS_ITEMS: NavItem[] = [
204
- { label: 'Dashboard', to: '/projects/analytics', icon: IconChartBar, exact: true }
205
- ]
206
-
207
- const MyDeliveryMiddle = () => (
208
- <Stack gap={0} style={{ flex: 1, overflowY: 'auto' }}>
209
- <Stack gap={0} p="sm">
210
- <SubshellNavList items={DELIVERY_PROJECT_ITEMS} />
211
- </Stack>
212
- <SubshellSidebarSection icon={IconListCheck} label="Work" withTopBorder />
213
- <Stack gap={0} p="sm">
214
- <SubshellNavList items={DELIVERY_WORK_ITEMS} />
215
- </Stack>
216
- <SubshellSidebarSection icon={IconMessageCircle} label="Communication" withTopBorder />
217
- <Stack gap={0} p="sm">
218
- <SubshellNavList items={DELIVERY_COMMUNICATION_ITEMS} />
219
- </Stack>
220
- <SubshellSidebarSection icon={IconChartBar} label="Analytics" withTopBorder />
221
- <Stack gap={0} p="sm">
222
- <SubshellNavList items={ANALYTICS_ITEMS} />
223
- </Stack>
224
- </Stack>
225
- )
226
-
227
- const MyDeliverySidebar = () => <ProjectsSidebar><MyDeliveryMiddle /></ProjectsSidebar>
228
- ```
229
-
230
- This is the same compose-from-primitives path CRM consumers use for structural changes. No special API -- just `SubshellSidebarSection` + `SubshellNavList` from `@elevasis/ui/layout`.
231
-
232
- For broader CRM extension work across pages, hooks, actions, workflows, and org-model boundaries, start with `node_modules/@elevasis/sdk/reference/scaffold/recipes/extend-crm.md`.
233
-
234
- For broader lead-gen extension work across pages, hooks, list/member state, artifacts, workflows, and org-model boundaries, start with `node_modules/@elevasis/sdk/reference/scaffold/recipes/extend-lead-gen.md`.
235
-
236
- ## Imports Cheat Sheet
237
-
238
- | What you need | Import from |
239
- | --------------------------------------------------------------------------------------------------------------------------------------------------------------------- | -------------------------------- |
240
- | `CRM_ITEMS`, `CrmSidebar`, `CrmSidebarTop`, `CrmSidebarMiddle`, `MyTasksPanel`, `QuickCreateActions`, `DealsListPage`, `DealDetailPage`, `crmManifest` | `@elevasis/ui/features/crm` |
241
- | `LEAD_GEN_ITEMS`, `LeadGenSidebar`, `LeadGenSidebarTop`, `LeadGenSidebarMiddle`, `leadGenManifest` | `@elevasis/ui/features/lead-gen` |
242
- | `DELIVERY_PROJECT_ITEMS`, `DELIVERY_WORK_ITEMS`, `DELIVERY_COMMUNICATION_ITEMS`, `ProjectsSidebar`, `ProjectsSidebarTop`, `ProjectsSidebarMiddle`, `deliveryManifest` | `@elevasis/ui/features/delivery` |
243
- | `SubshellNavList`, `SubshellNavItem`, `SubshellSidebarSection`, `NavItem` | `@elevasis/ui/layout` |
244
- | `FeatureModule` | `@elevasis/ui/provider` |
245
-
246
- Operations, monitoring, and settings have no customizable sidebar items. Operations sidebar is route-aware dispatch and not extended via the `items` pattern.
8
+
9
+ # Customizing Systems
10
+
11
+ **Status:** 🟢 Stable
12
+
13
+ > **Requires `@elevasis/ui` >= 2.8.1.**
14
+
15
+ There is one pattern for customizing a system's sidebar or pages: set `sidebar` on your manifest override to a component that composes the system's published pieces. Pass custom `items` to swap the nav array, or compose `SidebarTop` + `SidebarMiddle` + exported panels directly for structural changes. Never fork a source file as a first resort -- if you copy source you own upstream drift forever.
16
+
17
+ ## Decision Tree
18
+
19
+ **Adding or changing nav items?** Extend the exported item array and pass to `<*SidebarMiddle items={...}>`. This covers the vast majority of sidebar customization needs.
20
+
21
+ **Structural changes (injecting panels, reordering sections, wrapping sections)?** Compose `SidebarTop`, `SidebarMiddle`, and exported panels (`MyTasksPanel`, `QuickCreateActions`) directly into your own component and assign it to the manifest's `sidebar` field.
22
+
23
+ **Wrapping pages?** Import the system's page component and wrap with custom chrome in a route file.
24
+
25
+ **Neither fits?** The missing export is a bug in `@elevasis/ui` -- file an issue. Copying source is physically possible but unsupported. You own upstream drift forever.
26
+
27
+ ## Worked Example 1: Sidebar Nav Extension
28
+
29
+ Extend CRM's nav by spreading `CRM_ITEMS` and appending a Reports entry. Pass the extended array to `CrmSidebarMiddle`.
30
+
31
+ Wire the override in `ui/src/routes/__root.tsx`, where system manifests are assembled before being passed to `ElevasisSystemsProvider`.
32
+
33
+ ```tsx
34
+ // ui/src/routes/__root.tsx (excerpt -- add after existing imports)
35
+
36
+ import { crmManifest, CrmSidebar, CrmSidebarMiddle, CRM_ITEMS } from '@elevasis/ui/features/crm'
37
+ import { IconFileText } from '@tabler/icons-react'
38
+ import type { NavItem } from '@elevasis/ui/layout'
39
+
40
+ // Extend the published CRM nav array with a project-specific Reports entry.
41
+ const customCrmItems: NavItem[] = [
42
+ ...CRM_ITEMS,
43
+ { label: 'Reports', to: '/crm/reports', icon: IconFileText, exact: false }
44
+ ]
45
+
46
+ // Compose CrmSidebar (Top + Middle) with the extended item list.
47
+ const MyCrmSidebar = () => (
48
+ <CrmSidebar>
49
+ <CrmSidebarMiddle items={customCrmItems} />
50
+ </CrmSidebar>
51
+ )
52
+
53
+ // Override the manifest's sidebar, keeping every other field unchanged.
54
+ const customCrmManifest = { ...crmManifest, sidebar: MyCrmSidebar }
55
+ ```
56
+
57
+ Then swap `crmManifest` for `customCrmManifest` in the `SYSTEM_MANIFESTS` array:
58
+
59
+ ```tsx
60
+ // In the SYSTEM_MANIFESTS array (same file)
61
+ const SYSTEM_MANIFESTS: SystemModule[] = [
62
+ leadGenManifest,
63
+ customCrmManifest, // <-- replaces crmManifest
64
+ deliveryManifest,
65
+ operationsManifest,
66
+ monitoringManifest,
67
+ settingsManifest
68
+ ]
69
+ ```
70
+
71
+ Your new `/crm/reports` route file still needs to be created in `ui/src/routes/crm/` -- the nav item just controls the link.
72
+
73
+ ## Worked Example 2: Sidebar with Injected Panel
74
+
75
+ Inject a custom panel between the nav list and the My Tasks section. Compose the parts explicitly rather than relying on `CrmSidebarMiddle`'s default layout.
76
+
77
+ ```tsx
78
+ // ui/src/routes/__root.tsx (excerpt)
79
+
80
+ import {
81
+ crmManifest,
82
+ CrmSidebar,
83
+ CrmSidebarMiddle,
84
+ CrmSidebarTop,
85
+ MyTasksPanel,
86
+ QuickCreateActions,
87
+ CRM_ITEMS
88
+ } from '@elevasis/ui/features/crm'
89
+ import { SubshellNavList, SubshellSidebarSection } from '@elevasis/ui/layout'
90
+ import { Stack } from '@mantine/core'
91
+ import { IconChartBar } from '@tabler/icons-react'
92
+
93
+ // Custom middle that inserts a Pipeline Health panel between nav and My Tasks.
94
+ const MyCrmMiddle = () => (
95
+ <Stack gap={0} style={{ flex: 1, overflowY: 'auto' }}>
96
+ <Stack gap={0} p="sm">
97
+ <SubshellNavList items={CRM_ITEMS} />
98
+ </Stack>
99
+ {/* Inject custom panel here */}
100
+ <SubshellSidebarSection icon={IconChartBar} label="Pipeline Health" withTopBorder />
101
+ <Stack gap={0} p="sm">
102
+ <PipelineHealthWidget />
103
+ </Stack>
104
+ {/* Preserve the My Tasks section from the default middle */}
105
+ <MyTasksPanel footer={<QuickCreateActions showSectionLabel={false} />} showSectionLabel />
106
+ </Stack>
107
+ )
108
+
109
+ // Full sidebar: Top stays unchanged, Middle is replaced.
110
+ const MyCrmSidebar = () => (
111
+ <CrmSidebar>
112
+ <MyCrmMiddle />
113
+ </CrmSidebar>
114
+ )
115
+
116
+ const customCrmManifest = { ...crmManifest, sidebar: MyCrmSidebar }
117
+ ```
118
+
119
+ `PipelineHealthWidget` is a component you define in `ui/src/features/crm/` or `ui/src/lib/components/`. Keep route files and `__root.tsx` thin -- push component logic into feature modules.
120
+
121
+ ## Worked Example 3: Page Wrapping
122
+
123
+ Import a system's page component and wrap it with custom chrome in a route file. This keeps the system's business logic intact while adding project-specific framing (banners, secondary nav, analytics context, etc.).
124
+
125
+ The exported CRM page components are `DealsListPage` and `DealDetailPage`:
126
+
127
+ ```tsx
128
+ // ui/src/routes/crm/deals.index.tsx
129
+
130
+ import { createFileRoute } from '@tanstack/react-router'
131
+ import { DealsListPage } from '@elevasis/ui/features/crm'
132
+ import { ProtectedRoute } from '@/features/auth'
133
+ import { ProjectAnnouncementBanner } from '@/lib/components/ProjectAnnouncementBanner'
134
+ import { Stack } from '@mantine/core'
135
+
136
+ export const Route = createFileRoute('/crm/deals/')({
137
+ component: DealsListPageGuarded
138
+ })
139
+
140
+ function DealsListPageGuarded() {
141
+ return (
142
+ <ProtectedRoute>
143
+ <Stack gap={0}>
144
+ <ProjectAnnouncementBanner context="crm-deals" />
145
+ <DealsListPage />
146
+ </Stack>
147
+ </ProtectedRoute>
148
+ )
149
+ }
150
+ ```
151
+
152
+ The pattern is identical for `DealDetailPage`. Import the published component, wrap it in your chrome, export as the route component. No forking, no copying source.
153
+
154
+ ## Delivery: Three-Section Sidebar
155
+
156
+ Delivery keeps three named sections (Projects, Work, Communication). It exports three separate arrays and `ProjectsSidebarMiddle` accepts three matching optional props -- one per section. There is no single `items` prop.
157
+
158
+ ```tsx
159
+ // Adding items to an existing delivery section
160
+ import {
161
+ deliveryManifest,
162
+ ProjectsSidebar,
163
+ ProjectsSidebarMiddle,
164
+ DELIVERY_PROJECT_ITEMS,
165
+ DELIVERY_WORK_ITEMS,
166
+ DELIVERY_COMMUNICATION_ITEMS
167
+ } from '@elevasis/ui/features/delivery'
168
+ import type { NavItem } from '@elevasis/ui/layout'
169
+ import { IconChartBar } from '@tabler/icons-react'
170
+
171
+ const customProjectItems: NavItem[] = [
172
+ ...DELIVERY_PROJECT_ITEMS,
173
+ { label: 'Analytics', to: '/projects/analytics', icon: IconChartBar, exact: false }
174
+ ]
175
+
176
+ const MyDeliverySidebar = () => (
177
+ <ProjectsSidebar>
178
+ <ProjectsSidebarMiddle
179
+ projectItems={customProjectItems}
180
+ workItems={DELIVERY_WORK_ITEMS}
181
+ communicationItems={DELIVERY_COMMUNICATION_ITEMS}
182
+ />
183
+ </ProjectsSidebar>
184
+ )
185
+
186
+ const customDeliveryManifest = { ...deliveryManifest, sidebar: MyDeliverySidebar }
187
+ ```
188
+
189
+ **Adding a new section** (not extending an existing one) requires composing from primitives. Use `SubshellSidebarSection` as the section header and `SubshellNavList` to render items inside it:
190
+
191
+ ```tsx
192
+ import {
193
+ ProjectsSidebar,
194
+ DELIVERY_PROJECT_ITEMS,
195
+ DELIVERY_WORK_ITEMS,
196
+ DELIVERY_COMMUNICATION_ITEMS
197
+ } from '@elevasis/ui/features/delivery'
198
+ import { SubshellSidebarSection, SubshellNavList } from '@elevasis/ui/layout'
199
+ import { Stack } from '@mantine/core'
200
+ import { IconChartBar, IconListCheck, IconMessageCircle, IconBriefcase } from '@tabler/icons-react'
201
+ import type { NavItem } from '@elevasis/ui/layout'
202
+
203
+ const ANALYTICS_ITEMS: NavItem[] = [
204
+ { label: 'Dashboard', to: '/projects/analytics', icon: IconChartBar, exact: true }
205
+ ]
206
+
207
+ const MyDeliveryMiddle = () => (
208
+ <Stack gap={0} style={{ flex: 1, overflowY: 'auto' }}>
209
+ <Stack gap={0} p="sm">
210
+ <SubshellNavList items={DELIVERY_PROJECT_ITEMS} />
211
+ </Stack>
212
+ <SubshellSidebarSection icon={IconListCheck} label="Work" withTopBorder />
213
+ <Stack gap={0} p="sm">
214
+ <SubshellNavList items={DELIVERY_WORK_ITEMS} />
215
+ </Stack>
216
+ <SubshellSidebarSection icon={IconMessageCircle} label="Communication" withTopBorder />
217
+ <Stack gap={0} p="sm">
218
+ <SubshellNavList items={DELIVERY_COMMUNICATION_ITEMS} />
219
+ </Stack>
220
+ <SubshellSidebarSection icon={IconChartBar} label="Analytics" withTopBorder />
221
+ <Stack gap={0} p="sm">
222
+ <SubshellNavList items={ANALYTICS_ITEMS} />
223
+ </Stack>
224
+ </Stack>
225
+ )
226
+
227
+ const MyDeliverySidebar = () => <ProjectsSidebar><MyDeliveryMiddle /></ProjectsSidebar>
228
+ ```
229
+
230
+ This is the same compose-from-primitives path CRM consumers use for structural changes. No special API -- just `SubshellSidebarSection` + `SubshellNavList` from `@elevasis/ui/layout`.
231
+
232
+ For broader CRM extension work across pages, hooks, actions, workflows, and org-model boundaries, start with `node_modules/@elevasis/sdk/reference/scaffold/recipes/extend-crm.md`.
233
+
234
+ For broader lead-gen extension work across pages, hooks, list/member state, artifacts, workflows, and org-model boundaries, start with `node_modules/@elevasis/sdk/reference/scaffold/recipes/extend-lead-gen.md`.
235
+
236
+ ## Imports Cheat Sheet
237
+
238
+ | What you need | Import from |
239
+ | --------------------------------------------------------------------------------------------------------------------------------------------------------------------- | -------------------------------- |
240
+ | `CRM_ITEMS`, `CrmSidebar`, `CrmSidebarTop`, `CrmSidebarMiddle`, `MyTasksPanel`, `QuickCreateActions`, `DealsListPage`, `DealDetailPage`, `crmManifest` | `@elevasis/ui/features/crm` |
241
+ | `LEAD_GEN_ITEMS`, `LeadGenSidebar`, `LeadGenSidebarTop`, `LeadGenSidebarMiddle`, `leadGenManifest` | `@elevasis/ui/features/lead-gen` |
242
+ | `DELIVERY_PROJECT_ITEMS`, `DELIVERY_WORK_ITEMS`, `DELIVERY_COMMUNICATION_ITEMS`, `ProjectsSidebar`, `ProjectsSidebarTop`, `ProjectsSidebarMiddle`, `deliveryManifest` | `@elevasis/ui/features/delivery` |
243
+ | `SubshellNavList`, `SubshellNavItem`, `SubshellSidebarSection`, `NavItem` | `@elevasis/ui/layout` |
244
+ | `SystemModule` | `@elevasis/ui/provider` |
245
+
246
+ Operations, monitoring, and settings have no customizable sidebar items. Operations sidebar is route-aware dispatch and not extended via the `items` pattern.
@@ -1,49 +1,49 @@
1
1
  <!-- @generated by packages/sdk/scripts/copy-reference-docs.mjs -- DO NOT EDIT -->
2
2
  <!-- Regenerate: pnpm scaffold:sync -->
3
3
 
4
- # Feature Flags And Gating
5
-
6
- Feature visibility is keyed by Organization Model feature ID.
7
-
8
- ## Where Visibility Comes From
9
-
10
- - `features[].enabled` in the organization model defines the baseline.
11
- - Membership feature config can override individual feature IDs.
12
- - `requiresAdmin` hides sidebar entries from non-admins.
13
- - `devOnly` hides sidebar entries outside development mode.
14
-
15
- The shell derives visible sidebar entries from `shellModel.topLevel()` and `shellModel.childrenOf(id)`.
16
-
17
- ## Route Guards
18
-
19
- Navigation visibility is cosmetic. Always guard routes directly:
20
-
21
- ```tsx
22
- <ProtectedRoute>
23
- <FeatureGuard featureKey="sales.crm">
24
- <Outlet />
25
- </FeatureGuard>
26
- </ProtectedRoute>
27
- ```
28
-
29
- For admin-only routes:
30
-
31
- ```tsx
32
- <AdminGuard>
33
- <SystemHealthPage />
34
- </AdminGuard>
35
- ```
36
-
37
- ## Adding A Gated Feature
38
-
39
- ```ts
40
- {
41
- id: 'analytics',
42
- label: 'Analytics',
43
- enabled: true,
44
- path: '/analytics',
45
- uiPosition: 'sidebar-primary'
46
- }
47
- ```
48
-
49
- Use the same ID in `FeatureGuard featureKey` and `FeatureModule.featureId`.
4
+ # System Flags And Gating
5
+
6
+ System visibility is keyed by Organization Model system ID.
7
+
8
+ ## Where Visibility Comes From
9
+
10
+ - `systems.systems[].enabled` in the organization model defines the baseline.
11
+ - Membership system config can override individual system IDs.
12
+ - `requiresAdmin` hides sidebar entries from non-admins.
13
+ - `devOnly` hides sidebar entries outside development mode.
14
+
15
+ The shell derives visible sidebar entries from `shellModel.topLevel()` and `shellModel.childrenOf(id)`.
16
+
17
+ ## Route Guards
18
+
19
+ Navigation visibility is cosmetic. Always guard routes directly:
20
+
21
+ ```tsx
22
+ <ProtectedRoute>
23
+ <SystemGuard systemKey="sales.crm">
24
+ <Outlet />
25
+ </SystemGuard>
26
+ </ProtectedRoute>
27
+ ```
28
+
29
+ For admin-only routes:
30
+
31
+ ```tsx
32
+ <AdminGuard>
33
+ <SystemHealthPage />
34
+ </AdminGuard>
35
+ ```
36
+
37
+ ## Adding A Gated System
38
+
39
+ ```ts
40
+ {
41
+ id: 'analytics',
42
+ label: 'Analytics',
43
+ enabled: true,
44
+ path: '/analytics',
45
+ uiPosition: 'sidebar-primary'
46
+ }
47
+ ```
48
+
49
+ Use the same ID in `SystemGuard systemKey` and `SystemModule.systemId`.