@contentful/experience-design-system-cli 2.14.2 → 2.15.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 (193) hide show
  1. package/README.md +64 -2
  2. package/dist/package.json +3 -2
  3. package/dist/src/analyze/command.d.ts +11 -0
  4. package/dist/src/analyze/command.js +298 -3
  5. package/dist/src/analyze/composite-closure.d.ts +25 -0
  6. package/dist/src/analyze/composite-closure.js +0 -0
  7. package/dist/src/analyze/composition/agent-parser/author-prompt.d.ts +4 -0
  8. package/dist/src/analyze/composition/agent-parser/author-prompt.js +22 -0
  9. package/dist/src/analyze/composition/agent-parser/extract-parser.d.ts +8 -0
  10. package/dist/src/analyze/composition/agent-parser/extract-parser.js +44 -0
  11. package/dist/src/analyze/composition/agent-parser/load-prompt.d.ts +7 -0
  12. package/dist/src/analyze/composition/agent-parser/load-prompt.js +31 -0
  13. package/dist/src/analyze/composition/agent-parser/resolve-via-parser.d.ts +46 -0
  14. package/dist/src/analyze/composition/agent-parser/resolve-via-parser.js +88 -0
  15. package/dist/src/analyze/composition/agent-parser/sandbox.d.ts +45 -0
  16. package/dist/src/analyze/composition/agent-parser/sandbox.js +187 -0
  17. package/dist/src/analyze/composition/apply-mapping.d.ts +22 -0
  18. package/dist/src/analyze/composition/apply-mapping.js +67 -0
  19. package/dist/src/analyze/composition/candidate-critic-agent.d.ts +7 -0
  20. package/dist/src/analyze/composition/candidate-critic-agent.js +39 -0
  21. package/dist/src/analyze/composition/candidate-critic.d.ts +32 -0
  22. package/dist/src/analyze/composition/candidate-critic.js +63 -0
  23. package/dist/src/analyze/composition/candidate-files.d.ts +34 -0
  24. package/dist/src/analyze/composition/candidate-files.js +131 -0
  25. package/dist/src/analyze/composition/composition-cache-key.d.ts +19 -0
  26. package/dist/src/analyze/composition/composition-cache-key.js +19 -0
  27. package/dist/src/analyze/composition/interchange-schema.d.ts +37 -0
  28. package/dist/src/analyze/composition/interchange-schema.js +61 -0
  29. package/dist/src/analyze/composition/merge-edges.d.ts +19 -0
  30. package/dist/src/analyze/composition/merge-edges.js +50 -0
  31. package/dist/src/analyze/composition/parse-map-edges.d.ts +16 -0
  32. package/dist/src/analyze/composition/parse-map-edges.js +55 -0
  33. package/dist/src/analyze/composition/resolve-mapping-cli.d.ts +23 -0
  34. package/dist/src/analyze/composition/resolve-mapping-cli.js +29 -0
  35. package/dist/src/analyze/composition/resolve-mapping.d.ts +59 -0
  36. package/dist/src/analyze/composition/resolve-mapping.js +94 -0
  37. package/dist/src/analyze/cycle-detection.d.ts +27 -0
  38. package/dist/src/analyze/cycle-detection.js +234 -0
  39. package/dist/src/analyze/cycle-view.d.ts +7 -0
  40. package/dist/src/analyze/cycle-view.js +28 -0
  41. package/dist/src/analyze/fuzzy-search.d.ts +3 -0
  42. package/dist/src/analyze/fuzzy-search.js +55 -0
  43. package/dist/src/analyze/issue-inheritance.d.ts +12 -0
  44. package/dist/src/analyze/issue-inheritance.js +108 -0
  45. package/dist/src/analyze/lineage.d.ts +29 -0
  46. package/dist/src/analyze/lineage.js +0 -0
  47. package/dist/src/analyze/scope-gate-cascade.d.ts +11 -0
  48. package/dist/src/analyze/scope-gate-cascade.js +170 -0
  49. package/dist/src/analyze/search-neighborhood.d.ts +3 -0
  50. package/dist/src/analyze/search-neighborhood.js +56 -0
  51. package/dist/src/analyze/select/tui/App.js +5 -16
  52. package/dist/src/analyze/select/tui/components/ComponentRationalePanel.d.ts +0 -4
  53. package/dist/src/analyze/select/tui/components/ComponentRationalePanel.js +3 -15
  54. package/dist/src/analyze/select/tui/components/FieldEditor.d.ts +29 -38
  55. package/dist/src/analyze/select/tui/components/FieldEditor.js +309 -185
  56. package/dist/src/analyze/select/tui/components/FinalizeDialog.d.ts +13 -1
  57. package/dist/src/analyze/select/tui/components/FinalizeDialog.js +23 -2
  58. package/dist/src/analyze/select/tui/components/GotoBanner.d.ts +31 -0
  59. package/dist/src/analyze/select/tui/components/GotoBanner.js +30 -0
  60. package/dist/src/analyze/select/tui/components/GroupedSidebar.d.ts +91 -0
  61. package/dist/src/analyze/select/tui/components/GroupedSidebar.js +497 -0
  62. package/dist/src/analyze/select/tui/components/HelpOverlay.d.ts +13 -1
  63. package/dist/src/analyze/select/tui/components/HelpOverlay.js +9 -3
  64. package/dist/src/analyze/select/tui/components/JsonEditor.js +3 -3
  65. package/dist/src/analyze/select/tui/components/LineagePanel.d.ts +14 -0
  66. package/dist/src/analyze/select/tui/components/LineagePanel.js +22 -0
  67. package/dist/src/analyze/select/tui/components/RationalePanel.d.ts +0 -7
  68. package/dist/src/analyze/select/tui/components/RationalePanel.js +3 -15
  69. package/dist/src/analyze/select/tui/components/Sidebar.d.ts +0 -6
  70. package/dist/src/analyze/select/tui/components/Sidebar.js +11 -27
  71. package/dist/src/analyze/select/tui/components/StatusBar.js +2 -1
  72. package/dist/src/analyze/select/tui/components/removed-components-text.d.ts +7 -0
  73. package/dist/src/analyze/select/tui/components/removed-components-text.js +11 -0
  74. package/dist/src/analyze/select/tui/hooks/useImmediateInput.d.ts +1 -5
  75. package/dist/src/analyze/select/tui/hooks/useImmediateInput.js +8 -10
  76. package/dist/src/analyze/select/tui/theme.d.ts +15 -0
  77. package/dist/src/analyze/select/tui/theme.js +28 -0
  78. package/dist/src/analyze/selection-cascade.d.ts +3 -0
  79. package/dist/src/analyze/selection-cascade.js +19 -0
  80. package/dist/src/analyze/slot-graph.d.ts +11 -0
  81. package/dist/src/analyze/slot-graph.js +17 -0
  82. package/dist/src/apply/api-client.d.ts +2 -1
  83. package/dist/src/apply/api-client.js +40 -6
  84. package/dist/src/apply/command.d.ts +17 -1
  85. package/dist/src/apply/command.js +69 -11
  86. package/dist/src/apply/error-parser.d.ts +16 -0
  87. package/dist/src/apply/error-parser.js +117 -0
  88. package/dist/src/apply/tui/ServerPreviewView.js +3 -1
  89. package/dist/src/credentials-store.d.ts +6 -0
  90. package/dist/src/credentials-store.js +5 -1
  91. package/dist/src/generate/agent-runner.d.ts +6 -0
  92. package/dist/src/generate/agent-runner.js +24 -8
  93. package/dist/src/import/command.js +69 -31
  94. package/dist/src/import/cycle-auto-reject.d.ts +4 -0
  95. package/dist/src/import/cycle-auto-reject.js +14 -0
  96. package/dist/src/import/orchestrator.d.ts +20 -7
  97. package/dist/src/import/orchestrator.js +139 -35
  98. package/dist/src/import/strip-allowed-components.d.ts +18 -0
  99. package/dist/src/import/strip-allowed-components.js +22 -0
  100. package/dist/src/import/tui/CustomPromptBanner.d.ts +0 -5
  101. package/dist/src/import/tui/CustomPromptBanner.js +2 -1
  102. package/dist/src/import/tui/WizardApp.d.ts +10 -74
  103. package/dist/src/import/tui/WizardApp.js +234 -246
  104. package/dist/src/import/tui/ai-flag.d.ts +5 -0
  105. package/dist/src/import/tui/ai-flag.js +6 -0
  106. package/dist/src/import/tui/autocomplete.d.ts +5 -0
  107. package/dist/src/import/tui/autocomplete.js +32 -0
  108. package/dist/src/import/tui/components/AutoFilterBanner.d.ts +10 -0
  109. package/dist/src/import/tui/components/AutoFilterBanner.js +19 -0
  110. package/dist/src/import/tui/components/CounterStrip.d.ts +12 -0
  111. package/dist/src/import/tui/components/CounterStrip.js +12 -0
  112. package/dist/src/import/tui/components/LegendEntry.d.ts +2 -0
  113. package/dist/src/import/tui/components/LegendEntry.js +6 -0
  114. package/dist/src/import/tui/cycle-panel-scroll.d.ts +8 -0
  115. package/dist/src/import/tui/cycle-panel-scroll.js +33 -0
  116. package/dist/src/import/tui/final-review-host.d.ts +3 -7
  117. package/dist/src/import/tui/final-review-host.js +9 -4
  118. package/dist/src/import/tui/group-collapse.d.ts +2 -0
  119. package/dist/src/import/tui/group-collapse.js +11 -0
  120. package/dist/src/import/tui/history.d.ts +22 -0
  121. package/dist/src/import/tui/history.js +53 -0
  122. package/dist/src/import/tui/hooks/useLineage.d.ts +32 -0
  123. package/dist/src/import/tui/hooks/useLineage.js +50 -0
  124. package/dist/src/import/tui/hooks/useOverlayPanel.d.ts +13 -0
  125. package/dist/src/import/tui/hooks/useOverlayPanel.js +27 -0
  126. package/dist/src/import/tui/lineage-layout.d.ts +75 -0
  127. package/dist/src/import/tui/lineage-layout.js +82 -0
  128. package/dist/src/import/tui/runLivePreview.d.ts +11 -0
  129. package/dist/src/import/tui/runLivePreview.js +7 -1
  130. package/dist/src/import/tui/scope-gate-columns.d.ts +31 -0
  131. package/dist/src/import/tui/scope-gate-columns.js +94 -0
  132. package/dist/src/import/tui/scope-gate-host.d.ts +3 -1
  133. package/dist/src/import/tui/scope-gate-host.js +11 -3
  134. package/dist/src/import/tui/sidebar-width.d.ts +1 -0
  135. package/dist/src/import/tui/sidebar-width.js +3 -0
  136. package/dist/src/import/tui/step-filters.d.ts +19 -0
  137. package/dist/src/import/tui/step-filters.js +42 -0
  138. package/dist/src/import/tui/steps/AtomicGenerateReviewStep.d.ts +42 -0
  139. package/dist/src/import/tui/steps/AtomicGenerateReviewStep.js +726 -0
  140. package/dist/src/import/tui/steps/AtomicScopeGateStep.d.ts +3 -0
  141. package/dist/src/import/tui/steps/AtomicScopeGateStep.js +211 -0
  142. package/dist/src/import/tui/steps/CredentialsStep.js +5 -18
  143. package/dist/src/import/tui/steps/DoneStep.d.ts +0 -2
  144. package/dist/src/import/tui/steps/DoneStep.js +3 -2
  145. package/dist/src/import/tui/steps/ErrorStep.js +2 -1
  146. package/dist/src/import/tui/steps/GenerateReviewStep.d.ts +19 -25
  147. package/dist/src/import/tui/steps/GenerateReviewStep.js +1258 -229
  148. package/dist/src/import/tui/steps/PathValidationStep.js +3 -2
  149. package/dist/src/import/tui/steps/PreviewStep.js +2 -1
  150. package/dist/src/import/tui/steps/PushDecisionGateStep.d.ts +0 -7
  151. package/dist/src/import/tui/steps/PushDecisionGateStep.js +3 -6
  152. package/dist/src/import/tui/steps/PushingStep.js +2 -1
  153. package/dist/src/import/tui/steps/RunningStep.d.ts +4 -1
  154. package/dist/src/import/tui/steps/RunningStep.js +3 -2
  155. package/dist/src/import/tui/steps/ScopeGateStep.d.ts +24 -0
  156. package/dist/src/import/tui/steps/ScopeGateStep.js +850 -193
  157. package/dist/src/import/tui/steps/TokenInputStep.js +2 -1
  158. package/dist/src/import/tui/steps/WelcomeStep.js +2 -1
  159. package/dist/src/import/tui/steps/WizardPreviewStep.d.ts +6 -0
  160. package/dist/src/import/tui/steps/WizardPreviewStep.js +95 -56
  161. package/dist/src/import/tui/steps/auto-reject-decision.d.ts +7 -0
  162. package/dist/src/import/tui/steps/auto-reject-decision.js +9 -0
  163. package/dist/src/import/tui/steps/breaking-change-format.d.ts +2 -0
  164. package/dist/src/import/tui/steps/breaking-change-format.js +24 -0
  165. package/dist/src/import/tui/steps/enumerate-cycle-breaks.d.ts +14 -0
  166. package/dist/src/import/tui/steps/enumerate-cycle-breaks.js +0 -0
  167. package/dist/src/import/tui/steps/preview-diff.js +48 -5
  168. package/dist/src/import/tui/useFinalizePreview.d.ts +34 -0
  169. package/dist/src/import/tui/useFinalizePreview.js +0 -0
  170. package/dist/src/import/tui/useLivePreview.d.ts +3 -0
  171. package/dist/src/import/tui/useLivePreview.js +1 -0
  172. package/dist/src/import/tui/wizard-state-transitions.d.ts +5 -59
  173. package/dist/src/import/tui/wizard-state-transitions.js +5 -60
  174. package/dist/src/lib/composition-mode.d.ts +28 -0
  175. package/dist/src/lib/composition-mode.js +37 -0
  176. package/dist/src/lib/prompt-overrides.d.ts +38 -0
  177. package/dist/src/lib/prompt-overrides.js +69 -0
  178. package/dist/src/print/command.js +19 -1
  179. package/dist/src/runs/modify-launcher.d.ts +3 -0
  180. package/dist/src/runs/modify-launcher.js +2 -0
  181. package/dist/src/runs/replay-helpers.js +1 -0
  182. package/dist/src/runs/run-picker.js +2 -18
  183. package/dist/src/runs/store.d.ts +4 -0
  184. package/dist/src/session/db.d.ts +23 -40
  185. package/dist/src/session/db.js +110 -138
  186. package/dist/src/setup/composition-mode-prompt.d.ts +14 -0
  187. package/dist/src/setup/composition-mode-prompt.js +37 -0
  188. package/package.json +5 -4
  189. package/prompts/composition-dir-critic.md +7 -0
  190. package/prompts/composition-edges.md +8 -0
  191. package/prompts/composition-parser-repair-empty.md +1 -0
  192. package/prompts/composition-parser-repair-error.md +2 -0
  193. package/prompts/composition-parser.md +42 -0
