@agents-inc/cli 0.32.1 → 0.34.1

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 (212) hide show
  1. package/CHANGELOG.md +16 -0
  2. package/README.md +7 -7
  3. package/config/skills-matrix.yaml +1 -1
  4. package/config/stacks.yaml +1 -1
  5. package/dist/{chunk-OMV7TLWD.js → chunk-2LUXM5FB.js} +26 -89
  6. package/dist/chunk-2LUXM5FB.js.map +1 -0
  7. package/dist/{chunk-Z4TWOP3H.js → chunk-5YNZJ5TP.js} +2 -2
  8. package/dist/{chunk-UX2H2K2G.js → chunk-A5CYQQVG.js} +2 -2
  9. package/dist/chunk-ALS7SH7X.js +120 -0
  10. package/dist/chunk-ALS7SH7X.js.map +1 -0
  11. package/dist/{chunk-BZQBJP34.js → chunk-ANGAZ444.js} +2 -2
  12. package/dist/{chunk-IZZ4IIEG.js → chunk-B47QYIUL.js} +4 -4
  13. package/dist/{chunk-5PIKNCZX.js → chunk-CB7GYRUP.js} +5 -5
  14. package/dist/{chunk-4RAY5AOI.js → chunk-CEWNZQMH.js} +3 -3
  15. package/dist/{chunk-R74PZWQS.js → chunk-GGHH3KR2.js} +5 -5
  16. package/dist/chunk-GGHH3KR2.js.map +1 -0
  17. package/dist/{chunk-UICL22RT.js → chunk-GIFEDW27.js} +4 -4
  18. package/dist/{chunk-ODUOU55D.js → chunk-GVMA2EKC.js} +2 -2
  19. package/dist/chunk-HTTPKSL6.js +31 -0
  20. package/dist/chunk-HTTPKSL6.js.map +1 -0
  21. package/dist/{chunk-FJQRVFMB.js → chunk-JXMRTHDT.js} +2 -2
  22. package/dist/{chunk-PBEHPQLK.js → chunk-JZOLJVWA.js} +55 -20
  23. package/dist/chunk-JZOLJVWA.js.map +1 -0
  24. package/dist/{chunk-YND42IXK.js → chunk-KENWMEKN.js} +11 -9
  25. package/dist/chunk-KENWMEKN.js.map +1 -0
  26. package/dist/{chunk-IYG2LAIM.js → chunk-LFHZBF6N.js} +5 -17
  27. package/dist/chunk-LFHZBF6N.js.map +1 -0
  28. package/dist/{chunk-SO22IQPY.js → chunk-MZB3GGOH.js} +2 -2
  29. package/dist/chunk-MZB3GGOH.js.map +1 -0
  30. package/dist/{chunk-BZN2Z5P7.js → chunk-NLR6Z37M.js} +1 -1
  31. package/dist/chunk-NLR6Z37M.js.map +1 -0
  32. package/dist/{chunk-OGJIZ6QH.js → chunk-OKILA27U.js} +122 -232
  33. package/dist/chunk-OKILA27U.js.map +1 -0
  34. package/dist/{chunk-A27LOC4Z.js → chunk-QC37C32G.js} +2 -2
  35. package/dist/{chunk-3ZOIOVKT.js → chunk-R3AD6XBJ.js} +4 -4
  36. package/dist/chunk-R3AD6XBJ.js.map +1 -0
  37. package/dist/{chunk-LGUI3PMO.js → chunk-TKB4O2RY.js} +9 -9
  38. package/dist/chunk-TKB4O2RY.js.map +1 -0
  39. package/dist/{chunk-MM7NK5N2.js → chunk-TM4I4EHK.js} +5 -13
  40. package/dist/chunk-TM4I4EHK.js.map +1 -0
  41. package/dist/{chunk-R3XFQKPG.js → chunk-VEZ2GZEK.js} +2 -2
  42. package/dist/{chunk-WEUVWHMA.js → chunk-X7SPCWY6.js} +8 -8
  43. package/dist/{chunk-EMJ2ZKS7.js → chunk-XYCN2GCV.js} +3 -3
  44. package/dist/{chunk-LAPCUV4D.js → chunk-YCS7GF6Y.js} +2 -4
  45. package/dist/chunk-YCS7GF6Y.js.map +1 -0
  46. package/dist/{chunk-QPTOIZAT.js → chunk-YPJKOM42.js} +2 -2
  47. package/dist/{chunk-FZGYSLJL.js → chunk-ZE355C6C.js} +2 -2
  48. package/dist/{chunk-B2UBHA66.js → chunk-ZI5EBHCC.js} +26 -35
  49. package/dist/chunk-ZI5EBHCC.js.map +1 -0
  50. package/dist/{chunk-W2ZSCZ2U.js → chunk-ZP4BI6J2.js} +4 -4
  51. package/dist/commands/build/marketplace.js +3 -3
  52. package/dist/commands/build/plugins.js +5 -5
  53. package/dist/commands/build/stack.js +5 -5
  54. package/dist/commands/compile.js +7 -7
  55. package/dist/commands/compile.js.map +1 -1
  56. package/dist/commands/config/get.js +4 -4
  57. package/dist/commands/config/index.js +5 -5
  58. package/dist/commands/config/path.js +4 -4
  59. package/dist/commands/config/set-project.js +4 -4
  60. package/dist/commands/config/show.js +5 -5
  61. package/dist/commands/config/unset-project.js +4 -4
  62. package/dist/commands/diff.js +5 -5
  63. package/dist/commands/diff.js.map +1 -1
  64. package/dist/commands/doctor.js +7 -7
  65. package/dist/commands/doctor.js.map +1 -1
  66. package/dist/commands/edit.js +28 -31
  67. package/dist/commands/edit.js.map +1 -1
  68. package/dist/commands/eject.js +5 -5
  69. package/dist/commands/eject.js.map +1 -1
  70. package/dist/commands/import/skill.js +5 -5
  71. package/dist/commands/info.js +6 -6
  72. package/dist/commands/info.js.map +1 -1
  73. package/dist/commands/init.js +35 -41
  74. package/dist/commands/init.js.map +1 -1
  75. package/dist/commands/list.js +5 -5
  76. package/dist/commands/list.js.map +1 -1
  77. package/dist/commands/new/agent.js +5 -5
  78. package/dist/commands/new/skill.js +5 -5
  79. package/dist/commands/new/skill.js.map +1 -1
  80. package/dist/commands/outdated.js +5 -5
  81. package/dist/commands/outdated.js.map +1 -1
  82. package/dist/commands/search.js +7 -7
  83. package/dist/commands/uninstall.js +6 -6
  84. package/dist/commands/update.js +7 -7
  85. package/dist/commands/update.js.map +1 -1
  86. package/dist/commands/validate.js +5 -5
  87. package/dist/commands/version/bump.js +4 -4
  88. package/dist/commands/version/index.js +4 -4
  89. package/dist/commands/version/set.js +4 -4
  90. package/dist/commands/version/show.js +4 -4
  91. package/dist/components/skill-search/skill-search.js +3 -3
  92. package/dist/components/wizard/category-grid.js +2 -2
  93. package/dist/components/wizard/category-grid.test.js +34 -66
  94. package/dist/components/wizard/category-grid.test.js.map +1 -1
  95. package/dist/components/wizard/domain-selection.js +5 -5
  96. package/dist/components/wizard/help-modal.js +2 -2
  97. package/dist/components/wizard/menu-item.js +2 -2
  98. package/dist/components/wizard/search-modal.js +2 -2
  99. package/dist/components/wizard/search-modal.test.js +2 -2
  100. package/dist/components/wizard/section-progress.js +2 -2
  101. package/dist/components/wizard/section-progress.test.js +2 -2
  102. package/dist/components/wizard/source-grid.js +4 -4
  103. package/dist/components/wizard/source-grid.test.js +4 -4
  104. package/dist/components/wizard/stack-selection.js +8 -8
  105. package/dist/components/wizard/step-build.js +7 -7
  106. package/dist/components/wizard/step-build.test.js +17 -17
  107. package/dist/components/wizard/step-build.test.js.map +1 -1
  108. package/dist/components/wizard/step-confirm.js +3 -3
  109. package/dist/components/wizard/step-confirm.test.js +6 -6
  110. package/dist/components/wizard/step-refine.js +2 -2
  111. package/dist/components/wizard/step-refine.test.js +2 -2
  112. package/dist/components/wizard/step-settings.js +5 -5
  113. package/dist/components/wizard/step-settings.test.js +12 -12
  114. package/dist/components/wizard/step-settings.test.js.map +1 -1
  115. package/dist/components/wizard/step-sources.js +9 -9
  116. package/dist/components/wizard/step-sources.test.js +10 -10
  117. package/dist/components/wizard/step-stack.js +10 -10
  118. package/dist/components/wizard/step-stack.test.js +19 -23
  119. package/dist/components/wizard/step-stack.test.js.map +1 -1
  120. package/dist/components/wizard/view-title.js +2 -2
  121. package/dist/components/wizard/wizard-layout.js +7 -7
  122. package/dist/components/wizard/wizard-tabs.js +2 -2
  123. package/dist/components/wizard/wizard-tabs.test.js +7 -8
  124. package/dist/components/wizard/wizard-tabs.test.js.map +1 -1
  125. package/dist/components/wizard/wizard.js +23 -23
  126. package/dist/config/skills-matrix.yaml +1 -1
  127. package/dist/config/stacks.yaml +1 -1
  128. package/dist/hooks/init.js +3 -3
  129. package/dist/{source-manager-SBPPLOQQ.js → source-manager-WJYANKDI.js} +4 -4
  130. package/dist/src/agents/developer/api-developer/agent.yaml +1 -1
  131. package/dist/src/agents/developer/cli-developer/agent.yaml +1 -1
  132. package/dist/src/agents/developer/web-architecture/agent.yaml +1 -1
  133. package/dist/src/agents/developer/web-developer/agent.yaml +1 -1
  134. package/dist/src/agents/meta/agent-summoner/agent.yaml +1 -1
  135. package/dist/src/agents/meta/agent-summoner/critical-reminders.md +1 -1
  136. package/dist/src/agents/meta/agent-summoner/critical-requirements.md +1 -1
  137. package/dist/src/agents/meta/agent-summoner/examples.md +2 -2
  138. package/dist/src/agents/meta/agent-summoner/workflow.md +3 -3
  139. package/dist/src/agents/meta/documentor/agent.yaml +1 -1
  140. package/dist/src/agents/meta/skill-summoner/agent.yaml +1 -1
  141. package/dist/src/agents/meta/skill-summoner/output-format.md +1 -1
  142. package/dist/src/agents/migration/cli-migrator/agent.yaml +1 -1
  143. package/dist/src/agents/pattern/pattern-scout/agent.yaml +1 -1
  144. package/dist/src/agents/pattern/web-pattern-critique/agent.yaml +1 -1
  145. package/dist/src/agents/planning/web-pm/agent.yaml +1 -1
  146. package/dist/src/agents/researcher/api-researcher/agent.yaml +1 -1
  147. package/dist/src/agents/researcher/web-researcher/agent.yaml +1 -1
  148. package/dist/src/agents/reviewer/api-reviewer/agent.yaml +1 -1
  149. package/dist/src/agents/reviewer/cli-reviewer/agent.yaml +1 -1
  150. package/dist/src/agents/reviewer/web-reviewer/agent.yaml +1 -1
  151. package/dist/src/agents/tester/cli-tester/agent.yaml +1 -1
  152. package/dist/src/agents/tester/web-tester/agent.yaml +1 -1
  153. package/dist/stores/wizard-store.js +4 -4
  154. package/dist/stores/wizard-store.test.js +5 -5
  155. package/package.json +8 -8
  156. package/src/agents/developer/api-developer/agent.yaml +1 -1
  157. package/src/agents/developer/cli-developer/agent.yaml +1 -1
  158. package/src/agents/developer/web-architecture/agent.yaml +1 -1
  159. package/src/agents/developer/web-developer/agent.yaml +1 -1
  160. package/src/agents/meta/agent-summoner/agent.yaml +1 -1
  161. package/src/agents/meta/agent-summoner/critical-reminders.md +1 -1
  162. package/src/agents/meta/agent-summoner/critical-requirements.md +1 -1
  163. package/src/agents/meta/agent-summoner/examples.md +2 -2
  164. package/src/agents/meta/agent-summoner/workflow.md +3 -3
  165. package/src/agents/meta/documentor/agent.yaml +1 -1
  166. package/src/agents/meta/skill-summoner/agent.yaml +1 -1
  167. package/src/agents/meta/skill-summoner/output-format.md +1 -1
  168. package/src/agents/migration/cli-migrator/agent.yaml +1 -1
  169. package/src/agents/pattern/pattern-scout/agent.yaml +1 -1
  170. package/src/agents/pattern/web-pattern-critique/agent.yaml +1 -1
  171. package/src/agents/planning/web-pm/agent.yaml +1 -1
  172. package/src/agents/researcher/api-researcher/agent.yaml +1 -1
  173. package/src/agents/researcher/web-researcher/agent.yaml +1 -1
  174. package/src/agents/reviewer/api-reviewer/agent.yaml +1 -1
  175. package/src/agents/reviewer/cli-reviewer/agent.yaml +1 -1
  176. package/src/agents/reviewer/web-reviewer/agent.yaml +1 -1
  177. package/src/agents/tester/cli-tester/agent.yaml +1 -1
  178. package/src/agents/tester/web-tester/agent.yaml +1 -1
  179. package/dist/chunk-3ZOIOVKT.js.map +0 -1
  180. package/dist/chunk-B2UBHA66.js.map +0 -1
  181. package/dist/chunk-BZN2Z5P7.js.map +0 -1
  182. package/dist/chunk-H566H3MQ.js +0 -87
  183. package/dist/chunk-H566H3MQ.js.map +0 -1
  184. package/dist/chunk-IYG2LAIM.js.map +0 -1
  185. package/dist/chunk-LAPCUV4D.js.map +0 -1
  186. package/dist/chunk-LGUI3PMO.js.map +0 -1
  187. package/dist/chunk-MM7NK5N2.js.map +0 -1
  188. package/dist/chunk-O4D67NN7.js +0 -24
  189. package/dist/chunk-O4D67NN7.js.map +0 -1
  190. package/dist/chunk-OGJIZ6QH.js.map +0 -1
  191. package/dist/chunk-OMV7TLWD.js.map +0 -1
  192. package/dist/chunk-PBEHPQLK.js.map +0 -1
  193. package/dist/chunk-R74PZWQS.js.map +0 -1
  194. package/dist/chunk-SO22IQPY.js.map +0 -1
  195. package/dist/chunk-YND42IXK.js.map +0 -1
  196. /package/dist/{chunk-Z4TWOP3H.js.map → chunk-5YNZJ5TP.js.map} +0 -0
  197. /package/dist/{chunk-UX2H2K2G.js.map → chunk-A5CYQQVG.js.map} +0 -0
  198. /package/dist/{chunk-BZQBJP34.js.map → chunk-ANGAZ444.js.map} +0 -0
  199. /package/dist/{chunk-IZZ4IIEG.js.map → chunk-B47QYIUL.js.map} +0 -0
  200. /package/dist/{chunk-5PIKNCZX.js.map → chunk-CB7GYRUP.js.map} +0 -0
  201. /package/dist/{chunk-4RAY5AOI.js.map → chunk-CEWNZQMH.js.map} +0 -0
  202. /package/dist/{chunk-UICL22RT.js.map → chunk-GIFEDW27.js.map} +0 -0
  203. /package/dist/{chunk-ODUOU55D.js.map → chunk-GVMA2EKC.js.map} +0 -0
  204. /package/dist/{chunk-FJQRVFMB.js.map → chunk-JXMRTHDT.js.map} +0 -0
  205. /package/dist/{chunk-A27LOC4Z.js.map → chunk-QC37C32G.js.map} +0 -0
  206. /package/dist/{chunk-R3XFQKPG.js.map → chunk-VEZ2GZEK.js.map} +0 -0
  207. /package/dist/{chunk-WEUVWHMA.js.map → chunk-X7SPCWY6.js.map} +0 -0
  208. /package/dist/{chunk-EMJ2ZKS7.js.map → chunk-XYCN2GCV.js.map} +0 -0
  209. /package/dist/{chunk-QPTOIZAT.js.map → chunk-YPJKOM42.js.map} +0 -0
  210. /package/dist/{chunk-FZGYSLJL.js.map → chunk-ZE355C6C.js.map} +0 -0
  211. /package/dist/{chunk-W2ZSCZ2U.js.map → chunk-ZP4BI6J2.js.map} +0 -0
  212. /package/dist/{source-manager-SBPPLOQQ.js.map → source-manager-WJYANKDI.js.map} +0 -0
@@ -1 +1 @@
1
- {"version":3,"sources":["../../../src/cli/components/wizard/step-settings.test.tsx"],"sourcesContent":["import { render } from \"ink-testing-library\";\nimport { describe, expect, it, afterEach, beforeEach, vi } from \"vitest\";\nimport { StepSettings, type StepSettingsProps } from \"./step-settings\";\nimport {\n ESCAPE,\n ARROW_UP,\n ARROW_DOWN,\n INPUT_DELAY_MS,\n delay,\n} from \"../../lib/__tests__/test-constants\";\n\n// Mock source-manager\nvi.mock(\"../../lib/configuration/source-manager.js\", () => ({\n getSourceSummary: vi.fn(),\n addSource: vi.fn(),\n removeSource: vi.fn(),\n}));\n\n// Mock config\nvi.mock(\"../../lib/configuration/config.js\", () => ({\n DEFAULT_SOURCE: \"github:claude-collective/skills\",\n}));\n\nconst LOADING_SETTLE_MS = 200;\n\nconst defaultProps: StepSettingsProps = {\n projectDir: \"/test/project\",\n onClose: vi.fn(),\n};\n\nconst renderStepSettings = (props: Partial<StepSettingsProps> = {}) => {\n return render(<StepSettings {...defaultProps} {...props} />);\n};\n\ndescribe(\"StepSettings component\", () => {\n let cleanup: (() => void) | undefined;\n\n beforeEach(async () => {\n vi.resetAllMocks();\n\n const { getSourceSummary } = await import(\"../../lib/configuration/source-manager.js\");\n vi.mocked(getSourceSummary).mockResolvedValue({\n sources: [\n { name: \"public\", url: \"github:claude-collective/skills\", enabled: true },\n { name: \"acme-corp\", url: \"github:acme-corp/claude-skills\", enabled: true },\n ],\n localSkillCount: 3,\n pluginSkillCount: 1,\n });\n });\n\n afterEach(() => {\n cleanup?.();\n cleanup = undefined;\n });\n\n describe(\"rendering\", () => {\n it(\"should render the title\", async () => {\n const { lastFrame, unmount } = renderStepSettings();\n cleanup = unmount;\n\n await delay(LOADING_SETTLE_MS);\n const output = lastFrame();\n expect(output).toContain(\"Skill Sources\");\n });\n\n it(\"should render configured sources\", async () => {\n const { lastFrame, unmount } = renderStepSettings();\n cleanup = unmount;\n\n await delay(LOADING_SETTLE_MS);\n const output = lastFrame();\n expect(output).toContain(\"Public\");\n expect(output).toContain(\"acme-corp\");\n });\n\n it(\"should show default label for public source\", async () => {\n const { lastFrame, unmount } = renderStepSettings();\n cleanup = unmount;\n\n await delay(LOADING_SETTLE_MS);\n const output = lastFrame();\n expect(output).toContain(\"(default)\");\n });\n\n it(\"should show source URLs\", async () => {\n const { lastFrame, unmount } = renderStepSettings();\n cleanup = unmount;\n\n await delay(LOADING_SETTLE_MS);\n const output = lastFrame();\n expect(output).toContain(\"github:claude-collective/skills\");\n expect(output).toContain(\"github:acme-corp/claude-skills\");\n });\n\n it(\"should show local skill count\", async () => {\n const { lastFrame, unmount } = renderStepSettings();\n cleanup = unmount;\n\n await delay(LOADING_SETTLE_MS);\n const output = lastFrame();\n expect(output).toContain(\"3\");\n expect(output).toContain(\".claude/skills/\");\n });\n\n it(\"should show plugin count\", async () => {\n const { lastFrame, unmount } = renderStepSettings();\n cleanup = unmount;\n\n await delay(LOADING_SETTLE_MS);\n const output = lastFrame();\n expect(output).toContain(\"1\");\n expect(output).toContain(\"installed plugins\");\n });\n\n it(\"should show add source input area\", async () => {\n const { lastFrame, unmount } = renderStepSettings();\n cleanup = unmount;\n\n await delay(LOADING_SETTLE_MS);\n const output = lastFrame();\n expect(output).toContain(\"Add source\");\n });\n\n it(\"should show loading state initially\", () => {\n const { lastFrame, unmount } = renderStepSettings();\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(\"Loading sources...\");\n });\n });\n\n describe(\"keyboard navigation\", () => {\n it(\"should navigate down with arrow down\", async () => {\n const { lastFrame, stdin, unmount } = renderStepSettings();\n cleanup = unmount;\n\n await delay(LOADING_SETTLE_MS);\n\n // Move focus down\n stdin.write(ARROW_DOWN);\n await delay(INPUT_DELAY_MS);\n\n const output = lastFrame();\n // The second source (acme-corp) should now be focused\n expect(output).toContain(\"acme-corp\");\n });\n\n it(\"should navigate up with arrow up\", async () => {\n const { lastFrame, stdin, unmount } = renderStepSettings();\n cleanup = unmount;\n\n await delay(LOADING_SETTLE_MS);\n\n // Move down then up\n stdin.write(ARROW_DOWN);\n await delay(INPUT_DELAY_MS);\n stdin.write(ARROW_UP);\n await delay(INPUT_DELAY_MS);\n\n const output = lastFrame();\n expect(output).toContain(\"Public\");\n });\n\n it(\"should not navigate above first item\", async () => {\n const { lastFrame, stdin, unmount } = renderStepSettings();\n cleanup = unmount;\n\n await delay(LOADING_SETTLE_MS);\n\n // Try to move up from first item\n stdin.write(ARROW_UP);\n await delay(INPUT_DELAY_MS);\n\n const output = lastFrame();\n expect(output).toContain(\"Public\");\n });\n });\n\n describe(\"escape to close\", () => {\n it(\"should call onClose when Escape is pressed\", async () => {\n const onClose = vi.fn();\n const { stdin, unmount } = renderStepSettings({ onClose });\n cleanup = unmount;\n\n await delay(LOADING_SETTLE_MS);\n stdin.write(ESCAPE);\n await delay(INPUT_DELAY_MS);\n\n expect(onClose).toHaveBeenCalledTimes(1);\n });\n });\n\n describe(\"add source input mode\", () => {\n it(\"should enter add source mode on 'a' key\", async () => {\n const { lastFrame, stdin, unmount } = renderStepSettings();\n cleanup = unmount;\n\n await delay(LOADING_SETTLE_MS);\n\n stdin.write(\"a\");\n await delay(INPUT_DELAY_MS);\n\n const output = lastFrame();\n // Should show cursor block character indicating input mode\n expect(output).toContain(\"\\u2588\");\n });\n\n it(\"should exit add source mode on Escape\", async () => {\n const onClose = vi.fn();\n const { lastFrame, stdin, unmount } = renderStepSettings({ onClose });\n cleanup = unmount;\n\n await delay(LOADING_SETTLE_MS);\n\n // Enter add mode\n stdin.write(\"a\");\n await delay(INPUT_DELAY_MS);\n\n // Escape from add mode (should NOT close settings)\n stdin.write(ESCAPE);\n await delay(INPUT_DELAY_MS);\n\n expect(onClose).not.toHaveBeenCalled();\n\n const output = lastFrame();\n // Should still show the settings view\n expect(output).toContain(\"Skill Sources\");\n });\n\n it(\"should show hint text for add mode\", async () => {\n const { lastFrame, stdin, unmount } = renderStepSettings();\n cleanup = unmount;\n\n await delay(LOADING_SETTLE_MS);\n\n stdin.write(\"a\");\n await delay(INPUT_DELAY_MS);\n\n const output = lastFrame();\n expect(output).toContain(\"ENTER submit\");\n expect(output).toContain(\"ESC cancel\");\n });\n\n it(\"should show hint text for normal mode\", async () => {\n const { lastFrame, unmount } = renderStepSettings();\n cleanup = unmount;\n\n await delay(LOADING_SETTLE_MS);\n\n const output = lastFrame();\n expect(output).toContain(\"DEL remove\");\n expect(output).toContain(\"close\");\n });\n });\n\n describe(\"edge cases\", () => {\n it(\"should handle empty sources list gracefully\", async () => {\n const { getSourceSummary } = await import(\"../../lib/configuration/source-manager.js\");\n vi.mocked(getSourceSummary).mockResolvedValue({\n sources: [{ name: \"public\", url: \"github:claude-collective/skills\", enabled: true }],\n localSkillCount: 0,\n pluginSkillCount: 0,\n });\n\n const { lastFrame, unmount } = renderStepSettings();\n cleanup = unmount;\n\n await delay(LOADING_SETTLE_MS);\n\n const output = lastFrame();\n expect(output).toContain(\"Public\");\n expect(output).toContain(\"0\");\n });\n\n it(\"should handle getSourceSummary failure gracefully\", async () => {\n const { getSourceSummary } = await import(\"../../lib/configuration/source-manager.js\");\n vi.mocked(getSourceSummary).mockRejectedValue(new Error(\"Config read failed\"));\n\n const { lastFrame, unmount } = renderStepSettings();\n cleanup = unmount;\n\n await delay(LOADING_SETTLE_MS);\n\n const output = lastFrame();\n // Should show fallback with default source\n expect(output).toContain(\"Public\");\n });\n });\n});\n"],"mappings":"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","names":[]}
1
+ {"version":3,"sources":["../../../src/cli/components/wizard/step-settings.test.tsx"],"sourcesContent":["import { render } from \"ink-testing-library\";\nimport { describe, expect, it, afterEach, beforeEach, vi } from \"vitest\";\nimport { StepSettings, type StepSettingsProps } from \"./step-settings\";\nimport {\n ESCAPE,\n ARROW_UP,\n ARROW_DOWN,\n INPUT_DELAY_MS,\n delay,\n} from \"../../lib/__tests__/test-constants\";\n\n// Mock source-manager\nvi.mock(\"../../lib/configuration/source-manager.js\", () => ({\n getSourceSummary: vi.fn(),\n addSource: vi.fn(),\n removeSource: vi.fn(),\n}));\n\n// Mock config\nvi.mock(\"../../lib/configuration/config.js\", () => ({\n DEFAULT_SOURCE: \"github:agents-inc/skills\",\n}));\n\nconst LOADING_SETTLE_MS = 200;\n\nconst defaultProps: StepSettingsProps = {\n projectDir: \"/test/project\",\n onClose: vi.fn(),\n};\n\nconst renderStepSettings = (props: Partial<StepSettingsProps> = {}) => {\n return render(<StepSettings {...defaultProps} {...props} />);\n};\n\ndescribe(\"StepSettings component\", () => {\n let cleanup: (() => void) | undefined;\n\n beforeEach(async () => {\n vi.resetAllMocks();\n\n const { getSourceSummary } = await import(\"../../lib/configuration/source-manager.js\");\n vi.mocked(getSourceSummary).mockResolvedValue({\n sources: [\n { name: \"public\", url: \"github:agents-inc/skills\", enabled: true },\n { name: \"acme-corp\", url: \"github:acme-corp/claude-skills\", enabled: true },\n ],\n localSkillCount: 3,\n pluginSkillCount: 1,\n });\n });\n\n afterEach(() => {\n cleanup?.();\n cleanup = undefined;\n });\n\n describe(\"rendering\", () => {\n it(\"should render the title\", async () => {\n const { lastFrame, unmount } = renderStepSettings();\n cleanup = unmount;\n\n await delay(LOADING_SETTLE_MS);\n const output = lastFrame();\n expect(output).toContain(\"Skill Sources\");\n });\n\n it(\"should render configured sources\", async () => {\n const { lastFrame, unmount } = renderStepSettings();\n cleanup = unmount;\n\n await delay(LOADING_SETTLE_MS);\n const output = lastFrame();\n expect(output).toContain(\"Public\");\n expect(output).toContain(\"acme-corp\");\n });\n\n it(\"should show default label for public source\", async () => {\n const { lastFrame, unmount } = renderStepSettings();\n cleanup = unmount;\n\n await delay(LOADING_SETTLE_MS);\n const output = lastFrame();\n expect(output).toContain(\"(default)\");\n });\n\n it(\"should show source URLs\", async () => {\n const { lastFrame, unmount } = renderStepSettings();\n cleanup = unmount;\n\n await delay(LOADING_SETTLE_MS);\n const output = lastFrame();\n expect(output).toContain(\"github:agents-inc/skills\");\n expect(output).toContain(\"github:acme-corp/claude-skills\");\n });\n\n it(\"should show local skill count\", async () => {\n const { lastFrame, unmount } = renderStepSettings();\n cleanup = unmount;\n\n await delay(LOADING_SETTLE_MS);\n const output = lastFrame();\n expect(output).toContain(\"3\");\n expect(output).toContain(\".claude/skills/\");\n });\n\n it(\"should show plugin count\", async () => {\n const { lastFrame, unmount } = renderStepSettings();\n cleanup = unmount;\n\n await delay(LOADING_SETTLE_MS);\n const output = lastFrame();\n expect(output).toContain(\"1\");\n expect(output).toContain(\"installed plugins\");\n });\n\n it(\"should show add source input area\", async () => {\n const { lastFrame, unmount } = renderStepSettings();\n cleanup = unmount;\n\n await delay(LOADING_SETTLE_MS);\n const output = lastFrame();\n expect(output).toContain(\"Add source\");\n });\n\n it(\"should show loading state initially\", () => {\n const { lastFrame, unmount } = renderStepSettings();\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(\"Loading sources...\");\n });\n });\n\n describe(\"keyboard navigation\", () => {\n it(\"should navigate down with arrow down\", async () => {\n const { lastFrame, stdin, unmount } = renderStepSettings();\n cleanup = unmount;\n\n await delay(LOADING_SETTLE_MS);\n\n // Move focus down\n stdin.write(ARROW_DOWN);\n await delay(INPUT_DELAY_MS);\n\n const output = lastFrame();\n // The second source (acme-corp) should now be focused\n expect(output).toContain(\"acme-corp\");\n });\n\n it(\"should navigate up with arrow up\", async () => {\n const { lastFrame, stdin, unmount } = renderStepSettings();\n cleanup = unmount;\n\n await delay(LOADING_SETTLE_MS);\n\n // Move down then up\n stdin.write(ARROW_DOWN);\n await delay(INPUT_DELAY_MS);\n stdin.write(ARROW_UP);\n await delay(INPUT_DELAY_MS);\n\n const output = lastFrame();\n expect(output).toContain(\"Public\");\n });\n\n it(\"should not navigate above first item\", async () => {\n const { lastFrame, stdin, unmount } = renderStepSettings();\n cleanup = unmount;\n\n await delay(LOADING_SETTLE_MS);\n\n // Try to move up from first item\n stdin.write(ARROW_UP);\n await delay(INPUT_DELAY_MS);\n\n const output = lastFrame();\n expect(output).toContain(\"Public\");\n });\n });\n\n describe(\"escape to close\", () => {\n it(\"should call onClose when Escape is pressed\", async () => {\n const onClose = vi.fn();\n const { stdin, unmount } = renderStepSettings({ onClose });\n cleanup = unmount;\n\n await delay(LOADING_SETTLE_MS);\n stdin.write(ESCAPE);\n await delay(INPUT_DELAY_MS);\n\n expect(onClose).toHaveBeenCalledTimes(1);\n });\n });\n\n describe(\"add source input mode\", () => {\n it(\"should enter add source mode on 'a' key\", async () => {\n const { lastFrame, stdin, unmount } = renderStepSettings();\n cleanup = unmount;\n\n await delay(LOADING_SETTLE_MS);\n\n stdin.write(\"a\");\n await delay(INPUT_DELAY_MS);\n\n const output = lastFrame();\n // Should show cursor block character indicating input mode\n expect(output).toContain(\"\\u2588\");\n });\n\n it(\"should exit add source mode on Escape\", async () => {\n const onClose = vi.fn();\n const { lastFrame, stdin, unmount } = renderStepSettings({ onClose });\n cleanup = unmount;\n\n await delay(LOADING_SETTLE_MS);\n\n // Enter add mode\n stdin.write(\"a\");\n await delay(INPUT_DELAY_MS);\n\n // Escape from add mode (should NOT close settings)\n stdin.write(ESCAPE);\n await delay(INPUT_DELAY_MS);\n\n expect(onClose).not.toHaveBeenCalled();\n\n const output = lastFrame();\n // Should still show the settings view\n expect(output).toContain(\"Skill Sources\");\n });\n\n it(\"should show hint text for add mode\", async () => {\n const { lastFrame, stdin, unmount } = renderStepSettings();\n cleanup = unmount;\n\n await delay(LOADING_SETTLE_MS);\n\n stdin.write(\"a\");\n await delay(INPUT_DELAY_MS);\n\n const output = lastFrame();\n expect(output).toContain(\"ENTER submit\");\n expect(output).toContain(\"ESC cancel\");\n });\n\n it(\"should show hint text for normal mode\", async () => {\n const { lastFrame, unmount } = renderStepSettings();\n cleanup = unmount;\n\n await delay(LOADING_SETTLE_MS);\n\n const output = lastFrame();\n expect(output).toContain(\"DEL remove\");\n expect(output).toContain(\"close\");\n });\n });\n\n describe(\"edge cases\", () => {\n it(\"should handle empty sources list gracefully\", async () => {\n const { getSourceSummary } = await import(\"../../lib/configuration/source-manager.js\");\n vi.mocked(getSourceSummary).mockResolvedValue({\n sources: [{ name: \"public\", url: \"github:agents-inc/skills\", enabled: true }],\n localSkillCount: 0,\n pluginSkillCount: 0,\n });\n\n const { lastFrame, unmount } = renderStepSettings();\n cleanup = unmount;\n\n await delay(LOADING_SETTLE_MS);\n\n const output = lastFrame();\n expect(output).toContain(\"Public\");\n expect(output).toContain(\"0\");\n });\n\n it(\"should handle getSourceSummary failure gracefully\", async () => {\n const { getSourceSummary } = await import(\"../../lib/configuration/source-manager.js\");\n vi.mocked(getSourceSummary).mockRejectedValue(new Error(\"Config read failed\"));\n\n const { lastFrame, unmount } = renderStepSettings();\n cleanup = unmount;\n\n await delay(LOADING_SETTLE_MS);\n\n const output = lastFrame();\n // Should show fallback with default source\n expect(output).toContain(\"Public\");\n });\n });\n});\n"],"mappings":"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","names":[]}
@@ -1,18 +1,18 @@
1
1
  #!/usr/bin/env node