@@ -1,5 +1,6 @@
1
1
  import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
2
2
  import { useState, useEffect } from 'react';
3
+ import { PALETTE } from '../../../analyze/select/tui/theme.js';
3
4
  import { Box, Text } from 'ink';
4
5
  import { promises as fs } from 'node:fs';
5
6
  import { join } from 'node:path';
@@ -142,10 +143,10 @@ export function PathValidationStep({ projectPath, onConfirm, onSkipComponents, o
142
143
  }
143
144
  if (error) {
144
145
  const lines = error.split('\n');
145
- return (_jsxs(Box, { flexDirection: "column", gap: 1, paddingX: 2, paddingY: 1, children: [_jsxs(Box, { flexDirection: "column", children: [_jsxs(Text, { color: "red", children: ["\u2717 ", lines[0]] }), lines.slice(1).map((line, i) => (_jsx(Text, { dimColor: true, children: line }, i)))] }), _jsxs(Box, { gap: 3, marginTop: 1, children: [_jsx(Text, { dimColor: true, children: "[e / Enter] Try a different path" }), _jsx(Text, { dimColor: true, children: "[q] Quit" })] })] }));
146
+ return (_jsxs(Box, { flexDirection: "column", gap: 1, paddingX: 2, paddingY: 1, children: [_jsxs(Box, { flexDirection: "column", children: [_jsxs(Text, { color: PALETTE.error, children: ["\u2717 ", lines[0]] }), lines.slice(1).map((line, i) => (_jsx(Text, { dimColor: true, children: line }, i)))] }), _jsxs(Box, { gap: 3, marginTop: 1, children: [_jsx(Text, { dimColor: true, children: "[e / Enter] Try a different path" }), _jsx(Text, { dimColor: true, children: "[q] Quit" })] })] }));
146
147
  }
147
148
  const c = counts;
148
149
  const componentFiles = c.tsx + c.ts + c.vue + c.astro + c.jsx + c.js;
149
150
  const tokenFiles = c.json;
150
- return (_jsxs(Box, { flexDirection: "column", gap: 1, paddingX: 2, paddingY: 1, children: [_jsxs(Text, { children: ["Scanning ", _jsx(Text, { bold: true, children: projectPath }), "..."] }), _jsxs(Box, { flexDirection: "column", gap: 0, marginTop: 1, children: [_jsxs(Text, { color: "green", children: ["\u2713 Found ", c.total, " files:"] }), c.tsx > 0 && (_jsxs(Text, { children: [' • ', String(c.tsx).padStart(3), " .tsx files"] })), c.ts > 0 && (_jsxs(Text, { children: [' • ', String(c.ts).padStart(3), " .ts files"] })), c.vue > 0 && (_jsxs(Text, { children: [' • ', String(c.vue).padStart(3), " .vue files"] })), c.astro > 0 && (_jsxs(Text, { children: [' • ', String(c.astro).padStart(3), " .astro files"] })), c.jsx > 0 && (_jsxs(Text, { children: [' • ', String(c.jsx).padStart(3), " .jsx files"] })), c.js > 0 && (_jsxs(Text, { children: [' • ', String(c.js).padStart(3), " .js files"] })), c.json > 0 && (_jsxs(Text, { color: "cyan", children: [' • ', String(c.json).padStart(3), " .json files (design tokens)"] })), c.other > 0 && (_jsxs(Text, { dimColor: true, children: [' • ', String(c.other).padStart(3), " other (ignored)"] }))] }), componentFiles === 0 && tokenFiles === 0 && (_jsx(Text, { color: "yellow", children: "\u26A0 No component or token files found. Try a different path." })), componentFiles === 0 && tokenFiles > 0 && (_jsx(Text, { color: "yellow", children: "\u26A0 No component files found \u2014 only token files detected." })), _jsx(Box, { marginTop: 1, children: _jsx(Text, { children: "Does this look right?" }) }), _jsxs(Box, { gap: 3, marginTop: 1, children: [_jsx(Text, { dimColor: true, children: "[Enter] Yes, start extracting" }), _jsx(Text, { dimColor: true, children: "[s] Skip components" }), _jsx(Text, { dimColor: true, children: "[e] Change path" }), _jsx(Text, { dimColor: true, children: "[q] Quit" })] })] }));
151
+ return (_jsxs(Box, { flexDirection: "column", gap: 1, paddingX: 2, paddingY: 1, children: [_jsxs(Text, { children: ["Scanning ", _jsx(Text, { bold: true, children: projectPath }), "..."] }), _jsxs(Box, { flexDirection: "column", gap: 0, marginTop: 1, children: [_jsxs(Text, { color: PALETTE.success, children: ["\u2713 Found ", c.total, " files:"] }), c.tsx > 0 && (_jsxs(Text, { children: [' • ', String(c.tsx).padStart(3), " .tsx files"] })), c.ts > 0 && (_jsxs(Text, { children: [' • ', String(c.ts).padStart(3), " .ts files"] })), c.vue > 0 && (_jsxs(Text, { children: [' • ', String(c.vue).padStart(3), " .vue files"] })), c.astro > 0 && (_jsxs(Text, { children: [' • ', String(c.astro).padStart(3), " .astro files"] })), c.jsx > 0 && (_jsxs(Text, { children: [' • ', String(c.jsx).padStart(3), " .jsx files"] })), c.js > 0 && (_jsxs(Text, { children: [' • ', String(c.js).padStart(3), " .js files"] })), c.json > 0 && (_jsxs(Text, { color: PALETTE.info, children: [' • ', String(c.json).padStart(3), " .json files (design tokens)"] })), c.other > 0 && (_jsxs(Text, { dimColor: true, children: [' • ', String(c.other).padStart(3), " other (ignored)"] }))] }), componentFiles === 0 && tokenFiles === 0 && (_jsx(Text, { color: PALETTE.warning, children: "\u26A0 No component or token files found. Try a different path." })), componentFiles === 0 && tokenFiles > 0 && (_jsx(Text, { color: PALETTE.warning, children: "\u26A0 No component files found \u2014 only token files detected." })), _jsx(Box, { marginTop: 1, children: _jsx(Text, { children: "Does this look right?" }) }), _jsxs(Box, { gap: 3, marginTop: 1, children: [_jsx(Text, { dimColor: true, children: "[Enter] Yes, start extracting" }), _jsx(Text, { dimColor: true, children: "[s] Skip components" }), _jsx(Text, { dimColor: true, children: "[e] Change path" }), _jsx(Text, { dimColor: true, children: "[q] Quit" })] })] }));
151
152
  }
@@ -1,4 +1,5 @@
1
1
  import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-runtime";
2
+ import { PALETTE } from '../../../analyze/select/tui/theme.js';
2
3
  import { Box, Text } from 'ink';
3
4
  import { useImmediateInput } from '../../../analyze/select/tui/hooks/useImmediateInput.js';
4
5
  export function PreviewStep({ componentTypes, designTokens, spaceId, environmentId, stepNumber, totalSteps, onConfirm, onSaveFiles, onQuit, }) {
@@ -30,7 +31,7 @@ export function PreviewStep({ componentTypes, designTokens, spaceId, environment
30
31
  function EntityRows({ label, summary }) {
31
32
  if (!summary.created && !summary.updated && !summary.unchanged && !summary.conflicts && !summary.failed)
32
33
  return null;
33
- return (_jsxs(_Fragment, { children: [_jsx(Box, { gap: 1, marginTop: 1, children: _jsx(Text, { bold: true, dimColor: true, children: label }) }), summary.created > 0 && (_jsxs(Box, { gap: 1, children: [_jsx(Text, { color: "green", children: " \uFF0B" }), _jsxs(Text, { children: [summary.created, " will be created"] })] })), summary.updated > 0 && (_jsxs(Box, { gap: 1, children: [_jsx(Text, { color: "yellow", children: " \uFF5E" }), _jsxs(Text, { children: [summary.updated, " will be updated"] })] })), summary.unchanged > 0 && (_jsxs(Box, { gap: 1, children: [_jsx(Text, { dimColor: true, children: " \u00B7" }), _jsxs(Text, { dimColor: true, children: [summary.unchanged, " unchanged"] })] })), summary.conflicts > 0 && (_jsxs(Box, { gap: 1, children: [_jsx(Text, { color: "red", children: " \u2717" }), _jsxs(Text, { color: "red", children: [summary.conflicts, " conflict", summary.conflicts !== 1 ? 's' : '', " \u2014 resolve before pushing"] })] })), summary.failed > 0 && (_jsxs(Box, { gap: 1, children: [_jsx(Text, { color: "red", children: " \u2717" }), _jsxs(Text, { color: "red", children: [summary.failed, " failed \u2014 check logs"] })] }))] }));
34
+ return (_jsxs(_Fragment, { children: [_jsx(Box, { gap: 1, marginTop: 1, children: _jsx(Text, { bold: true, dimColor: true, children: label }) }), summary.created > 0 && (_jsxs(Box, { gap: 1, children: [_jsx(Text, { color: PALETTE.success, children: " \uFF0B" }), _jsxs(Text, { children: [summary.created, " will be created"] })] })), summary.updated > 0 && (_jsxs(Box, { gap: 1, children: [_jsx(Text, { color: PALETTE.warning, children: " \uFF5E" }), _jsxs(Text, { children: [summary.updated, " will be updated"] })] })), summary.unchanged > 0 && (_jsxs(Box, { gap: 1, children: [_jsx(Text, { dimColor: true, children: " \u00B7" }), _jsxs(Text, { dimColor: true, children: [summary.unchanged, " unchanged"] })] })), summary.conflicts > 0 && (_jsxs(Box, { gap: 1, children: [_jsx(Text, { color: PALETTE.error, children: " \u2717" }), _jsxs(Text, { color: PALETTE.error, children: [summary.conflicts, " conflict", summary.conflicts !== 1 ? 's' : '', " \u2014 resolve before pushing"] })] })), summary.failed > 0 && (_jsxs(Box, { gap: 1, children: [_jsx(Text, { color: PALETTE.error, children: " \u2717" }), _jsxs(Text, { color: PALETTE.error, children: [summary.failed, " failed \u2014 check logs"] })] }))] }));
34
35
  }
35
36
  return (_jsxs(Box, { flexDirection: "column", gap: 1, paddingX: 2, paddingY: 1, children: [_jsxs(Box, { flexDirection: "column", gap: 0, children: [_jsx(Text, { dimColor: true, children: '─'.repeat(40) }), _jsxs(Box, { gap: 1, children: [_jsxs(Text, { bold: true, children: ["Step ", stepNumber, " of ", totalSteps] }), _jsx(Text, { bold: true, children: "\u2014" }), _jsx(Text, { bold: true, children: "Push to Contentful" })] }), _jsx(Text, { dimColor: true, children: '─'.repeat(40) })] }), hasAnything ? (_jsxs(_Fragment, { children: [_jsx(Text, { children: "Here's what will happen in your space:" }), _jsxs(Box, { flexDirection: "column", gap: 0, children: [hasComponents && _jsx(EntityRows, { label: "ComponentTypes", summary: componentTypes }), hasTokens && _jsx(EntityRows, { label: "Design Tokens", summary: designTokens })] })] })) : (_jsx(Text, { dimColor: true, children: "Nothing to push \u2014 everything is already up to date." })), _jsxs(Box, { gap: 1, marginTop: 1, children: [_jsx(Text, { dimColor: true, children: "Space:" }), _jsx(Text, { children: spaceId }), _jsx(Text, { dimColor: true, children: "/" }), _jsx(Text, { dimColor: true, children: "Environment:" }), _jsx(Text, { children: environmentId })] }), _jsxs(Box, { gap: 3, marginTop: 1, children: [_jsx(Text, { dimColor: true, children: "[Enter] Push to Contentful" }), onSaveFiles && _jsx(Text, { dimColor: true, children: "[s] Save files instead" }), _jsx(Text, { dimColor: true, children: "[q] Cancel" })] })] }));
36
37
  }
@@ -6,13 +6,6 @@ type PushDecisionGateStepProps = {
6
6
  fileList: string;
7
7
  onChoice: (choice: PushDecisionChoice) => void;
8
8
  onQuit: () => void;
9
- /**
10
- * Skip-credentials spec — Task 3. When the operator advanced past the
11
- * credentials screen via the skip path, push options are not actually
12
- * usable (we never validated a token). Render all three rows for visual
13
- * continuity but disable "Save AND push" and "Push only", with the
14
- * `(unavailable — credentials skipped)` suffix.
15
- */
16
9
  pushDisabled?: boolean;
17
10
  };
18
11
  export declare function PushDecisionGateStep({ summary, context, onChoice, onQuit, pushDisabled, }: PushDecisionGateStepProps): React.ReactElement;
@@ -1,5 +1,6 @@
1
1
  import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
2
2
  import { useState } from 'react';
3
+ import { PALETTE } from '../../../analyze/select/tui/theme.js';
3
4
  import { Box, Text } from 'ink';
4
5
  import { useImmediateInput } from '../../../analyze/select/tui/hooks/useImmediateInput.js';
5
6
  const OPTIONS = [
@@ -9,9 +10,6 @@ const OPTIONS = [
9
10
  ];
10
11
  const SAVE_ONLY_INDEX = OPTIONS.findIndex((o) => o.value === 'save-only');
11
12
  export function PushDecisionGateStep({ summary, context, onChoice, onQuit, pushDisabled = false, }) {
12
- // When push is disabled, the cursor defaults to "Save only" (the only
13
- // selectable row). When push is enabled, "Save AND push" is the default —
14
- // matches the existing scope-gate UX.
15
13
  const [cursor, setCursor] = useState(pushDisabled ? SAVE_ONLY_INDEX : 0);
16
14
  function isSelectable(index) {
17
15
  if (!pushDisabled)
@@ -43,7 +41,6 @@ export function PushDecisionGateStep({ summary, context, onChoice, onQuit, pushD
43
41
  }
44
42
  if (input === 'j' || key.downArrow) {
45
43
  setCursor((c) => {
46
- // Walk forward to the next selectable row. If none, stay put.
47
44
  for (let i = c + 1; i < OPTIONS.length; i++) {
48
45
  if (isSelectable(i))
49
46
  return i;
@@ -67,10 +64,10 @@ export function PushDecisionGateStep({ summary, context, onChoice, onQuit, pushD
67
64
  return;
68
65
  }
69
66
  });
70
- return (_jsxs(Box, { flexDirection: "column", gap: 1, paddingX: 2, paddingY: 1, children: [_jsx(Text, { color: "green", children: "\u2713 Generation complete" }), _jsx(Text, { dimColor: true, children: summary }), _jsx(Box, { marginTop: 1, children: _jsx(Text, { children: context }) }), _jsx(Box, { flexDirection: "column", marginTop: 1, children: OPTIONS.map((opt, i) => {
67
+ return (_jsxs(Box, { flexDirection: "column", gap: 1, paddingX: 2, paddingY: 1, children: [_jsx(Text, { color: PALETTE.success, children: "\u2713 Generation complete" }), _jsx(Text, { dimColor: true, children: summary }), _jsx(Box, { marginTop: 1, children: _jsx(Text, { children: context }) }), _jsx(Box, { flexDirection: "column", marginTop: 1, children: OPTIONS.map((opt, i) => {
71
68
  const selected = i === cursor;
72
69
  const disabled = pushDisabled && opt.value !== 'save-only';
73
70
  const suffix = disabled ? ' (unavailable — credentials skipped)' : '';
74
- return (_jsxs(Text, { color: selected ? 'cyan' : undefined, dimColor: disabled, children: [selected ? '›' : ' ', " [", opt.shortcut, "] ", opt.label, suffix] }, opt.value));
71
+ return (_jsxs(Text, { color: selected ? PALETTE.info : undefined, dimColor: disabled, children: [selected ? '›' : ' ', " [", opt.shortcut, "] ", opt.label, suffix] }, opt.value));
75
72
  }) }), _jsxs(Box, { gap: 3, marginTop: 1, children: [_jsx(Text, { dimColor: true, children: "[Enter] Confirm" }), _jsx(Text, { dimColor: true, children: "[j/k] Move" }), _jsx(Text, { dimColor: true, children: "[q] Quit" })] })] }));
76
73
  }
@@ -1,5 +1,6 @@
1
1
  import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
2
2
  import { useEffect, useState } from 'react';
3
+ import { PALETTE } from '../../../analyze/select/tui/theme.js';
3
4
  import { Box, Text } from 'ink';
4
5
  const SPINNER_FRAMES = ['⠋', '⠙', '⠹', '⠸', '⠼', '⠴', '⠦', '⠧', '⠇', '⠏'];
5
6
  export function PushingStep({ stepNumber, totalSteps, progress }) {
@@ -19,5 +20,5 @@ export function PushingStep({ stepNumber, totalSteps, progress }) {
19
20
  const operationId = progress && progress.kind === 'queued' ? progress.operationId : null;
20
21
  const showGlobal = progress && progress.kind === 'progress';
21
22
  const showCurrent = progress && progress.kind === 'progress' && progress.current ? progress.current : null;
22
- return (_jsxs(Box, { flexDirection: "column", gap: 1, paddingX: 2, paddingY: 1, children: [_jsxs(Box, { flexDirection: "column", gap: 0, children: [_jsx(Text, { dimColor: true, children: '─'.repeat(40) }), _jsxs(Box, { gap: 1, children: [_jsxs(Text, { bold: true, children: ["Step ", stepNumber, " of ", totalSteps] }), _jsx(Text, { bold: true, children: "\u2014" }), _jsx(Text, { bold: true, children: "Push to Contentful" })] }), _jsx(Text, { dimColor: true, children: '─'.repeat(40) })] }), _jsx(Text, { children: "Writing component types and design tokens to your Contentful space..." }), operationId && (_jsxs(Box, { gap: 1, children: [_jsx(Text, { dimColor: true, children: "Operation:" }), _jsx(Text, { children: operationId })] })), showGlobal && progress && progress.kind === 'progress' && (_jsxs(Box, { gap: 1, children: [_jsx(Text, { color: "cyan", children: SPINNER_FRAMES[frame] }), _jsxs(Text, { dimColor: true, children: [progress.processed, "/", progress.total, " entities"] })] })), showCurrent && (_jsxs(Box, { gap: 1, children: [_jsx(Text, { dimColor: true, children: "Now processing:" }), _jsx(Text, { children: showCurrent })] })), _jsx(Box, { marginTop: 1, children: _jsxs(Text, { dimColor: true, children: ["Elapsed: ", elapsedStr] }) })] }));
23
+ return (_jsxs(Box, { flexDirection: "column", gap: 1, paddingX: 2, paddingY: 1, children: [_jsxs(Box, { flexDirection: "column", gap: 0, children: [_jsx(Text, { dimColor: true, children: '─'.repeat(40) }), _jsxs(Box, { gap: 1, children: [_jsxs(Text, { bold: true, children: ["Step ", stepNumber, " of ", totalSteps] }), _jsx(Text, { bold: true, children: "\u2014" }), _jsx(Text, { bold: true, children: "Push to Contentful" })] }), _jsx(Text, { dimColor: true, children: '─'.repeat(40) })] }), _jsx(Text, { children: "Writing component types and design tokens to your Contentful space..." }), operationId && (_jsxs(Box, { gap: 1, children: [_jsx(Text, { dimColor: true, children: "Operation:" }), _jsx(Text, { children: operationId })] })), showGlobal && progress && progress.kind === 'progress' && (_jsxs(Box, { gap: 1, children: [_jsx(Text, { color: PALETTE.info, children: SPINNER_FRAMES[frame] }), _jsxs(Text, { dimColor: true, children: [progress.processed, "/", progress.total, " entities"] })] })), showCurrent && (_jsxs(Box, { gap: 1, children: [_jsx(Text, { dimColor: true, children: "Now processing:" }), _jsx(Text, { children: showCurrent })] })), _jsx(Box, { marginTop: 1, children: _jsxs(Text, { dimColor: true, children: ["Elapsed: ", elapsedStr] }) })] }));
23
24
  }
@@ -5,6 +5,9 @@ type RunningStepProps = {
5
5
  title: string;
6
6
  description: string;
7
7
  detail?: string;
8
+ /** Optional second progress line (own spinner) — e.g. composition resolution
9
+ * running after the file scan on the extracting screen. */
10
+ secondaryDetail?: string;
8
11
  };
9
- export declare function RunningStep({ stepNumber, totalSteps, title, description, detail, }: RunningStepProps): React.ReactElement;
12
+ export declare function RunningStep({ stepNumber, totalSteps, title, description, detail, secondaryDetail, }: RunningStepProps): React.ReactElement;
10
13
  export {};
@@ -1,8 +1,9 @@
1
1
  import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
2
2
  import { useEffect, useState } from 'react';
3
+ import { PALETTE } from '../../../analyze/select/tui/theme.js';
3
4
  import { Box, Text } from 'ink';
4
5
  const SPINNER_FRAMES = ['⠋', '⠙', '⠹', '⠸', '⠼', '⠴', '⠦', '⠧', '⠇', '⠏'];
5
- export function RunningStep({ stepNumber, totalSteps, title, description, detail, }) {
6
+ export function RunningStep({ stepNumber, totalSteps, title, description, detail, secondaryDetail, }) {
6
7
  const [frame, setFrame] = useState(0);
7
8
  const [elapsed, setElapsed] = useState(0);
8
9
  useEffect(() => {
@@ -16,5 +17,5 @@ export function RunningStep({ stepNumber, totalSteps, title, description, detail
16
17
  const mins = Math.floor(elapsed / 60);
17
18
  const secs = elapsed % 60;
18
19
  const elapsedStr = mins > 0 ? `${mins}m ${secs}s` : `${secs}s`;
19
- return (_jsxs(Box, { flexDirection: "column", gap: 1, paddingX: 2, paddingY: 1, children: [_jsxs(Box, { flexDirection: "column", gap: 0, children: [_jsx(Text, { dimColor: true, children: '─'.repeat(40) }), _jsxs(Box, { gap: 1, children: [_jsxs(Text, { bold: true, children: ["Step ", stepNumber, " of ", totalSteps] }), _jsx(Text, { bold: true, children: "\u2014" }), _jsx(Text, { bold: true, children: title })] }), _jsx(Text, { dimColor: true, children: '─'.repeat(40) })] }), _jsx(Text, { children: description }), _jsxs(Box, { gap: 1, marginTop: 1, children: [_jsx(Text, { color: "cyan", children: SPINNER_FRAMES[frame] }), _jsx(Text, { dimColor: true, children: detail ?? 'Running...' })] }), _jsx(Box, { marginTop: 1, children: _jsxs(Text, { dimColor: true, children: ["Elapsed: ", elapsedStr] }) })] }));
20
+ return (_jsxs(Box, { flexDirection: "column", gap: 1, paddingX: 2, paddingY: 1, children: [_jsxs(Box, { flexDirection: "column", gap: 0, children: [_jsx(Text, { dimColor: true, children: '─'.repeat(40) }), _jsxs(Box, { gap: 1, children: [_jsxs(Text, { bold: true, children: ["Step ", stepNumber, " of ", totalSteps] }), _jsx(Text, { bold: true, children: "\u2014" }), _jsx(Text, { bold: true, children: title })] }), _jsx(Text, { dimColor: true, children: '─'.repeat(40) })] }), _jsx(Text, { children: description }), _jsxs(Box, { gap: 1, marginTop: 1, children: [_jsx(Text, { color: PALETTE.info, children: SPINNER_FRAMES[frame] }), _jsx(Text, { dimColor: true, children: detail ?? 'Running...' })] }), secondaryDetail !== undefined && (_jsxs(Box, { gap: 1, children: [_jsx(Text, { color: PALETTE.info, children: SPINNER_FRAMES[(frame + 5) % SPINNER_FRAMES.length] }), _jsx(Text, { dimColor: true, children: secondaryDetail })] })), _jsx(Box, { marginTop: 1, children: _jsxs(Text, { dimColor: true, children: ["Elapsed: ", elapsedStr] }) })] }));
20
21
  }
@@ -4,6 +4,10 @@ export type ScopeComponent = {
4
4
  componentId: string;
5
5
  aiDecision?: 'accepted' | 'rejected' | 'failed' | null;
6
6
  aiReason?: string | null;
7
+ slots?: Array<{
8
+ name: string;
9
+ allowedComponents: string[];
10
+ }>;
7
11
  };
8
12
  export type ScopeGateStepProps = {
9
13
  components: ScopeComponent[];
@@ -21,3 +25,23 @@ export type ScopeGateStepProps = {
21
25
  onCancelAutoFilter?: () => void;
22
26
  };
23
27
  export declare function ScopeGateStep({ components, onConfirm, onQuit, aiFilterStatus, aiFilterProgress, aiFilterError, onCancelAutoFilter, }: ScopeGateStepProps): React.ReactElement;
28
+ export declare function sideColumnLabelStyle(input: {
29
+ isCycle: boolean;
30
+ isSelected: boolean;
31
+ focused: boolean;
32
+ }): {
33
+ nameColor: string | undefined;
34
+ nameBold: boolean;
35
+ nameInverse: boolean;
36
+ nameUnderline: boolean;
37
+ suffixColor: string | undefined;
38
+ suffixDim: boolean;
39
+ suffixInverse: boolean;
40
+ suffixUnderline: boolean;
41
+ };
42
+ export declare function computeColumnWindow(total: number, cursor: number, visibleCount: number): {
43
+ start: number;
44
+ end: number;
45
+ above: number;
46
+ below: number;
47
+ };