2
2
  import {
3
3
  StepSources
4
- } from "../../chunk-WEUVWHMA.js";
5
- import "../../chunk-O4D67NN7.js";
6
- import "../../chunk-5PIKNCZX.js";
4
+ } from "../../chunk-X7SPCWY6.js";
5
+ import "../../chunk-CB7GYRUP.js";
7
6
  import "../../chunk-7SOPVGDV.js";
8
- import "../../chunk-A27LOC4Z.js";
9
- import "../../chunk-JMVWYAHT.js";
7
+ import "../../chunk-HTTPKSL6.js";
10
8
  import "../../chunk-DC5AK3LW.js";
11
- import "../../chunk-3ZOIOVKT.js";
12
- import "../../chunk-MM7NK5N2.js";
9
+ import "../../chunk-QC37C32G.js";
10
+ import "../../chunk-JMVWYAHT.js";
11
+ import "../../chunk-R3AD6XBJ.js";
12
+ import "../../chunk-TM4I4EHK.js";
13
13
  import "../../chunk-T4EXUIBY.js";
14
- import "../../chunk-BZN2Z5P7.js";
15
- import "../../chunk-LAPCUV4D.js";
14
+ import "../../chunk-NLR6Z37M.js";
15
+ import "../../chunk-YCS7GF6Y.js";
16
16
  import "../../chunk-DHET7RCE.js";
17
17
  export {
18
18
  StepSources
@@ -14,7 +14,7 @@ import {
14
14
  import {
15
15
  createMockMatrix,
16
16
  getTestSkill
17
- } from "../../chunk-BZQBJP34.js";
17
+ } from "../../chunk-ANGAZ444.js";
18
18
  import {
19
19
  afterEach,
20
20
  beforeEach,
@@ -25,22 +25,22 @@ import {
25
25
  } from "../../chunk-XY3XDVMI.js";
26
26
  import {
27
27
  StepSources
28
- } from "../../chunk-WEUVWHMA.js";
29
- import "../../chunk-O4D67NN7.js";
30
- import "../../chunk-5PIKNCZX.js";
28
+ } from "../../chunk-X7SPCWY6.js";
29
+ import "../../chunk-CB7GYRUP.js";
31
30
  import "../../chunk-7SOPVGDV.js";
32
- import "../../chunk-A27LOC4Z.js";
33
- import "../../chunk-JMVWYAHT.js";
31
+ import "../../chunk-HTTPKSL6.js";
34
32
  import "../../chunk-DC5AK3LW.js";
33
+ import "../../chunk-QC37C32G.js";
34
+ import "../../chunk-JMVWYAHT.js";
35
35
  import {
36
36
  useWizardStore
37
- } from "../../chunk-3ZOIOVKT.js";
38
- import "../../chunk-MM7NK5N2.js";
37
+ } from "../../chunk-R3AD6XBJ.js";
38
+ import "../../chunk-TM4I4EHK.js";
39
39
  import "../../chunk-T4EXUIBY.js";
40
- import "../../chunk-BZN2Z5P7.js";
40
+ import "../../chunk-NLR6Z37M.js";
41
41
  import {
42
42
  DEFAULT_BRANDING
43
- } from "../../chunk-LAPCUV4D.js";
43
+ } from "../../chunk-YCS7GF6Y.js";
44
44
  import {
45
45
  init_esm_shims
46
46
  } from "../../chunk-DHET7RCE.js";
@@ -1,17 +1,17 @@
1
1
  #!/usr/bin/env node
2
2
  import {
3
3
  StepStack
4
- } from "../../chunk-IZZ4IIEG.js";
5
- import "../../chunk-LGUI3PMO.js";
6
- import "../../chunk-O4D67NN7.js";
7
- import "../../chunk-SO22IQPY.js";
8
- import "../../chunk-H566H3MQ.js";
9
- import "../../chunk-QPTOIZAT.js";
10
- import "../../chunk-3ZOIOVKT.js";
11
- import "../../chunk-MM7NK5N2.js";
4
+ } from "../../chunk-B47QYIUL.js";
5
+ import "../../chunk-TKB4O2RY.js";
6
+ import "../../chunk-MZB3GGOH.js";
7
+ import "../../chunk-HTTPKSL6.js";
8
+ import "../../chunk-ALS7SH7X.js";
9
+ import "../../chunk-YPJKOM42.js";
10
+ import "../../chunk-R3AD6XBJ.js";
11
+ import "../../chunk-TM4I4EHK.js";
12
12
  import "../../chunk-T4EXUIBY.js";
13
- import "../../chunk-BZN2Z5P7.js";
14
- import "../../chunk-LAPCUV4D.js";
13
+ import "../../chunk-NLR6Z37M.js";
14
+ import "../../chunk-YCS7GF6Y.js";
15
15
  import "../../chunk-DHET7RCE.js";
16
16
  export {
17
17
  StepStack
@@ -16,7 +16,7 @@ import {
16
16
  createMockMatrix,
17
17
  createMockResolvedStack,
18
18
  createMockSkill
19
- } from "../../chunk-BZQBJP34.js";
19
+ } from "../../chunk-ANGAZ444.js";
20
20
  import {
21
21
  afterEach,
22
22
  beforeEach,
@@ -27,19 +27,19 @@ import {
27
27
  } from "../../chunk-XY3XDVMI.js";
28
28
  import {
29
29
  StepStack
30
- } from "../../chunk-IZZ4IIEG.js";
31
- import "../../chunk-LGUI3PMO.js";
32
- import "../../chunk-O4D67NN7.js";
33
- import "../../chunk-SO22IQPY.js";
34
- import "../../chunk-H566H3MQ.js";
35
- import "../../chunk-QPTOIZAT.js";
30
+ } from "../../chunk-B47QYIUL.js";
31
+ import "../../chunk-TKB4O2RY.js";
32
+ import "../../chunk-MZB3GGOH.js";
33
+ import "../../chunk-HTTPKSL6.js";
34
+ import "../../chunk-ALS7SH7X.js";
35
+ import "../../chunk-YPJKOM42.js";
36
36
  import {
37
37
  useWizardStore
38
- } from "../../chunk-3ZOIOVKT.js";
39
- import "../../chunk-MM7NK5N2.js";
38
+ } from "../../chunk-R3AD6XBJ.js";
39
+ import "../../chunk-TM4I4EHK.js";
40
40
  import "../../chunk-T4EXUIBY.js";
41
- import "../../chunk-BZN2Z5P7.js";
42
- import "../../chunk-LAPCUV4D.js";
41
+ import "../../chunk-NLR6Z37M.js";
42
+ import "../../chunk-YCS7GF6Y.js";
43
43
  import {
44
44
  init_esm_shims
45
45
  } from "../../chunk-DHET7RCE.js";
@@ -115,7 +115,7 @@ describe("StepStack component", () => {
115
115
  const { lastFrame, unmount } = render(/* @__PURE__ */ jsx(StepStack, { matrix: mockMatrix }));
116
116
  cleanup = unmount;
117
117
  const output = lastFrame();
118
- globalExpect(output).toContain("Choose a stack");
118
+ globalExpect(output).toContain("[1] Choose a stack");
119
119
  });
120
120
  it("should render divider between stacks and scratch option", () => {
121
121
  const { lastFrame, unmount } = render(/* @__PURE__ */ jsx(StepStack, { matrix: mockMatrix }));
@@ -257,7 +257,7 @@ describe("StepStack component", () => {
257
257
  const { lastFrame, unmount } = render(/* @__PURE__ */ jsx(StepStack, { matrix: emptyMatrix }));
258
258
  cleanup = unmount;
259
259
  const output = lastFrame();
260
- globalExpect(output).toContain("Choose a stack");
260
+ globalExpect(output).toContain("[1] Choose a stack");
261
261
  globalExpect(output).toContain("Start from scratch");
262
262
  });
263
263
  });
@@ -295,9 +295,7 @@ describe("StepStack component", () => {
295
295
  const { stdin, unmount } = render(/* @__PURE__ */ jsx(StepStack, { matrix: mockMatrix }));
296
296
  cleanup = unmount;
297
297
  await delay(RENDER_DELAY_MS);
298
- stdin.write(ARROW_DOWN);
299
- await delay(SELECT_NAV_DELAY_MS);
300
- stdin.write(ENTER);
298
+ stdin.write(" ");
301
299
  await delay(SELECT_NAV_DELAY_MS);
302
300
  const { selectedDomains } = useWizardStore.getState();
303
301
  globalExpect(selectedDomains).toContain("web");
@@ -306,9 +304,7 @@ describe("StepStack component", () => {
306
304
  const { stdin, unmount } = render(/* @__PURE__ */ jsx(StepStack, { matrix: mockMatrix }));
307
305
  cleanup = unmount;
308
306
  await delay(RENDER_DELAY_MS);
309
- stdin.write(ARROW_DOWN);
310
- await delay(SELECT_NAV_DELAY_MS);
311
- stdin.write(ENTER);
307
+ stdin.write(" ");
312
308
  await delay(SELECT_NAV_DELAY_MS);
313
309
  globalExpect(useWizardStore.getState().selectedDomains).toContain("web");
314
310
  useWizardStore.getState().toggleDomain("api");
@@ -329,7 +325,7 @@ describe("StepStack component", () => {
329
325
  const { stdin, unmount } = render(/* @__PURE__ */ jsx(StepStack, { matrix: mockMatrix }));
330
326
  cleanup = unmount;
331
327
  await delay(RENDER_DELAY_MS);
332
- for (let i = 0; i < 6; i++) {
328
+ for (let i = 0; i < 5; i++) {
333
329
  stdin.write(ARROW_DOWN);
334
330
  await delay(SELECT_NAV_DELAY_MS);
335
331
  }
@@ -340,16 +336,16 @@ describe("StepStack component", () => {
340
336
  });
341
337
  });
342
338
  describe("back navigation", () => {
343
- it("should return to stack/scratch selection when selecting back option", async () => {
339
+ it("should return to stack/scratch selection when pressing ESC", async () => {
344
340
  const { stdin, lastFrame, unmount } = render(/* @__PURE__ */ jsx(StepStack, { matrix: mockMatrix }));
345
341
  cleanup = unmount;
346
342
  await delay(RENDER_DELAY_MS);
347
- stdin.write(ENTER);
343
+ stdin.write(ESCAPE);
348
344
  await delay(SELECT_NAV_DELAY_MS);
349
345
  const { approach } = useWizardStore.getState();
350
346
  globalExpect(approach).toBeNull();
351
347
  const output = lastFrame();
352
- globalExpect(output).toContain("Choose a stack");
348
+ globalExpect(output).toContain("[1] Choose a stack");
353
349
  });
354
350
  });
355
351
  });
@@ -1 +1 @@
1
- {"version":3,"sources":["../../../src/cli/components/wizard/step-stack.test.tsx"],"sourcesContent":["import { render } from \"ink-testing-library\";\nimport { afterEach, beforeEach, describe, expect, it, vi } from \"vitest\";\nimport { StepStack } from \"./step-stack\";\nimport { useWizardStore } from \"../../stores/wizard-store\";\nimport {\n createMockCategory,\n createMockMatrix,\n createMockResolvedStack,\n createMockSkill,\n} from \"../../lib/__tests__/helpers\";\n\nimport type { MergedSkillsMatrix } from \"../../types\";\nimport {\n ARROW_DOWN,\n ARROW_UP,\n ENTER,\n ESCAPE,\n RENDER_DELAY_MS,\n SELECT_NAV_DELAY_MS,\n delay,\n} from \"../../lib/__tests__/test-constants\";\n\nconst createMockStackWithSkills = (): MergedSkillsMatrix => {\n const skills = {\n [\"web-framework-react\"]: createMockSkill(\"web-framework-react\", \"framework\", {\n description: \"React framework\",\n }),\n [\"web-state-zustand\"]: createMockSkill(\"web-state-zustand\", \"client-state\", {\n description: \"State management\",\n }),\n [\"api-framework-hono\"]: createMockSkill(\"api-framework-hono\", \"api\", {\n description: \"Web framework\",\n }),\n };\n\n const suggestedStacks = [\n createMockResolvedStack(\"react-fullstack\", \"React Fullstack\", {\n description: \"Full React stack with Zustand and Hono\",\n allSkillIds: [\"web-framework-react\", \"web-state-zustand\", \"api-framework-hono\"],\n }),\n createMockResolvedStack(\"react-minimal\", \"React Minimal\", {\n description: \"Minimal React setup\",\n allSkillIds: [\"web-framework-react\"],\n }),\n ];\n\n return createMockMatrix(skills, {\n suggestedStacks,\n categories: {\n framework: createMockCategory(\"framework\", \"Web\", {\n description: \"Web skills\",\n exclusive: false,\n }),\n api: createMockCategory(\"api\", \"API\", {\n description: \"API skills\",\n exclusive: false,\n order: 1,\n }),\n },\n });\n};\n\ndescribe(\"StepStack component\", () => {\n let cleanup: (() => void) | undefined;\n let mockMatrix: MergedSkillsMatrix;\n\n beforeEach(() => {\n useWizardStore.getState().reset();\n mockMatrix = createMockStackWithSkills();\n });\n\n afterEach(() => {\n cleanup?.();\n cleanup = undefined;\n });\n\n describe(\"unified stack/scratch selection (initial view)\", () => {\n describe(\"rendering\", () => {\n it(\"should render stack options and scratch option\", () => {\n const { lastFrame, unmount } = render(<StepStack matrix={mockMatrix} />);\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(\"React Fullstack\");\n expect(output).toContain(\"React Minimal\");\n expect(output).toContain(\"Start from scratch\");\n });\n\n it(\"should render focused stack description (only focused item shows description)\", () => {\n const { lastFrame, unmount } = render(<StepStack matrix={mockMatrix} />);\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(\"Full React stack\");\n });\n\n it(\"should render ViewTitle for stack selection\", () => {\n const { lastFrame, unmount } = render(<StepStack matrix={mockMatrix} />);\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(\"Choose a stack\");\n });\n\n it(\"should render divider between stacks and scratch option\", () => {\n const { lastFrame, unmount } = render(<StepStack matrix={mockMatrix} />);\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(\"\\u2500\");\n });\n });\n\n describe(\"stack selection\", () => {\n it(\"should select first stack on Enter and show domain selection\", async () => {\n const { stdin, lastFrame, unmount } = render(<StepStack matrix={mockMatrix} />);\n cleanup = unmount;\n\n await delay(RENDER_DELAY_MS);\n\n stdin.write(ENTER);\n await delay(SELECT_NAV_DELAY_MS);\n\n const { approach, selectedStackId } = useWizardStore.getState();\n expect(approach).toBe(\"stack\");\n expect(selectedStackId).toBe(\"react-fullstack\");\n\n const output = lastFrame();\n expect(output).toContain(\"Select domains to configure\");\n });\n\n it(\"should select second stack when navigated to\", async () => {\n const { stdin, unmount } = render(<StepStack matrix={mockMatrix} />);\n cleanup = unmount;\n\n await delay(RENDER_DELAY_MS);\n\n stdin.write(ARROW_DOWN);\n await delay(SELECT_NAV_DELAY_MS);\n stdin.write(ENTER);\n await delay(SELECT_NAV_DELAY_MS);\n\n const { selectedStackId } = useWizardStore.getState();\n expect(selectedStackId).toBe(\"react-minimal\");\n });\n });\n\n describe(\"scratch selection\", () => {\n it(\"should show domain selection when scratch is selected\", async () => {\n const { stdin, lastFrame, unmount } = render(<StepStack matrix={mockMatrix} />);\n cleanup = unmount;\n\n await delay(RENDER_DELAY_MS);\n\n stdin.write(ARROW_DOWN);\n await delay(SELECT_NAV_DELAY_MS);\n stdin.write(ARROW_DOWN);\n await delay(SELECT_NAV_DELAY_MS);\n stdin.write(ENTER);\n await delay(SELECT_NAV_DELAY_MS);\n\n const { approach, selectedStackId } = useWizardStore.getState();\n expect(approach).toBe(\"scratch\");\n expect(selectedStackId).toBeNull();\n\n const output = lastFrame();\n expect(output).toContain(\"Select domains to configure\");\n });\n\n it(\"should pre-select domains except CLI when scratch is chosen\", async () => {\n const { stdin, unmount } = render(<StepStack matrix={mockMatrix} />);\n cleanup = unmount;\n\n await delay(RENDER_DELAY_MS);\n\n stdin.write(ARROW_DOWN);\n await delay(SELECT_NAV_DELAY_MS);\n stdin.write(ARROW_DOWN);\n await delay(SELECT_NAV_DELAY_MS);\n stdin.write(ENTER);\n await delay(SELECT_NAV_DELAY_MS);\n\n const { selectedDomains } = useWizardStore.getState();\n expect(selectedDomains).toContain(\"web\");\n expect(selectedDomains).toContain(\"api\");\n expect(selectedDomains).toContain(\"mobile\");\n expect(selectedDomains).toContain(\"web-extras\");\n expect(selectedDomains).not.toContain(\"cli\");\n });\n });\n\n describe(\"cancel navigation\", () => {\n it(\"should call onCancel when pressing Escape at initial view\", async () => {\n const onCancel = vi.fn();\n const { stdin, unmount } = render(<StepStack matrix={mockMatrix} onCancel={onCancel} />);\n cleanup = unmount;\n\n await delay(RENDER_DELAY_MS);\n\n stdin.write(ESCAPE);\n await delay(SELECT_NAV_DELAY_MS);\n\n expect(onCancel).toHaveBeenCalledTimes(1);\n });\n });\n\n describe(\"arrow key navigation\", () => {\n it(\"should navigate down to second stack card\", async () => {\n const { stdin, unmount } = render(<StepStack matrix={mockMatrix} />);\n cleanup = unmount;\n\n await delay(RENDER_DELAY_MS);\n\n stdin.write(ARROW_DOWN);\n await delay(SELECT_NAV_DELAY_MS);\n stdin.write(ENTER);\n await delay(SELECT_NAV_DELAY_MS);\n\n const { selectedStackId } = useWizardStore.getState();\n expect(selectedStackId).toBe(\"react-minimal\");\n });\n\n it(\"should navigate down then up back to first stack\", async () => {\n const { stdin, unmount } = render(<StepStack matrix={mockMatrix} />);\n cleanup = unmount;\n\n await delay(RENDER_DELAY_MS);\n\n stdin.write(ARROW_DOWN);\n await delay(SELECT_NAV_DELAY_MS);\n stdin.write(ARROW_UP);\n await delay(SELECT_NAV_DELAY_MS);\n stdin.write(ENTER);\n await delay(SELECT_NAV_DELAY_MS);\n\n const { selectedStackId } = useWizardStore.getState();\n expect(selectedStackId).toBe(\"react-fullstack\");\n });\n\n it(\"should clamp at top boundary\", async () => {\n const { stdin, unmount } = render(<StepStack matrix={mockMatrix} />);\n cleanup = unmount;\n\n await delay(RENDER_DELAY_MS);\n\n stdin.write(ARROW_UP);\n await delay(SELECT_NAV_DELAY_MS);\n stdin.write(ARROW_UP);\n await delay(SELECT_NAV_DELAY_MS);\n stdin.write(ENTER);\n await delay(SELECT_NAV_DELAY_MS);\n\n const { selectedStackId } = useWizardStore.getState();\n expect(selectedStackId).toBe(\"react-fullstack\");\n });\n\n it(\"should clamp at bottom boundary (scratch is last)\", async () => {\n const { stdin, unmount } = render(<StepStack matrix={mockMatrix} />);\n cleanup = unmount;\n\n await delay(RENDER_DELAY_MS);\n\n stdin.write(ARROW_DOWN);\n await delay(SELECT_NAV_DELAY_MS);\n stdin.write(ARROW_DOWN);\n await delay(SELECT_NAV_DELAY_MS);\n stdin.write(ARROW_DOWN);\n await delay(SELECT_NAV_DELAY_MS);\n stdin.write(ARROW_DOWN);\n await delay(SELECT_NAV_DELAY_MS);\n stdin.write(ENTER);\n await delay(SELECT_NAV_DELAY_MS);\n\n const { approach } = useWizardStore.getState();\n expect(approach).toBe(\"scratch\");\n });\n });\n\n describe(\"empty state\", () => {\n it(\"should still show scratch option with no stacks available\", () => {\n const emptyMatrix = createMockMatrix({}, { suggestedStacks: [] });\n\n const { lastFrame, unmount } = render(<StepStack matrix={emptyMatrix} />);\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(\"Choose a stack\");\n expect(output).toContain(\"Start from scratch\");\n });\n });\n });\n\n describe(\"domain selection mode (after stack/scratch choice)\", () => {\n beforeEach(() => {\n useWizardStore.getState().setApproach(\"scratch\");\n });\n\n describe(\"rendering\", () => {\n it(\"should render domain options\", () => {\n const { lastFrame, unmount } = render(<StepStack matrix={mockMatrix} />);\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(\"Web\");\n expect(output).toContain(\"Web Extras\");\n expect(output).toContain(\"API\");\n expect(output).toContain(\"CLI\");\n });\n\n it(\"should render header text for domain selection\", () => {\n const { lastFrame, unmount } = render(<StepStack matrix={mockMatrix} />);\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(\"Select domains to configure\");\n });\n\n it(\"should show domain descriptions\", () => {\n const { lastFrame, unmount } = render(<StepStack matrix={mockMatrix} />);\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(\"Frontend web applications\");\n expect(output).toContain(\"Backend APIs\");\n });\n });\n\n describe(\"domain selection\", () => {\n it(\"should toggle domain when selected\", async () => {\n const { stdin, unmount } = render(<StepStack matrix={mockMatrix} />);\n cleanup = unmount;\n\n await delay(RENDER_DELAY_MS);\n\n // Navigate down to first domain (Web) and select\n stdin.write(ARROW_DOWN);\n await delay(SELECT_NAV_DELAY_MS);\n stdin.write(ENTER);\n await delay(SELECT_NAV_DELAY_MS);\n\n const { selectedDomains } = useWizardStore.getState();\n expect(selectedDomains).toContain(\"web\");\n });\n\n it(\"should allow multiple domain selection\", async () => {\n const { stdin, unmount } = render(<StepStack matrix={mockMatrix} />);\n cleanup = unmount;\n\n await delay(RENDER_DELAY_MS);\n\n stdin.write(ARROW_DOWN);\n await delay(SELECT_NAV_DELAY_MS);\n stdin.write(ENTER);\n await delay(SELECT_NAV_DELAY_MS);\n\n expect(useWizardStore.getState().selectedDomains).toContain(\"web\");\n\n useWizardStore.getState().toggleDomain(\"api\");\n\n const { selectedDomains } = useWizardStore.getState();\n expect(selectedDomains).toContain(\"web\");\n expect(selectedDomains).toContain(\"api\");\n });\n\n it(\"should show selected domains summary when domains selected\", async () => {\n useWizardStore.getState().toggleDomain(\"web\");\n\n const { lastFrame, unmount } = render(<StepStack matrix={mockMatrix} />);\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(\"Selected:\");\n expect(output).toContain(\"web\");\n });\n\n it(\"should navigate to build step when continuing\", async () => {\n useWizardStore.getState().toggleDomain(\"web\");\n\n const { stdin, unmount } = render(<StepStack matrix={mockMatrix} />);\n cleanup = unmount;\n\n await delay(RENDER_DELAY_MS);\n\n // Navigate to continue option (last option)\n for (let i = 0; i < 6; i++) {\n stdin.write(ARROW_DOWN);\n await delay(SELECT_NAV_DELAY_MS);\n }\n stdin.write(ENTER);\n await delay(SELECT_NAV_DELAY_MS);\n\n const { step } = useWizardStore.getState();\n expect(step).toBe(\"build\");\n });\n });\n\n describe(\"back navigation\", () => {\n it(\"should return to stack/scratch selection when selecting back option\", async () => {\n const { stdin, lastFrame, unmount } = render(<StepStack matrix={mockMatrix} />);\n cleanup = unmount;\n\n await delay(RENDER_DELAY_MS);\n\n // First option is back\n stdin.write(ENTER);\n await delay(SELECT_NAV_DELAY_MS);\n\n const { approach } = useWizardStore.getState();\n expect(approach).toBeNull();\n\n const output = lastFrame();\n expect(output).toContain(\"Choose a stack\");\n });\n });\n });\n});\n"],"mappings":"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","names":[]}
1
+ {"version":3,"sources":["../../../src/cli/components/wizard/step-stack.test.tsx"],"sourcesContent":["import { render } from \"ink-testing-library\";\nimport { afterEach, beforeEach, describe, expect, it, vi } from \"vitest\";\nimport { StepStack } from \"./step-stack\";\nimport { useWizardStore } from \"../../stores/wizard-store\";\nimport {\n createMockCategory,\n createMockMatrix,\n createMockResolvedStack,\n createMockSkill,\n} from \"../../lib/__tests__/helpers\";\n\nimport type { MergedSkillsMatrix } from \"../../types\";\nimport {\n ARROW_DOWN,\n ARROW_UP,\n ENTER,\n ESCAPE,\n RENDER_DELAY_MS,\n SELECT_NAV_DELAY_MS,\n delay,\n} from \"../../lib/__tests__/test-constants\";\n\nconst createMockStackWithSkills = (): MergedSkillsMatrix => {\n const skills = {\n [\"web-framework-react\"]: createMockSkill(\"web-framework-react\", \"framework\", {\n description: \"React framework\",\n }),\n [\"web-state-zustand\"]: createMockSkill(\"web-state-zustand\", \"client-state\", {\n description: \"State management\",\n }),\n [\"api-framework-hono\"]: createMockSkill(\"api-framework-hono\", \"api\", {\n description: \"Web framework\",\n }),\n };\n\n const suggestedStacks = [\n createMockResolvedStack(\"react-fullstack\", \"React Fullstack\", {\n description: \"Full React stack with Zustand and Hono\",\n allSkillIds: [\"web-framework-react\", \"web-state-zustand\", \"api-framework-hono\"],\n }),\n createMockResolvedStack(\"react-minimal\", \"React Minimal\", {\n description: \"Minimal React setup\",\n allSkillIds: [\"web-framework-react\"],\n }),\n ];\n\n return createMockMatrix(skills, {\n suggestedStacks,\n categories: {\n framework: createMockCategory(\"framework\", \"Web\", {\n description: \"Web skills\",\n exclusive: false,\n }),\n api: createMockCategory(\"api\", \"API\", {\n description: \"API skills\",\n exclusive: false,\n order: 1,\n }),\n },\n });\n};\n\ndescribe(\"StepStack component\", () => {\n let cleanup: (() => void) | undefined;\n let mockMatrix: MergedSkillsMatrix;\n\n beforeEach(() => {\n useWizardStore.getState().reset();\n mockMatrix = createMockStackWithSkills();\n });\n\n afterEach(() => {\n cleanup?.();\n cleanup = undefined;\n });\n\n describe(\"unified stack/scratch selection (initial view)\", () => {\n describe(\"rendering\", () => {\n it(\"should render stack options and scratch option\", () => {\n const { lastFrame, unmount } = render(<StepStack matrix={mockMatrix} />);\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(\"React Fullstack\");\n expect(output).toContain(\"React Minimal\");\n expect(output).toContain(\"Start from scratch\");\n });\n\n it(\"should render focused stack description (only focused item shows description)\", () => {\n const { lastFrame, unmount } = render(<StepStack matrix={mockMatrix} />);\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(\"Full React stack\");\n });\n\n it(\"should render ViewTitle for stack selection\", () => {\n const { lastFrame, unmount } = render(<StepStack matrix={mockMatrix} />);\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(\"[1] Choose a stack\");\n });\n\n it(\"should render divider between stacks and scratch option\", () => {\n const { lastFrame, unmount } = render(<StepStack matrix={mockMatrix} />);\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(\"\\u2500\");\n });\n });\n\n describe(\"stack selection\", () => {\n it(\"should select first stack on Enter and show domain selection\", async () => {\n const { stdin, lastFrame, unmount } = render(<StepStack matrix={mockMatrix} />);\n cleanup = unmount;\n\n await delay(RENDER_DELAY_MS);\n\n stdin.write(ENTER);\n await delay(SELECT_NAV_DELAY_MS);\n\n const { approach, selectedStackId } = useWizardStore.getState();\n expect(approach).toBe(\"stack\");\n expect(selectedStackId).toBe(\"react-fullstack\");\n\n const output = lastFrame();\n expect(output).toContain(\"Select domains to configure\");\n });\n\n it(\"should select second stack when navigated to\", async () => {\n const { stdin, unmount } = render(<StepStack matrix={mockMatrix} />);\n cleanup = unmount;\n\n await delay(RENDER_DELAY_MS);\n\n stdin.write(ARROW_DOWN);\n await delay(SELECT_NAV_DELAY_MS);\n stdin.write(ENTER);\n await delay(SELECT_NAV_DELAY_MS);\n\n const { selectedStackId } = useWizardStore.getState();\n expect(selectedStackId).toBe(\"react-minimal\");\n });\n });\n\n describe(\"scratch selection\", () => {\n it(\"should show domain selection when scratch is selected\", async () => {\n const { stdin, lastFrame, unmount } = render(<StepStack matrix={mockMatrix} />);\n cleanup = unmount;\n\n await delay(RENDER_DELAY_MS);\n\n stdin.write(ARROW_DOWN);\n await delay(SELECT_NAV_DELAY_MS);\n stdin.write(ARROW_DOWN);\n await delay(SELECT_NAV_DELAY_MS);\n stdin.write(ENTER);\n await delay(SELECT_NAV_DELAY_MS);\n\n const { approach, selectedStackId } = useWizardStore.getState();\n expect(approach).toBe(\"scratch\");\n expect(selectedStackId).toBeNull();\n\n const output = lastFrame();\n expect(output).toContain(\"Select domains to configure\");\n });\n\n it(\"should pre-select domains except CLI when scratch is chosen\", async () => {\n const { stdin, unmount } = render(<StepStack matrix={mockMatrix} />);\n cleanup = unmount;\n\n await delay(RENDER_DELAY_MS);\n\n stdin.write(ARROW_DOWN);\n await delay(SELECT_NAV_DELAY_MS);\n stdin.write(ARROW_DOWN);\n await delay(SELECT_NAV_DELAY_MS);\n stdin.write(ENTER);\n await delay(SELECT_NAV_DELAY_MS);\n\n const { selectedDomains } = useWizardStore.getState();\n expect(selectedDomains).toContain(\"web\");\n expect(selectedDomains).toContain(\"api\");\n expect(selectedDomains).toContain(\"mobile\");\n expect(selectedDomains).toContain(\"web-extras\");\n expect(selectedDomains).not.toContain(\"cli\");\n });\n });\n\n describe(\"cancel navigation\", () => {\n it(\"should call onCancel when pressing Escape at initial view\", async () => {\n const onCancel = vi.fn();\n const { stdin, unmount } = render(<StepStack matrix={mockMatrix} onCancel={onCancel} />);\n cleanup = unmount;\n\n await delay(RENDER_DELAY_MS);\n\n stdin.write(ESCAPE);\n await delay(SELECT_NAV_DELAY_MS);\n\n expect(onCancel).toHaveBeenCalledTimes(1);\n });\n });\n\n describe(\"arrow key navigation\", () => {\n it(\"should navigate down to second stack card\", async () => {\n const { stdin, unmount } = render(<StepStack matrix={mockMatrix} />);\n cleanup = unmount;\n\n await delay(RENDER_DELAY_MS);\n\n stdin.write(ARROW_DOWN);\n await delay(SELECT_NAV_DELAY_MS);\n stdin.write(ENTER);\n await delay(SELECT_NAV_DELAY_MS);\n\n const { selectedStackId } = useWizardStore.getState();\n expect(selectedStackId).toBe(\"react-minimal\");\n });\n\n it(\"should navigate down then up back to first stack\", async () => {\n const { stdin, unmount } = render(<StepStack matrix={mockMatrix} />);\n cleanup = unmount;\n\n await delay(RENDER_DELAY_MS);\n\n stdin.write(ARROW_DOWN);\n await delay(SELECT_NAV_DELAY_MS);\n stdin.write(ARROW_UP);\n await delay(SELECT_NAV_DELAY_MS);\n stdin.write(ENTER);\n await delay(SELECT_NAV_DELAY_MS);\n\n const { selectedStackId } = useWizardStore.getState();\n expect(selectedStackId).toBe(\"react-fullstack\");\n });\n\n it(\"should clamp at top boundary\", async () => {\n const { stdin, unmount } = render(<StepStack matrix={mockMatrix} />);\n cleanup = unmount;\n\n await delay(RENDER_DELAY_MS);\n\n stdin.write(ARROW_UP);\n await delay(SELECT_NAV_DELAY_MS);\n stdin.write(ARROW_UP);\n await delay(SELECT_NAV_DELAY_MS);\n stdin.write(ENTER);\n await delay(SELECT_NAV_DELAY_MS);\n\n const { selectedStackId } = useWizardStore.getState();\n expect(selectedStackId).toBe(\"react-fullstack\");\n });\n\n it(\"should clamp at bottom boundary (scratch is last)\", async () => {\n const { stdin, unmount } = render(<StepStack matrix={mockMatrix} />);\n cleanup = unmount;\n\n await delay(RENDER_DELAY_MS);\n\n stdin.write(ARROW_DOWN);\n await delay(SELECT_NAV_DELAY_MS);\n stdin.write(ARROW_DOWN);\n await delay(SELECT_NAV_DELAY_MS);\n stdin.write(ARROW_DOWN);\n await delay(SELECT_NAV_DELAY_MS);\n stdin.write(ARROW_DOWN);\n await delay(SELECT_NAV_DELAY_MS);\n stdin.write(ENTER);\n await delay(SELECT_NAV_DELAY_MS);\n\n const { approach } = useWizardStore.getState();\n expect(approach).toBe(\"scratch\");\n });\n });\n\n describe(\"empty state\", () => {\n it(\"should still show scratch option with no stacks available\", () => {\n const emptyMatrix = createMockMatrix({}, { suggestedStacks: [] });\n\n const { lastFrame, unmount } = render(<StepStack matrix={emptyMatrix} />);\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(\"[1] Choose a stack\");\n expect(output).toContain(\"Start from scratch\");\n });\n });\n });\n\n describe(\"domain selection mode (after stack/scratch choice)\", () => {\n beforeEach(() => {\n useWizardStore.getState().setApproach(\"scratch\");\n });\n\n describe(\"rendering\", () => {\n it(\"should render domain options\", () => {\n const { lastFrame, unmount } = render(<StepStack matrix={mockMatrix} />);\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(\"Web\");\n expect(output).toContain(\"Web Extras\");\n expect(output).toContain(\"API\");\n expect(output).toContain(\"CLI\");\n });\n\n it(\"should render header text for domain selection\", () => {\n const { lastFrame, unmount } = render(<StepStack matrix={mockMatrix} />);\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(\"Select domains to configure\");\n });\n\n it(\"should show domain descriptions\", () => {\n const { lastFrame, unmount } = render(<StepStack matrix={mockMatrix} />);\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(\"Frontend web applications\");\n expect(output).toContain(\"Backend APIs\");\n });\n });\n\n describe(\"domain selection\", () => {\n it(\"should toggle domain when selected\", async () => {\n const { stdin, unmount } = render(<StepStack matrix={mockMatrix} />);\n cleanup = unmount;\n\n await delay(RENDER_DELAY_MS);\n\n // First domain (Web) is focused by default, toggle with space\n stdin.write(\" \");\n await delay(SELECT_NAV_DELAY_MS);\n\n const { selectedDomains } = useWizardStore.getState();\n expect(selectedDomains).toContain(\"web\");\n });\n\n it(\"should allow multiple domain selection\", async () => {\n const { stdin, unmount } = render(<StepStack matrix={mockMatrix} />);\n cleanup = unmount;\n\n await delay(RENDER_DELAY_MS);\n\n // First domain (Web) is focused by default\n stdin.write(\" \");\n await delay(SELECT_NAV_DELAY_MS);\n\n expect(useWizardStore.getState().selectedDomains).toContain(\"web\");\n\n useWizardStore.getState().toggleDomain(\"api\");\n\n const { selectedDomains } = useWizardStore.getState();\n expect(selectedDomains).toContain(\"web\");\n expect(selectedDomains).toContain(\"api\");\n });\n\n it(\"should show selected domains summary when domains selected\", async () => {\n useWizardStore.getState().toggleDomain(\"web\");\n\n const { lastFrame, unmount } = render(<StepStack matrix={mockMatrix} />);\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(\"Selected:\");\n expect(output).toContain(\"web\");\n });\n\n it(\"should navigate to build step when continuing\", async () => {\n useWizardStore.getState().toggleDomain(\"web\");\n\n const { stdin, unmount } = render(<StepStack matrix={mockMatrix} />);\n cleanup = unmount;\n\n await delay(RENDER_DELAY_MS);\n\n // Navigate to continue option (after 5 domains)\n for (let i = 0; i < 5; i++) {\n stdin.write(ARROW_DOWN);\n await delay(SELECT_NAV_DELAY_MS);\n }\n stdin.write(ENTER);\n await delay(SELECT_NAV_DELAY_MS);\n\n const { step } = useWizardStore.getState();\n expect(step).toBe(\"build\");\n });\n });\n\n describe(\"back navigation\", () => {\n it(\"should return to stack/scratch selection when pressing ESC\", async () => {\n const { stdin, lastFrame, unmount } = render(<StepStack matrix={mockMatrix} />);\n cleanup = unmount;\n\n await delay(RENDER_DELAY_MS);\n\n stdin.write(ESCAPE);\n await delay(SELECT_NAV_DELAY_MS);\n\n const { approach } = useWizardStore.getState();\n expect(approach).toBeNull();\n\n const output = lastFrame();\n expect(output).toContain(\"[1] Choose a stack\");\n });\n });\n });\n});\n"],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAAA;AA+E8C;AAzD9C,IAAM,4BAA4B,MAA0B;AAC1D,QAAM,SAAS;AAAA,IACb,CAAC,qBAAqB,GAAG,gBAAgB,uBAAuB,aAAa;AAAA,MAC3E,aAAa;AAAA,IACf,CAAC;AAAA,IACD,CAAC,mBAAmB,GAAG,gBAAgB,qBAAqB,gBAAgB;AAAA,MAC1E,aAAa;AAAA,IACf,CAAC;AAAA,IACD,CAAC,oBAAoB,GAAG,gBAAgB,sBAAsB,OAAO;AAAA,MACnE,aAAa;AAAA,IACf,CAAC;AAAA,EACH;AAEA,QAAM,kBAAkB;AAAA,IACtB,wBAAwB,mBAAmB,mBAAmB;AAAA,MAC5D,aAAa;AAAA,MACb,aAAa,CAAC,uBAAuB,qBAAqB,oBAAoB;AAAA,IAChF,CAAC;AAAA,IACD,wBAAwB,iBAAiB,iBAAiB;AAAA,MACxD,aAAa;AAAA,MACb,aAAa,CAAC,qBAAqB;AAAA,IACrC,CAAC;AAAA,EACH;AAEA,SAAO,iBAAiB,QAAQ;AAAA,IAC9B;AAAA,IACA,YAAY;AAAA,MACV,WAAW,mBAAmB,aAAa,OAAO;AAAA,QAChD,aAAa;AAAA,QACb,WAAW;AAAA,MACb,CAAC;AAAA,MACD,KAAK,mBAAmB,OAAO,OAAO;AAAA,QACpC,aAAa;AAAA,QACb,WAAW;AAAA,QACX,OAAO;AAAA,MACT,CAAC;AAAA,IACH;AAAA,EACF,CAAC;AACH;AAEA,SAAS,uBAAuB,MAAM;AACpC,MAAI;AACJ,MAAI;AAEJ,aAAW,MAAM;AACf,mBAAe,SAAS,EAAE,MAAM;AAChC,iBAAa,0BAA0B;AAAA,EACzC,CAAC;AAED,YAAU,MAAM;AACd,cAAU;AACV,cAAU;AAAA,EACZ,CAAC;AAED,WAAS,kDAAkD,MAAM;AAC/D,aAAS,aAAa,MAAM;AAC1B,SAAG,kDAAkD,MAAM;AACzD,cAAM,EAAE,WAAW,QAAQ,IAAI,OAAO,oBAAC,aAAU,QAAQ,YAAY,CAAE;AACvE,kBAAU;AAEV,cAAM,SAAS,UAAU;AACzB,qBAAO,MAAM,EAAE,UAAU,iBAAiB;AAC1C,qBAAO,MAAM,EAAE,UAAU,eAAe;AACxC,qBAAO,MAAM,EAAE,UAAU,oBAAoB;AAAA,MAC/C,CAAC;AAED,SAAG,iFAAiF,MAAM;AACxF,cAAM,EAAE,WAAW,QAAQ,IAAI,OAAO,oBAAC,aAAU,QAAQ,YAAY,CAAE;AACvE,kBAAU;AAEV,cAAM,SAAS,UAAU;AACzB,qBAAO,MAAM,EAAE,UAAU,kBAAkB;AAAA,MAC7C,CAAC;AAED,SAAG,+CAA+C,MAAM;AACtD,cAAM,EAAE,WAAW,QAAQ,IAAI,OAAO,oBAAC,aAAU,QAAQ,YAAY,CAAE;AACvE,kBAAU;AAEV,cAAM,SAAS,UAAU;AACzB,qBAAO,MAAM,EAAE,UAAU,oBAAoB;AAAA,MAC/C,CAAC;AAED,SAAG,2DAA2D,MAAM;AAClE,cAAM,EAAE,WAAW,QAAQ,IAAI,OAAO,oBAAC,aAAU,QAAQ,YAAY,CAAE;AACvE,kBAAU;AAEV,cAAM,SAAS,UAAU;AACzB,qBAAO,MAAM,EAAE,UAAU,QAAQ;AAAA,MACnC,CAAC;AAAA,IACH,CAAC;AAED,aAAS,mBAAmB,MAAM;AAChC,SAAG,gEAAgE,YAAY;AAC7E,cAAM,EAAE,OAAO,WAAW,QAAQ,IAAI,OAAO,oBAAC,aAAU,QAAQ,YAAY,CAAE;AAC9E,kBAAU;AAEV,cAAM,MAAM,eAAe;AAE3B,cAAM,MAAM,KAAK;AACjB,cAAM,MAAM,mBAAmB;AAE/B,cAAM,EAAE,UAAU,gBAAgB,IAAI,eAAe,SAAS;AAC9D,qBAAO,QAAQ,EAAE,KAAK,OAAO;AAC7B,qBAAO,eAAe,EAAE,KAAK,iBAAiB;AAE9C,cAAM,SAAS,UAAU;AACzB,qBAAO,MAAM,EAAE,UAAU,6BAA6B;AAAA,MACxD,CAAC;AAED,SAAG,gDAAgD,YAAY;AAC7D,cAAM,EAAE,OAAO,QAAQ,IAAI,OAAO,oBAAC,aAAU,QAAQ,YAAY,CAAE;AACnE,kBAAU;AAEV,cAAM,MAAM,eAAe;AAE3B,cAAM,MAAM,UAAU;AACtB,cAAM,MAAM,mBAAmB;AAC/B,cAAM,MAAM,KAAK;AACjB,cAAM,MAAM,mBAAmB;AAE/B,cAAM,EAAE,gBAAgB,IAAI,eAAe,SAAS;AACpD,qBAAO,eAAe,EAAE,KAAK,eAAe;AAAA,MAC9C,CAAC;AAAA,IACH,CAAC;AAED,aAAS,qBAAqB,MAAM;AAClC,SAAG,yDAAyD,YAAY;AACtE,cAAM,EAAE,OAAO,WAAW,QAAQ,IAAI,OAAO,oBAAC,aAAU,QAAQ,YAAY,CAAE;AAC9E,kBAAU;AAEV,cAAM,MAAM,eAAe;AAE3B,cAAM,MAAM,UAAU;AACtB,cAAM,MAAM,mBAAmB;AAC/B,cAAM,MAAM,UAAU;AACtB,cAAM,MAAM,mBAAmB;AAC/B,cAAM,MAAM,KAAK;AACjB,cAAM,MAAM,mBAAmB;AAE/B,cAAM,EAAE,UAAU,gBAAgB,IAAI,eAAe,SAAS;AAC9D,qBAAO,QAAQ,EAAE,KAAK,SAAS;AAC/B,qBAAO,eAAe,EAAE,SAAS;AAEjC,cAAM,SAAS,UAAU;AACzB,qBAAO,MAAM,EAAE,UAAU,6BAA6B;AAAA,MACxD,CAAC;AAED,SAAG,+DAA+D,YAAY;AAC5E,cAAM,EAAE,OAAO,QAAQ,IAAI,OAAO,oBAAC,aAAU,QAAQ,YAAY,CAAE;AACnE,kBAAU;AAEV,cAAM,MAAM,eAAe;AAE3B,cAAM,MAAM,UAAU;AACtB,cAAM,MAAM,mBAAmB;AAC/B,cAAM,MAAM,UAAU;AACtB,cAAM,MAAM,mBAAmB;AAC/B,cAAM,MAAM,KAAK;AACjB,cAAM,MAAM,mBAAmB;AAE/B,cAAM,EAAE,gBAAgB,IAAI,eAAe,SAAS;AACpD,qBAAO,eAAe,EAAE,UAAU,KAAK;AACvC,qBAAO,eAAe,EAAE,UAAU,KAAK;AACvC,qBAAO,eAAe,EAAE,UAAU,QAAQ;AAC1C,qBAAO,eAAe,EAAE,UAAU,YAAY;AAC9C,qBAAO,eAAe,EAAE,IAAI,UAAU,KAAK;AAAA,MAC7C,CAAC;AAAA,IACH,CAAC;AAED,aAAS,qBAAqB,MAAM;AAClC,SAAG,6DAA6D,YAAY;AAC1E,cAAM,WAAW,GAAG,GAAG;AACvB,cAAM,EAAE,OAAO,QAAQ,IAAI,OAAO,oBAAC,aAAU,QAAQ,YAAY,UAAoB,CAAE;AACvF,kBAAU;AAEV,cAAM,MAAM,eAAe;AAE3B,cAAM,MAAM,MAAM;AAClB,cAAM,MAAM,mBAAmB;AAE/B,qBAAO,QAAQ,EAAE,sBAAsB,CAAC;AAAA,MAC1C,CAAC;AAAA,IACH,CAAC;AAED,aAAS,wBAAwB,MAAM;AACrC,SAAG,6CAA6C,YAAY;AAC1D,cAAM,EAAE,OAAO,QAAQ,IAAI,OAAO,oBAAC,aAAU,QAAQ,YAAY,CAAE;AACnE,kBAAU;AAEV,cAAM,MAAM,eAAe;AAE3B,cAAM,MAAM,UAAU;AACtB,cAAM,MAAM,mBAAmB;AAC/B,cAAM,MAAM,KAAK;AACjB,cAAM,MAAM,mBAAmB;AAE/B,cAAM,EAAE,gBAAgB,IAAI,eAAe,SAAS;AACpD,qBAAO,eAAe,EAAE,KAAK,eAAe;AAAA,MAC9C,CAAC;AAED,SAAG,oDAAoD,YAAY;AACjE,cAAM,EAAE,OAAO,QAAQ,IAAI,OAAO,oBAAC,aAAU,QAAQ,YAAY,CAAE;AACnE,kBAAU;AAEV,cAAM,MAAM,eAAe;AAE3B,cAAM,MAAM,UAAU;AACtB,cAAM,MAAM,mBAAmB;AAC/B,cAAM,MAAM,QAAQ;AACpB,cAAM,MAAM,mBAAmB;AAC/B,cAAM,MAAM,KAAK;AACjB,cAAM,MAAM,mBAAmB;AAE/B,cAAM,EAAE,gBAAgB,IAAI,eAAe,SAAS;AACpD,qBAAO,eAAe,EAAE,KAAK,iBAAiB;AAAA,MAChD,CAAC;AAED,SAAG,gCAAgC,YAAY;AAC7C,cAAM,EAAE,OAAO,QAAQ,IAAI,OAAO,oBAAC,aAAU,QAAQ,YAAY,CAAE;AACnE,kBAAU;AAEV,cAAM,MAAM,eAAe;AAE3B,cAAM,MAAM,QAAQ;AACpB,cAAM,MAAM,mBAAmB;AAC/B,cAAM,MAAM,QAAQ;AACpB,cAAM,MAAM,mBAAmB;AAC/B,cAAM,MAAM,KAAK;AACjB,cAAM,MAAM,mBAAmB;AAE/B,cAAM,EAAE,gBAAgB,IAAI,eAAe,SAAS;AACpD,qBAAO,eAAe,EAAE,KAAK,iBAAiB;AAAA,MAChD,CAAC;AAED,SAAG,qDAAqD,YAAY;AAClE,cAAM,EAAE,OAAO,QAAQ,IAAI,OAAO,oBAAC,aAAU,QAAQ,YAAY,CAAE;AACnE,kBAAU;AAEV,cAAM,MAAM,eAAe;AAE3B,cAAM,MAAM,UAAU;AACtB,cAAM,MAAM,mBAAmB;AAC/B,cAAM,MAAM,UAAU;AACtB,cAAM,MAAM,mBAAmB;AAC/B,cAAM,MAAM,UAAU;AACtB,cAAM,MAAM,mBAAmB;AAC/B,cAAM,MAAM,UAAU;AACtB,cAAM,MAAM,mBAAmB;AAC/B,cAAM,MAAM,KAAK;AACjB,cAAM,MAAM,mBAAmB;AAE/B,cAAM,EAAE,SAAS,IAAI,eAAe,SAAS;AAC7C,qBAAO,QAAQ,EAAE,KAAK,SAAS;AAAA,MACjC,CAAC;AAAA,IACH,CAAC;AAED,aAAS,eAAe,MAAM;AAC5B,SAAG,6DAA6D,MAAM;AACpE,cAAM,cAAc,iBAAiB,CAAC,GAAG,EAAE,iBAAiB,CAAC,EAAE,CAAC;AAEhE,cAAM,EAAE,WAAW,QAAQ,IAAI,OAAO,oBAAC,aAAU,QAAQ,aAAa,CAAE;AACxE,kBAAU;AAEV,cAAM,SAAS,UAAU;AACzB,qBAAO,MAAM,EAAE,UAAU,oBAAoB;AAC7C,qBAAO,MAAM,EAAE,UAAU,oBAAoB;AAAA,MAC/C,CAAC;AAAA,IACH,CAAC;AAAA,EACH,CAAC;AAED,WAAS,sDAAsD,MAAM;AACnE,eAAW,MAAM;AACf,qBAAe,SAAS,EAAE,YAAY,SAAS;AAAA,IACjD,CAAC;AAED,aAAS,aAAa,MAAM;AAC1B,SAAG,gCAAgC,MAAM;AACvC,cAAM,EAAE,WAAW,QAAQ,IAAI,OAAO,oBAAC,aAAU,QAAQ,YAAY,CAAE;AACvE,kBAAU;AAEV,cAAM,SAAS,UAAU;AACzB,qBAAO,MAAM,EAAE,UAAU,KAAK;AAC9B,qBAAO,MAAM,EAAE,UAAU,YAAY;AACrC,qBAAO,MAAM,EAAE,UAAU,KAAK;AAC9B,qBAAO,MAAM,EAAE,UAAU,KAAK;AAAA,MAChC,CAAC;AAED,SAAG,kDAAkD,MAAM;AACzD,cAAM,EAAE,WAAW,QAAQ,IAAI,OAAO,oBAAC,aAAU,QAAQ,YAAY,CAAE;AACvE,kBAAU;AAEV,cAAM,SAAS,UAAU;AACzB,qBAAO,MAAM,EAAE,UAAU,6BAA6B;AAAA,MACxD,CAAC;AAED,SAAG,mCAAmC,MAAM;AAC1C,cAAM,EAAE,WAAW,QAAQ,IAAI,OAAO,oBAAC,aAAU,QAAQ,YAAY,CAAE;AACvE,kBAAU;AAEV,cAAM,SAAS,UAAU;AACzB,qBAAO,MAAM,EAAE,UAAU,2BAA2B;AACpD,qBAAO,MAAM,EAAE,UAAU,cAAc;AAAA,MACzC,CAAC;AAAA,IACH,CAAC;AAED,aAAS,oBAAoB,MAAM;AACjC,SAAG,sCAAsC,YAAY;AACnD,cAAM,EAAE,OAAO,QAAQ,IAAI,OAAO,oBAAC,aAAU,QAAQ,YAAY,CAAE;AACnE,kBAAU;AAEV,cAAM,MAAM,eAAe;AAG3B,cAAM,MAAM,GAAG;AACf,cAAM,MAAM,mBAAmB;AAE/B,cAAM,EAAE,gBAAgB,IAAI,eAAe,SAAS;AACpD,qBAAO,eAAe,EAAE,UAAU,KAAK;AAAA,MACzC,CAAC;AAED,SAAG,0CAA0C,YAAY;AACvD,cAAM,EAAE,OAAO,QAAQ,IAAI,OAAO,oBAAC,aAAU,QAAQ,YAAY,CAAE;AACnE,kBAAU;AAEV,cAAM,MAAM,eAAe;AAG3B,cAAM,MAAM,GAAG;AACf,cAAM,MAAM,mBAAmB;AAE/B,qBAAO,eAAe,SAAS,EAAE,eAAe,EAAE,UAAU,KAAK;AAEjE,uBAAe,SAAS,EAAE,aAAa,KAAK;AAE5C,cAAM,EAAE,gBAAgB,IAAI,eAAe,SAAS;AACpD,qBAAO,eAAe,EAAE,UAAU,KAAK;AACvC,qBAAO,eAAe,EAAE,UAAU,KAAK;AAAA,MACzC,CAAC;AAED,SAAG,8DAA8D,YAAY;AAC3E,uBAAe,SAAS,EAAE,aAAa,KAAK;AAE5C,cAAM,EAAE,WAAW,QAAQ,IAAI,OAAO,oBAAC,aAAU,QAAQ,YAAY,CAAE;AACvE,kBAAU;AAEV,cAAM,SAAS,UAAU;AACzB,qBAAO,MAAM,EAAE,UAAU,WAAW;AACpC,qBAAO,MAAM,EAAE,UAAU,KAAK;AAAA,MAChC,CAAC;AAED,SAAG,iDAAiD,YAAY;AAC9D,uBAAe,SAAS,EAAE,aAAa,KAAK;AAE5C,cAAM,EAAE,OAAO,QAAQ,IAAI,OAAO,oBAAC,aAAU,QAAQ,YAAY,CAAE;AACnE,kBAAU;AAEV,cAAM,MAAM,eAAe;AAG3B,iBAAS,IAAI,GAAG,IAAI,GAAG,KAAK;AAC1B,gBAAM,MAAM,UAAU;AACtB,gBAAM,MAAM,mBAAmB;AAAA,QACjC;AACA,cAAM,MAAM,KAAK;AACjB,cAAM,MAAM,mBAAmB;AAE/B,cAAM,EAAE,KAAK,IAAI,eAAe,SAAS;AACzC,qBAAO,IAAI,EAAE,KAAK,OAAO;AAAA,MAC3B,CAAC;AAAA,IACH,CAAC;AAED,aAAS,mBAAmB,MAAM;AAChC,SAAG,8DAA8D,YAAY;AAC3E,cAAM,EAAE,OAAO,WAAW,QAAQ,IAAI,OAAO,oBAAC,aAAU,QAAQ,YAAY,CAAE;AAC9E,kBAAU;AAEV,cAAM,MAAM,eAAe;AAE3B,cAAM,MAAM,MAAM;AAClB,cAAM,MAAM,mBAAmB;AAE/B,cAAM,EAAE,SAAS,IAAI,eAAe,SAAS;AAC7C,qBAAO,QAAQ,EAAE,SAAS;AAE1B,cAAM,SAAS,UAAU;AACzB,qBAAO,MAAM,EAAE,UAAU,oBAAoB;AAAA,MAC/C,CAAC;AAAA,IACH,CAAC;AAAA,EACH,CAAC;AACH,CAAC;","names":[]}
@@ -1,8 +1,8 @@
1
1
  #!/usr/bin/env node
2
2
  import {
3
3
  ViewTitle
4
- } from "../../chunk-O4D67NN7.js";
5
- import "../../chunk-LAPCUV4D.js";
4
+ } from "../../chunk-HTTPKSL6.js";
5
+ import "../../chunk-YCS7GF6Y.js";
6
6
  import "../../chunk-DHET7RCE.js";
7
7
  export {
8
8
  ViewTitle
@@ -1,14 +1,14 @@
1
1
  #!/usr/bin/env node
2
2
  import {
3
3
  WizardLayout
4
- } from "../../chunk-PBEHPQLK.js";
5
- import "../../chunk-IYG2LAIM.js";
6
- import "../../chunk-FZGYSLJL.js";
7
- import "../../chunk-3ZOIOVKT.js";
8
- import "../../chunk-MM7NK5N2.js";
4
+ } from "../../chunk-JZOLJVWA.js";
5
+ import "../../chunk-LFHZBF6N.js";
6
+ import "../../chunk-ZE355C6C.js";
7
+ import "../../chunk-R3AD6XBJ.js";
8
+ import "../../chunk-TM4I4EHK.js";
9
9
  import "../../chunk-T4EXUIBY.js";
10
- import "../../chunk-BZN2Z5P7.js";
11
- import "../../chunk-LAPCUV4D.js";
10
+ import "../../chunk-NLR6Z37M.js";
11
+ import "../../chunk-YCS7GF6Y.js";
12
12
  import "../../chunk-DHET7RCE.js";
13
13
  export {
14
14
  WizardLayout
@@ -3,8 +3,8 @@ import {
3
3
  WIZARD_STEPS,
4
4
  WizardTabs,
5
5
  formatStepLabel
6
- } from "../../chunk-IYG2LAIM.js";
7
- import "../../chunk-LAPCUV4D.js";
6
+ } from "../../chunk-LFHZBF6N.js";
7
+ import "../../chunk-YCS7GF6Y.js";
8
8
  import "../../chunk-DHET7RCE.js";
9
9
  export {
10
10
  WIZARD_STEPS,
@@ -12,8 +12,8 @@ import {
12
12
  WIZARD_STEPS,
13
13
  WizardTabs,
14
14
  formatStepLabel
15
- } from "../../chunk-IYG2LAIM.js";
16
- import "../../chunk-LAPCUV4D.js";
15
+ } from "../../chunk-LFHZBF6N.js";
16
+ import "../../chunk-YCS7GF6Y.js";
17
17
  import {
18
18
  init_esm_shims
19
19
  } from "../../chunk-DHET7RCE.js";
@@ -62,18 +62,17 @@ describe("WizardTabs component", () => {
62
62
  });
63
63
  it("should render with custom steps", () => {
64
64
  const customSteps = [
65
- { id: "one", label: "First", number: 1 },
66
- { id: "two", label: "Second", number: 2 }
65
+ { id: "stack", label: "First", number: 1 },
66
+ { id: "build", label: "Second", number: 2 }
67
67
  ];
68
68
  const { lastFrame, unmount } = renderWizardTabs({
69
69
  steps: customSteps,
70
- currentStep: "one"
70
+ currentStep: "stack"
71
71
  });
72
72
  cleanup = unmount;
73
73
  const output = lastFrame();
74
74
  globalExpect(output).toContain(formatCustomStepLabel(customSteps[0]).full);
75
75
  globalExpect(output).toContain(formatCustomStepLabel(customSteps[1]).full);
76
- globalExpect(output).not.toContain(formatStepLabel("stack").label);
77
76
  });
78
77
  it("should render horizontal dividers above and below tabs", () => {
79
78
  const { lastFrame, unmount } = renderWizardTabs();
@@ -279,10 +278,10 @@ describe("WizardTabs component", () => {
279
278
  globalExpect(output).toContain(formatStepLabel("confirm").full);
280
279
  });
281
280
  it("should handle single step", () => {
282
- const singleStep = [{ id: "only", label: "Only Step", number: 1 }];
281
+ const singleStep = [{ id: "confirm", label: "Only Step", number: 1 }];
283
282
  const { lastFrame, unmount } = renderWizardTabs({
284
283
  steps: singleStep,
285
- currentStep: "only",
284
+ currentStep: "confirm",
286
285
  completedSteps: []
287
286
  });
288
287
  cleanup = unmount;
@@ -1 +1 @@
1
- {"version":3,"sources":["../../../src/cli/components/wizard/wizard-tabs.test.tsx"],"sourcesContent":["import { render } from \"ink-testing-library\";\nimport { afterEach, describe, expect, it } from \"vitest\";\nimport type { WizardStep } from \"../../stores/wizard-store\";\nimport { WizardTabs, WIZARD_STEPS, formatStepLabel, type WizardTabsProps } from \"./wizard-tabs\";\n\n/** Format a custom (non-WIZARD_STEPS) step label for test assertions */\nconst formatCustomStepLabel = (step: { label: string; number: number }) => {\n const prefix = `[${step.number}]`;\n return { prefix, label: step.label, full: `${prefix} ${step.label}` };\n};\n\nconst renderWizardTabs = (props: Partial<WizardTabsProps> = {}) => {\n const defaultProps: WizardTabsProps = {\n steps: WIZARD_STEPS,\n currentStep: \"stack\",\n completedSteps: [],\n skippedSteps: [],\n ...props,\n };\n return render(<WizardTabs {...defaultProps} />);\n};\n\ndescribe(\"WizardTabs component\", () => {\n let cleanup: (() => void) | undefined;\n\n afterEach(() => {\n cleanup?.();\n cleanup = undefined;\n });\n\n describe(\"rendering\", () => {\n it(\"should render all 4 tabs\", () => {\n const { lastFrame, unmount } = renderWizardTabs();\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatStepLabel(\"stack\").full);\n expect(output).toContain(formatStepLabel(\"build\").full);\n expect(output).toContain(formatStepLabel(\"sources\").full);\n expect(output).toContain(formatStepLabel(\"confirm\").full);\n });\n\n it(\"should render all step numbers\", () => {\n const { lastFrame, unmount } = renderWizardTabs();\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatStepLabel(\"stack\").prefix);\n expect(output).toContain(formatStepLabel(\"build\").prefix);\n expect(output).toContain(formatStepLabel(\"sources\").prefix);\n expect(output).toContain(formatStepLabel(\"confirm\").prefix);\n });\n\n it(\"should render with custom steps\", () => {\n const customSteps = [\n { id: \"one\", label: \"First\", number: 1 },\n { id: \"two\", label: \"Second\", number: 2 },\n ];\n const { lastFrame, unmount } = renderWizardTabs({\n steps: customSteps,\n currentStep: \"one\",\n });\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatCustomStepLabel(customSteps[0]).full);\n expect(output).toContain(formatCustomStepLabel(customSteps[1]).full);\n expect(output).not.toContain(formatStepLabel(\"stack\").label);\n });\n\n it(\"should render horizontal dividers above and below tabs\", () => {\n const { lastFrame, unmount } = renderWizardTabs();\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(\"\\u2500\");\n });\n });\n\n describe(\"current step\", () => {\n it(\"should render current step label\", () => {\n const { lastFrame, unmount } = renderWizardTabs({\n currentStep: \"build\",\n });\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatStepLabel(\"build\").full);\n });\n\n it(\"should mark first step as current by default\", () => {\n const { lastFrame, unmount } = renderWizardTabs({\n currentStep: \"stack\",\n completedSteps: [],\n });\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatStepLabel(\"stack\").full);\n });\n\n it(\"should update current step when changed\", () => {\n const { lastFrame, unmount } = renderWizardTabs({\n currentStep: \"confirm\",\n completedSteps: [\"stack\", \"build\"],\n });\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatStepLabel(\"confirm\").full);\n });\n });\n\n describe(\"completed steps\", () => {\n it(\"should render completed step labels\", () => {\n const { lastFrame, unmount } = renderWizardTabs({\n currentStep: \"build\",\n completedSteps: [\"stack\"],\n });\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatStepLabel(\"stack\").full);\n });\n\n it(\"should render multiple completed steps\", () => {\n const { lastFrame, unmount } = renderWizardTabs({\n currentStep: \"sources\",\n completedSteps: [\"stack\", \"build\"],\n });\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatStepLabel(\"stack\").full);\n expect(output).toContain(formatStepLabel(\"build\").full);\n });\n\n it(\"should render current step separately from completed steps\", () => {\n const { lastFrame, unmount } = renderWizardTabs({\n currentStep: \"stack\",\n completedSteps: [],\n });\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatStepLabel(\"stack\").full);\n });\n });\n\n describe(\"pending steps\", () => {\n it(\"should render pending step labels\", () => {\n const { lastFrame, unmount } = renderWizardTabs({\n currentStep: \"stack\",\n completedSteps: [],\n });\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatStepLabel(\"build\").full);\n expect(output).toContain(formatStepLabel(\"sources\").full);\n });\n\n it(\"should render steps after current\", () => {\n const { lastFrame, unmount } = renderWizardTabs({\n currentStep: \"build\",\n completedSteps: [\"stack\"],\n });\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatStepLabel(\"confirm\").full);\n });\n });\n\n describe(\"skipped steps\", () => {\n it(\"should render skipped step labels\", () => {\n const { lastFrame, unmount } = renderWizardTabs({\n currentStep: \"sources\",\n completedSteps: [\"stack\"],\n skippedSteps: [\"build\"],\n });\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatStepLabel(\"build\").full);\n });\n\n it(\"should handle multiple skipped steps\", () => {\n const { lastFrame, unmount } = renderWizardTabs({\n currentStep: \"confirm\",\n completedSteps: [\"stack\"],\n skippedSteps: [\"build\", \"sources\"],\n });\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatStepLabel(\"build\").full);\n expect(output).toContain(formatStepLabel(\"sources\").full);\n });\n\n it(\"should prioritize completed over skipped when step is in both arrays\", () => {\n const { lastFrame, unmount } = renderWizardTabs({\n currentStep: \"sources\",\n completedSteps: [\"stack\", \"build\"],\n skippedSteps: [\"build\"],\n });\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatStepLabel(\"stack\").full);\n expect(output).toContain(formatStepLabel(\"build\").full);\n });\n });\n\n describe(\"state priority\", () => {\n it(\"should prioritize completed over current\", () => {\n const { lastFrame, unmount } = renderWizardTabs({\n currentStep: \"stack\",\n completedSteps: [\"stack\"],\n });\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatStepLabel(\"stack\").full);\n });\n\n it(\"should prioritize current over skipped\", () => {\n const { lastFrame, unmount } = renderWizardTabs({\n currentStep: \"build\",\n completedSteps: [],\n skippedSteps: [\"build\"],\n });\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatStepLabel(\"build\").full);\n });\n\n it(\"should prioritize completed over skipped\", () => {\n const { lastFrame, unmount } = renderWizardTabs({\n currentStep: \"sources\",\n completedSteps: [\"stack\"],\n skippedSteps: [\"stack\"],\n });\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatStepLabel(\"stack\").full);\n });\n });\n\n describe(\"visual layout\", () => {\n it(\"should render tabs horizontally\", () => {\n const { lastFrame, unmount } = renderWizardTabs();\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatStepLabel(\"stack\").label);\n expect(output).toContain(formatStepLabel(\"confirm\").label);\n });\n\n it(\"should include step labels\", () => {\n const { lastFrame, unmount } = renderWizardTabs();\n cleanup = unmount;\n\n const output = lastFrame();\n WIZARD_STEPS.forEach((step) => {\n expect(output).toContain(formatStepLabel(step.id as WizardStep).label);\n });\n });\n });\n\n describe(\"edge cases\", () => {\n it(\"should handle empty completed steps\", () => {\n const { lastFrame, unmount } = renderWizardTabs({\n currentStep: \"stack\",\n completedSteps: [],\n });\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatStepLabel(\"stack\").full);\n expect(output).toContain(formatStepLabel(\"confirm\").full);\n });\n\n it(\"should handle empty skipped steps\", () => {\n const { lastFrame, unmount } = renderWizardTabs({\n currentStep: \"sources\",\n completedSteps: [\"stack\", \"build\"],\n skippedSteps: [],\n });\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatStepLabel(\"stack\").full);\n expect(output).toContain(formatStepLabel(\"build\").full);\n expect(output).toContain(formatStepLabel(\"sources\").full);\n });\n\n it(\"should handle all steps completed\", () => {\n const { lastFrame, unmount } = renderWizardTabs({\n currentStep: \"confirm\",\n completedSteps: [\"stack\", \"build\", \"sources\", \"confirm\"],\n });\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatStepLabel(\"stack\").full);\n expect(output).toContain(formatStepLabel(\"build\").full);\n expect(output).toContain(formatStepLabel(\"sources\").full);\n expect(output).toContain(formatStepLabel(\"confirm\").full);\n });\n\n it(\"should handle single step\", () => {\n const singleStep = [{ id: \"only\", label: \"Only Step\", number: 1 }];\n const { lastFrame, unmount } = renderWizardTabs({\n steps: singleStep,\n currentStep: \"only\",\n completedSteps: [],\n });\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatCustomStepLabel(singleStep[0]).full);\n });\n });\n});\n"],"mappings":"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","names":[]}
1
+ {"version":3,"sources":["../../../src/cli/components/wizard/wizard-tabs.test.tsx"],"sourcesContent":["import { render } from \"ink-testing-library\";\nimport { afterEach, describe, expect, it } from \"vitest\";\nimport type { WizardStep } from \"../../stores/wizard-store\";\nimport { WizardTabs, WIZARD_STEPS, formatStepLabel, type WizardTabsProps } from \"./wizard-tabs\";\n\n/** Format a custom (non-WIZARD_STEPS) step label for test assertions */\nconst formatCustomStepLabel = (step: { label: string; number: number }) => {\n const prefix = `[${step.number}]`;\n return { prefix, label: step.label, full: `${prefix} ${step.label}` };\n};\n\nconst renderWizardTabs = (props: Partial<WizardTabsProps> = {}) => {\n const defaultProps: WizardTabsProps = {\n steps: WIZARD_STEPS,\n currentStep: \"stack\",\n completedSteps: [],\n skippedSteps: [],\n ...props,\n };\n return render(<WizardTabs {...defaultProps} />);\n};\n\ndescribe(\"WizardTabs component\", () => {\n let cleanup: (() => void) | undefined;\n\n afterEach(() => {\n cleanup?.();\n cleanup = undefined;\n });\n\n describe(\"rendering\", () => {\n it(\"should render all 4 tabs\", () => {\n const { lastFrame, unmount } = renderWizardTabs();\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatStepLabel(\"stack\").full);\n expect(output).toContain(formatStepLabel(\"build\").full);\n expect(output).toContain(formatStepLabel(\"sources\").full);\n expect(output).toContain(formatStepLabel(\"confirm\").full);\n });\n\n it(\"should render all step numbers\", () => {\n const { lastFrame, unmount } = renderWizardTabs();\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatStepLabel(\"stack\").prefix);\n expect(output).toContain(formatStepLabel(\"build\").prefix);\n expect(output).toContain(formatStepLabel(\"sources\").prefix);\n expect(output).toContain(formatStepLabel(\"confirm\").prefix);\n });\n\n it(\"should render with custom steps\", () => {\n const customSteps = [\n { id: \"stack\" as WizardStep, label: \"First\", number: 1 },\n { id: \"build\" as WizardStep, label: \"Second\", number: 2 },\n ];\n const { lastFrame, unmount } = renderWizardTabs({\n steps: customSteps,\n currentStep: \"stack\",\n });\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatCustomStepLabel(customSteps[0]).full);\n expect(output).toContain(formatCustomStepLabel(customSteps[1]).full);\n });\n\n it(\"should render horizontal dividers above and below tabs\", () => {\n const { lastFrame, unmount } = renderWizardTabs();\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(\"\\u2500\");\n });\n });\n\n describe(\"current step\", () => {\n it(\"should render current step label\", () => {\n const { lastFrame, unmount } = renderWizardTabs({\n currentStep: \"build\",\n });\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatStepLabel(\"build\").full);\n });\n\n it(\"should mark first step as current by default\", () => {\n const { lastFrame, unmount } = renderWizardTabs({\n currentStep: \"stack\",\n completedSteps: [],\n });\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatStepLabel(\"stack\").full);\n });\n\n it(\"should update current step when changed\", () => {\n const { lastFrame, unmount } = renderWizardTabs({\n currentStep: \"confirm\",\n completedSteps: [\"stack\", \"build\"],\n });\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatStepLabel(\"confirm\").full);\n });\n });\n\n describe(\"completed steps\", () => {\n it(\"should render completed step labels\", () => {\n const { lastFrame, unmount } = renderWizardTabs({\n currentStep: \"build\",\n completedSteps: [\"stack\"],\n });\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatStepLabel(\"stack\").full);\n });\n\n it(\"should render multiple completed steps\", () => {\n const { lastFrame, unmount } = renderWizardTabs({\n currentStep: \"sources\",\n completedSteps: [\"stack\", \"build\"],\n });\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatStepLabel(\"stack\").full);\n expect(output).toContain(formatStepLabel(\"build\").full);\n });\n\n it(\"should render current step separately from completed steps\", () => {\n const { lastFrame, unmount } = renderWizardTabs({\n currentStep: \"stack\",\n completedSteps: [],\n });\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatStepLabel(\"stack\").full);\n });\n });\n\n describe(\"pending steps\", () => {\n it(\"should render pending step labels\", () => {\n const { lastFrame, unmount } = renderWizardTabs({\n currentStep: \"stack\",\n completedSteps: [],\n });\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatStepLabel(\"build\").full);\n expect(output).toContain(formatStepLabel(\"sources\").full);\n });\n\n it(\"should render steps after current\", () => {\n const { lastFrame, unmount } = renderWizardTabs({\n currentStep: \"build\",\n completedSteps: [\"stack\"],\n });\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatStepLabel(\"confirm\").full);\n });\n });\n\n describe(\"skipped steps\", () => {\n it(\"should render skipped step labels\", () => {\n const { lastFrame, unmount } = renderWizardTabs({\n currentStep: \"sources\",\n completedSteps: [\"stack\"],\n skippedSteps: [\"build\"],\n });\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatStepLabel(\"build\").full);\n });\n\n it(\"should handle multiple skipped steps\", () => {\n const { lastFrame, unmount } = renderWizardTabs({\n currentStep: \"confirm\",\n completedSteps: [\"stack\"],\n skippedSteps: [\"build\", \"sources\"],\n });\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatStepLabel(\"build\").full);\n expect(output).toContain(formatStepLabel(\"sources\").full);\n });\n\n it(\"should prioritize completed over skipped when step is in both arrays\", () => {\n const { lastFrame, unmount } = renderWizardTabs({\n currentStep: \"sources\",\n completedSteps: [\"stack\", \"build\"],\n skippedSteps: [\"build\"],\n });\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatStepLabel(\"stack\").full);\n expect(output).toContain(formatStepLabel(\"build\").full);\n });\n });\n\n describe(\"state priority\", () => {\n it(\"should prioritize completed over current\", () => {\n const { lastFrame, unmount } = renderWizardTabs({\n currentStep: \"stack\",\n completedSteps: [\"stack\"],\n });\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatStepLabel(\"stack\").full);\n });\n\n it(\"should prioritize current over skipped\", () => {\n const { lastFrame, unmount } = renderWizardTabs({\n currentStep: \"build\",\n completedSteps: [],\n skippedSteps: [\"build\"],\n });\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatStepLabel(\"build\").full);\n });\n\n it(\"should prioritize completed over skipped\", () => {\n const { lastFrame, unmount } = renderWizardTabs({\n currentStep: \"sources\",\n completedSteps: [\"stack\"],\n skippedSteps: [\"stack\"],\n });\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatStepLabel(\"stack\").full);\n });\n });\n\n describe(\"visual layout\", () => {\n it(\"should render tabs horizontally\", () => {\n const { lastFrame, unmount } = renderWizardTabs();\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatStepLabel(\"stack\").label);\n expect(output).toContain(formatStepLabel(\"confirm\").label);\n });\n\n it(\"should include step labels\", () => {\n const { lastFrame, unmount } = renderWizardTabs();\n cleanup = unmount;\n\n const output = lastFrame();\n WIZARD_STEPS.forEach((step) => {\n expect(output).toContain(formatStepLabel(step.id).label);\n });\n });\n });\n\n describe(\"edge cases\", () => {\n it(\"should handle empty completed steps\", () => {\n const { lastFrame, unmount } = renderWizardTabs({\n currentStep: \"stack\",\n completedSteps: [],\n });\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatStepLabel(\"stack\").full);\n expect(output).toContain(formatStepLabel(\"confirm\").full);\n });\n\n it(\"should handle empty skipped steps\", () => {\n const { lastFrame, unmount } = renderWizardTabs({\n currentStep: \"sources\",\n completedSteps: [\"stack\", \"build\"],\n skippedSteps: [],\n });\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatStepLabel(\"stack\").full);\n expect(output).toContain(formatStepLabel(\"build\").full);\n expect(output).toContain(formatStepLabel(\"sources\").full);\n });\n\n it(\"should handle all steps completed\", () => {\n const { lastFrame, unmount } = renderWizardTabs({\n currentStep: \"confirm\",\n completedSteps: [\"stack\", \"build\", \"sources\", \"confirm\"],\n });\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatStepLabel(\"stack\").full);\n expect(output).toContain(formatStepLabel(\"build\").full);\n expect(output).toContain(formatStepLabel(\"sources\").full);\n expect(output).toContain(formatStepLabel(\"confirm\").full);\n });\n\n it(\"should handle single step\", () => {\n const singleStep = [{ id: \"confirm\" as WizardStep, label: \"Only Step\", number: 1 }];\n const { lastFrame, unmount } = renderWizardTabs({\n steps: singleStep,\n currentStep: \"confirm\",\n completedSteps: [],\n });\n cleanup = unmount;\n\n const output = lastFrame();\n expect(output).toContain(formatCustomStepLabel(singleStep[0]).full);\n });\n });\n});\n"],"mappings":"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","names":[]}