@ob1-sg/horizon 0.1.10 → 0.1.11

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 (153) hide show
  1. package/dist/cli.d.ts +3 -0
  2. package/dist/cli.d.ts.map +1 -0
  3. package/dist/cli.js +43 -0
  4. package/dist/cli.js.map +1 -0
  5. package/dist/config.d.ts +10 -0
  6. package/dist/config.d.ts.map +1 -0
  7. package/dist/config.js +293 -0
  8. package/dist/config.js.map +1 -0
  9. package/dist/index.d.ts +4 -0
  10. package/dist/index.d.ts.map +1 -0
  11. package/dist/index.js +629 -0
  12. package/dist/index.js.map +1 -0
  13. package/dist/lib/__tests__/attachment-downloader.test.d.ts +2 -0
  14. package/dist/lib/__tests__/attachment-downloader.test.d.ts.map +1 -0
  15. package/dist/lib/__tests__/attachment-downloader.test.js +163 -0
  16. package/dist/lib/__tests__/attachment-downloader.test.js.map +1 -0
  17. package/dist/lib/__tests__/cli-detection.test.d.ts +2 -0
  18. package/dist/lib/__tests__/cli-detection.test.d.ts.map +1 -0
  19. package/dist/lib/__tests__/cli-detection.test.js +119 -0
  20. package/dist/lib/__tests__/cli-detection.test.js.map +1 -0
  21. package/dist/lib/__tests__/config.test.d.ts +2 -0
  22. package/dist/lib/__tests__/config.test.d.ts.map +1 -0
  23. package/dist/lib/__tests__/config.test.js +291 -0
  24. package/dist/lib/__tests__/config.test.js.map +1 -0
  25. package/dist/lib/__tests__/gcp.test.d.ts +2 -0
  26. package/dist/lib/__tests__/gcp.test.d.ts.map +1 -0
  27. package/dist/lib/__tests__/gcp.test.js +104 -0
  28. package/dist/lib/__tests__/gcp.test.js.map +1 -0
  29. package/dist/lib/__tests__/git.test.d.ts +2 -0
  30. package/dist/lib/__tests__/git.test.d.ts.map +1 -0
  31. package/dist/lib/__tests__/git.test.js +62 -0
  32. package/dist/lib/__tests__/git.test.js.map +1 -0
  33. package/dist/lib/__tests__/linear-quick-check.test.d.ts +2 -0
  34. package/dist/lib/__tests__/linear-quick-check.test.d.ts.map +1 -0
  35. package/dist/lib/__tests__/linear-quick-check.test.js +152 -0
  36. package/dist/lib/__tests__/linear-quick-check.test.js.map +1 -0
  37. package/dist/lib/__tests__/loop-instance-name.test.d.ts +2 -0
  38. package/dist/lib/__tests__/loop-instance-name.test.d.ts.map +1 -0
  39. package/dist/lib/__tests__/loop-instance-name.test.js +90 -0
  40. package/dist/lib/__tests__/loop-instance-name.test.js.map +1 -0
  41. package/dist/lib/__tests__/output-logger.test.d.ts +2 -0
  42. package/dist/lib/__tests__/output-logger.test.d.ts.map +1 -0
  43. package/dist/lib/__tests__/output-logger.test.js +136 -0
  44. package/dist/lib/__tests__/output-logger.test.js.map +1 -0
  45. package/dist/lib/__tests__/prompts.test.d.ts +2 -0
  46. package/dist/lib/__tests__/prompts.test.d.ts.map +1 -0
  47. package/dist/lib/__tests__/prompts.test.js +70 -0
  48. package/dist/lib/__tests__/prompts.test.js.map +1 -0
  49. package/dist/lib/__tests__/provider.test.d.ts +2 -0
  50. package/dist/lib/__tests__/provider.test.d.ts.map +1 -0
  51. package/dist/lib/__tests__/provider.test.js +89 -0
  52. package/dist/lib/__tests__/provider.test.js.map +1 -0
  53. package/dist/lib/__tests__/rate-limit.test.d.ts +2 -0
  54. package/dist/lib/__tests__/rate-limit.test.d.ts.map +1 -0
  55. package/dist/lib/__tests__/rate-limit.test.js +275 -0
  56. package/dist/lib/__tests__/rate-limit.test.js.map +1 -0
  57. package/dist/lib/__tests__/readline.test.d.ts +2 -0
  58. package/dist/lib/__tests__/readline.test.d.ts.map +1 -0
  59. package/dist/lib/__tests__/readline.test.js +55 -0
  60. package/dist/lib/__tests__/readline.test.js.map +1 -0
  61. package/dist/lib/__tests__/stats-logger.test.d.ts +2 -0
  62. package/dist/lib/__tests__/stats-logger.test.d.ts.map +1 -0
  63. package/dist/lib/__tests__/stats-logger.test.js +297 -0
  64. package/dist/lib/__tests__/stats-logger.test.js.map +1 -0
  65. package/dist/lib/__tests__/update-checker.test.d.ts +2 -0
  66. package/dist/lib/__tests__/update-checker.test.d.ts.map +1 -0
  67. package/dist/lib/__tests__/update-checker.test.js +141 -0
  68. package/dist/lib/__tests__/update-checker.test.js.map +1 -0
  69. package/dist/lib/__tests__/version.test.d.ts +2 -0
  70. package/dist/lib/__tests__/version.test.d.ts.map +1 -0
  71. package/dist/lib/__tests__/version.test.js +51 -0
  72. package/dist/lib/__tests__/version.test.js.map +1 -0
  73. package/dist/lib/attachment-downloader.d.ts +26 -0
  74. package/dist/lib/attachment-downloader.d.ts.map +1 -0
  75. package/dist/lib/attachment-downloader.js +259 -0
  76. package/dist/lib/attachment-downloader.js.map +1 -0
  77. package/dist/lib/claude.d.ts +6 -0
  78. package/dist/lib/claude.d.ts.map +1 -0
  79. package/dist/lib/claude.js +358 -0
  80. package/dist/lib/claude.js.map +1 -0
  81. package/dist/lib/cli-detection.d.ts +25 -0
  82. package/dist/lib/cli-detection.d.ts.map +1 -0
  83. package/dist/lib/cli-detection.js +53 -0
  84. package/dist/lib/cli-detection.js.map +1 -0
  85. package/dist/lib/codex.d.ts +4 -0
  86. package/dist/lib/codex.d.ts.map +1 -0
  87. package/dist/lib/codex.js +285 -0
  88. package/dist/lib/codex.js.map +1 -0
  89. package/dist/lib/gcp.d.ts +21 -0
  90. package/dist/lib/gcp.d.ts.map +1 -0
  91. package/dist/lib/gcp.js +96 -0
  92. package/dist/lib/gcp.js.map +1 -0
  93. package/dist/lib/git.d.ts +3 -0
  94. package/dist/lib/git.d.ts.map +1 -0
  95. package/dist/lib/git.js +24 -0
  96. package/dist/lib/git.js.map +1 -0
  97. package/dist/lib/init-project.d.ts +13 -0
  98. package/dist/lib/init-project.d.ts.map +1 -0
  99. package/dist/lib/init-project.js +420 -0
  100. package/dist/lib/init-project.js.map +1 -0
  101. package/dist/lib/linear-api.d.ts +32 -0
  102. package/dist/lib/linear-api.d.ts.map +1 -0
  103. package/dist/lib/linear-api.js +267 -0
  104. package/dist/lib/linear-api.js.map +1 -0
  105. package/dist/lib/linear-quick-check.d.ts +13 -0
  106. package/dist/lib/linear-quick-check.d.ts.map +1 -0
  107. package/dist/lib/linear-quick-check.js +61 -0
  108. package/dist/lib/linear-quick-check.js.map +1 -0
  109. package/dist/lib/loop-instance-name.d.ts +29 -0
  110. package/dist/lib/loop-instance-name.d.ts.map +1 -0
  111. package/dist/lib/loop-instance-name.js +105 -0
  112. package/dist/lib/loop-instance-name.js.map +1 -0
  113. package/dist/lib/output-logger.d.ts +23 -0
  114. package/dist/lib/output-logger.d.ts.map +1 -0
  115. package/dist/lib/output-logger.js +104 -0
  116. package/dist/lib/output-logger.js.map +1 -0
  117. package/dist/lib/prompts.d.ts +17 -0
  118. package/dist/lib/prompts.d.ts.map +1 -0
  119. package/dist/lib/prompts.js +65 -0
  120. package/dist/lib/prompts.js.map +1 -0
  121. package/dist/lib/provider.d.ts +32 -0
  122. package/dist/lib/provider.d.ts.map +1 -0
  123. package/dist/lib/provider.js +27 -0
  124. package/dist/lib/provider.js.map +1 -0
  125. package/dist/lib/rate-limit.d.ts +14 -0
  126. package/dist/lib/rate-limit.d.ts.map +1 -0
  127. package/dist/lib/rate-limit.js +154 -0
  128. package/dist/lib/rate-limit.js.map +1 -0
  129. package/dist/lib/readline.d.ts +4 -0
  130. package/dist/lib/readline.d.ts.map +1 -0
  131. package/dist/lib/readline.js +39 -0
  132. package/dist/lib/readline.js.map +1 -0
  133. package/dist/lib/setup.d.ts +123 -0
  134. package/dist/lib/setup.d.ts.map +1 -0
  135. package/dist/lib/setup.js +492 -0
  136. package/dist/lib/setup.js.map +1 -0
  137. package/dist/lib/stats-logger.d.ts +92 -0
  138. package/dist/lib/stats-logger.d.ts.map +1 -0
  139. package/dist/lib/stats-logger.js +258 -0
  140. package/dist/lib/stats-logger.js.map +1 -0
  141. package/dist/lib/update-checker.d.ts +17 -0
  142. package/dist/lib/update-checker.d.ts.map +1 -0
  143. package/dist/lib/update-checker.js +140 -0
  144. package/dist/lib/update-checker.js.map +1 -0
  145. package/dist/lib/version.d.ts +10 -0
  146. package/dist/lib/version.d.ts.map +1 -0
  147. package/dist/lib/version.js +37 -0
  148. package/dist/lib/version.js.map +1 -0
  149. package/dist/types.d.ts +92 -0
  150. package/dist/types.d.ts.map +1 -0
  151. package/dist/types.js +3 -0
  152. package/dist/types.js.map +1 -0
  153. package/package.json +1 -1
@@ -0,0 +1,420 @@
1
+ /**
2
+ * Horizon configuration wizard (`horizon config`).
3
+ * Shows all current values and allows user to change them with "Enter to keep" UX.
4
+ */
5
+ import { existsSync, readFileSync, writeFileSync, rmSync, } from 'fs';
6
+ import { join } from 'path';
7
+ import { getRepoRoot } from '../config.js';
8
+ import { createLinearClient, validateApiKey, getTeamByKeyOrId, deleteHorizonStatuses, HORIZON_STATUS_PREFIX, getHorizonStatusNames, } from './linear-api.js';
9
+ import { ensureHorizonDir, ensureHorizonDocsDir, ensureGitignore, loadExistingConfig, saveEnvConfig, saveMcpConfig, saveCodexMcpConfig, checkAndDisplayCliAvailability, validateLinearKey, fetchLinearTeams, checkLinearStatuses, createLinearStatuses, createPromptInterface, promptSecret, promptWithDefault, promptConfirm, promptSelect, maskApiKey, } from './setup.js';
10
+ /**
11
+ * Main configuration wizard for `horizon config`.
12
+ */
13
+ export async function configProject() {
14
+ const projectRoot = getRepoRoot();
15
+ console.log('');
16
+ console.log('╭─ Horizon Configuration ─╮');
17
+ console.log('');
18
+ console.log(`Project: ${projectRoot}`);
19
+ console.log('');
20
+ // Ensure directories exist
21
+ ensureHorizonDir();
22
+ ensureHorizonDocsDir();
23
+ ensureGitignore();
24
+ // Check CLI availability
25
+ const cliAvailability = checkAndDisplayCliAvailability();
26
+ if (!cliAvailability) {
27
+ process.exit(1);
28
+ }
29
+ // Load existing configuration
30
+ const existingConfig = loadExistingConfig();
31
+ const rl = createPromptInterface();
32
+ try {
33
+ // ═══════════════════════════════════════════════════════════════════════════
34
+ // Linear Configuration
35
+ // ═══════════════════════════════════════════════════════════════════════════
36
+ console.log('─── Linear Configuration ───\n');
37
+ // API Key
38
+ let apiKey;
39
+ if (existingConfig.linearApiKey) {
40
+ console.log(`Linear API Key: ${maskApiKey(existingConfig.linearApiKey)} (configured)`);
41
+ const newKey = await promptWithDefault(rl, ' [Enter to keep, or paste new key]', '');
42
+ apiKey = newKey || existingConfig.linearApiKey;
43
+ // Validate if changed
44
+ if (newKey && newKey !== existingConfig.linearApiKey) {
45
+ console.log('Validating...');
46
+ const isValid = await validateLinearKey(newKey);
47
+ if (!isValid) {
48
+ console.log('Invalid API key. Keeping existing key.');
49
+ apiKey = existingConfig.linearApiKey;
50
+ }
51
+ else {
52
+ console.log('✓ Valid');
53
+ }
54
+ }
55
+ }
56
+ else {
57
+ console.log('To get your API key:');
58
+ console.log(' 1. Go to: https://linear.app/settings/account/security/api-keys/new');
59
+ console.log(' 2. Enter a label (e.g., "Horizon")');
60
+ console.log(' 3. Click "Create key"');
61
+ console.log('');
62
+ apiKey = await promptSecret(rl, 'Linear API Key');
63
+ if (!apiKey) {
64
+ console.log('\nLinear API key is required.');
65
+ process.exit(1);
66
+ }
67
+ console.log('Validating...');
68
+ const isValid = await validateLinearKey(apiKey);
69
+ if (!isValid) {
70
+ console.log('Invalid API key.');
71
+ process.exit(1);
72
+ }
73
+ console.log('✓ Valid');
74
+ }
75
+ console.log('');
76
+ // Fetch teams for selection
77
+ console.log('Fetching teams...');
78
+ let teams = [];
79
+ try {
80
+ teams = await fetchLinearTeams(apiKey);
81
+ }
82
+ catch (error) {
83
+ console.log('Failed to fetch teams. Please check your API key.');
84
+ process.exit(1);
85
+ }
86
+ if (teams.length === 0) {
87
+ console.log('No teams found in your Linear workspace.');
88
+ process.exit(1);
89
+ }
90
+ // Team selection
91
+ const currentTeamIndex = existingConfig.linearTeamKey
92
+ ? teams.findIndex((t) => t.key === existingConfig.linearTeamKey)
93
+ : 0;
94
+ const defaultTeamIndex = currentTeamIndex >= 0 ? currentTeamIndex : 0;
95
+ console.log('Select team:');
96
+ const teamOptions = teams.map((team) => ({
97
+ value: team.key,
98
+ label: `${team.name} (${team.key})`,
99
+ }));
100
+ const teamKey = await promptSelect(rl, teamOptions, defaultTeamIndex);
101
+ const selectedTeam = teams.find((t) => t.key === teamKey);
102
+ console.log(`Selected: ${selectedTeam.name} (${selectedTeam.key})`);
103
+ console.log('');
104
+ // ═══════════════════════════════════════════════════════════════════════════
105
+ // Provider Configuration
106
+ // ═══════════════════════════════════════════════════════════════════════════
107
+ console.log('─── Provider ───\n');
108
+ let provider;
109
+ // Determine available options based on CLI detection
110
+ const providerOptions = [];
111
+ if (cliAvailability.claude) {
112
+ providerOptions.push({ value: 'claude', label: 'claude', description: 'Claude Code CLI' });
113
+ }
114
+ if (cliAvailability.codex) {
115
+ providerOptions.push({ value: 'codex', label: 'codex', description: 'OpenAI Codex CLI' });
116
+ }
117
+ if (providerOptions.length === 1) {
118
+ provider = providerOptions[0].value;
119
+ console.log(`Provider: ${provider} (only available option)\n`);
120
+ }
121
+ else {
122
+ const currentProvider = existingConfig.provider || 'claude';
123
+ const defaultProviderIndex = providerOptions.findIndex((p) => p.value === currentProvider);
124
+ console.log('Select provider:');
125
+ provider = await promptSelect(rl, providerOptions, defaultProviderIndex >= 0 ? defaultProviderIndex : 0);
126
+ }
127
+ // ═══════════════════════════════════════════════════════════════════════════
128
+ // Advanced Options
129
+ // ═══════════════════════════════════════════════════════════════════════════
130
+ console.log('─── Model ───\n');
131
+ let claudeModel = existingConfig.claudeModel || 'opus';
132
+ let codexModel = existingConfig.codexModel || 'gpt-5.2';
133
+ let codexEffort = existingConfig.codexReasoningEffort || 'high';
134
+ let maxIterations = existingConfig.maxIterations ?? 0;
135
+ if (provider === 'claude') {
136
+ const modelOptions = [
137
+ { value: 'opus', label: 'opus', description: 'Most capable' },
138
+ { value: 'sonnet', label: 'sonnet', description: 'Balanced' },
139
+ { value: 'haiku', label: 'haiku', description: 'Fastest' },
140
+ ];
141
+ const defaultModelIndex = modelOptions.findIndex((m) => m.value === claudeModel);
142
+ console.log('Select model:');
143
+ claudeModel = await promptSelect(rl, modelOptions, defaultModelIndex >= 0 ? defaultModelIndex : 0);
144
+ }
145
+ else {
146
+ const modelInput = await promptWithDefault(rl, `Codex Model (${codexModel})`, codexModel);
147
+ codexModel = modelInput || codexModel;
148
+ const effortOptions = [
149
+ { value: 'low', label: 'low' },
150
+ { value: 'medium', label: 'medium' },
151
+ { value: 'high', label: 'high' },
152
+ { value: 'extra_high', label: 'extra_high' },
153
+ ];
154
+ const defaultEffortIndex = effortOptions.findIndex((e) => e.value === codexEffort);
155
+ console.log('\nSelect reasoning effort:');
156
+ codexEffort = await promptSelect(rl, effortOptions, defaultEffortIndex >= 0 ? defaultEffortIndex : 2);
157
+ }
158
+ console.log('');
159
+ console.log('─── Advanced ───\n');
160
+ const maxIterInput = await promptWithDefault(rl, `Max Iterations (0=unlimited) (${maxIterations})`, String(maxIterations));
161
+ const parsedMax = parseInt(maxIterInput, 10);
162
+ if (!isNaN(parsedMax) && parsedMax >= 0) {
163
+ maxIterations = parsedMax;
164
+ }
165
+ console.log('');
166
+ // ═══════════════════════════════════════════════════════════════════════════
167
+ // Merge Mode Configuration
168
+ // ═══════════════════════════════════════════════════════════════════════════
169
+ console.log('─── Merge Mode ───\n');
170
+ const currentMergeMode = existingConfig.mergeMode || 'auto';
171
+ const mergeModeOptions = [
172
+ { value: 'auto', label: 'auto', description: 'Agent decides: merge directly or create PR (recommended)' },
173
+ { value: 'merge', label: 'merge', description: 'Merge directly to main' },
174
+ { value: 'pr', label: 'pr', description: 'Create PR for review' },
175
+ ];
176
+ const defaultMergeIndex = mergeModeOptions.findIndex((m) => m.value === currentMergeMode);
177
+ console.log('When work completes:');
178
+ const mergeMode = await promptSelect(rl, mergeModeOptions, defaultMergeIndex >= 0 ? defaultMergeIndex : 0);
179
+ console.log('');
180
+ // ═══════════════════════════════════════════════════════════════════════════
181
+ // Summary
182
+ // ═══════════════════════════════════════════════════════════════════════════
183
+ console.log('─── Summary ───\n');
184
+ console.log(` Team: ${selectedTeam.name} (${selectedTeam.key})`);
185
+ console.log(` Provider: ${provider}${provider === 'claude' ? ` (${claudeModel})` : ` (${codexModel})`}`);
186
+ console.log(` Merge: ${mergeMode}`);
187
+ console.log(` Max iterations: ${maxIterations === 0 ? 'unlimited' : maxIterations}`);
188
+ console.log('');
189
+ // ═══════════════════════════════════════════════════════════════════════════
190
+ // Save Configuration
191
+ // ═══════════════════════════════════════════════════════════════════════════
192
+ const newConfig = {
193
+ linearApiKey: apiKey,
194
+ linearTeamKey: teamKey,
195
+ provider,
196
+ claudeModel,
197
+ codexModel,
198
+ codexReasoningEffort: codexEffort,
199
+ maxIterations,
200
+ mergeMode,
201
+ };
202
+ saveEnvConfig(newConfig);
203
+ saveMcpConfig(apiKey);
204
+ // Configure Codex MCP if using Codex provider
205
+ if (provider === 'codex') {
206
+ saveCodexMcpConfig();
207
+ }
208
+ console.log('Saved to .horizon/env');
209
+ // ═══════════════════════════════════════════════════════════════════════════
210
+ // Linear Workflow Statuses
211
+ // ═══════════════════════════════════════════════════════════════════════════
212
+ console.log('');
213
+ console.log('─── Linear Workflow Statuses ───\n');
214
+ const statusesExist = await checkLinearStatuses(apiKey, teamKey);
215
+ if (statusesExist) {
216
+ console.log(`${HORIZON_STATUS_PREFIX} statuses already exist. No action needed.\n`);
217
+ }
218
+ else {
219
+ console.log('Horizon will create the following workflow statuses:\n');
220
+ const statusNames = getHorizonStatusNames();
221
+ statusNames.forEach((name) => {
222
+ console.log(` • ${name}`);
223
+ });
224
+ console.log('');
225
+ console.log(`These statuses use the ${HORIZON_STATUS_PREFIX} prefix to avoid conflicts`);
226
+ console.log('with your existing workflow statuses.\n');
227
+ const createStatuses = await promptConfirm(rl, 'Create these statuses?', true);
228
+ if (createStatuses) {
229
+ console.log('\nCreating statuses...');
230
+ const result = await createLinearStatuses(apiKey, teamKey);
231
+ if (result.created.length > 0) {
232
+ console.log(`Created ${result.created.length} status(es).`);
233
+ }
234
+ if (result.existing.length > 0) {
235
+ console.log(`Found ${result.existing.length} existing status(es).`);
236
+ }
237
+ if (result.errors.length > 0) {
238
+ console.log(`Errors (${result.errors.length}):`);
239
+ result.errors.forEach((err) => console.log(` - ${err}`));
240
+ }
241
+ }
242
+ else {
243
+ console.log('\nSkipped status creation. You can create them later by running `horizon config` again.');
244
+ }
245
+ }
246
+ // Show Codex MCP status if using Codex
247
+ if (provider === 'codex') {
248
+ console.log('');
249
+ console.log('─── Codex MCP ───\n');
250
+ console.log('Linear MCP configured in ~/.codex/config.toml');
251
+ console.log('(Uses LINEAR_API_KEY from .horizon/env)');
252
+ }
253
+ // Done
254
+ console.log('');
255
+ console.log('✓ Configuration complete');
256
+ console.log(' Run `horizon` to start');
257
+ console.log('');
258
+ }
259
+ finally {
260
+ rl.close();
261
+ }
262
+ }
263
+ /**
264
+ * Removes Horizon from the current project (`horizon uninstall`).
265
+ */
266
+ export async function uninstallProject() {
267
+ const projectRoot = getRepoRoot();
268
+ const horizonDir = join(projectRoot, '.horizon');
269
+ console.log('');
270
+ console.log('╭─ Horizon Uninstall ─╮');
271
+ console.log('');
272
+ console.log(`Project: ${projectRoot}`);
273
+ console.log('');
274
+ // Check if Horizon is even installed
275
+ if (!existsSync(horizonDir)) {
276
+ console.log('Horizon is not installed in this project.');
277
+ console.log('(No .horizon/ directory found)');
278
+ process.exit(0);
279
+ }
280
+ // Show what will be removed
281
+ console.log('This will remove:');
282
+ console.log('');
283
+ console.log(' 1. .horizon/ directory containing:');
284
+ console.log(' - env (Linear API key and configuration)');
285
+ console.log(' - mcp.json (MCP configuration)');
286
+ console.log(' - prompts/ (agent prompts)');
287
+ console.log(' - output/ (run logs and session data)');
288
+ console.log('');
289
+ console.log(' 2. .horizon/ entry from .gitignore');
290
+ console.log('');
291
+ // Load existing config to check for Linear credentials
292
+ const existingConfig = loadExistingConfig();
293
+ const hasLinearConfig = existingConfig.linearApiKey && existingConfig.linearTeamKey;
294
+ if (hasLinearConfig) {
295
+ console.log(` 3. Optionally: ${HORIZON_STATUS_PREFIX} workflow statuses from Linear`);
296
+ console.log(' (Only empty statuses can be deleted)');
297
+ console.log('');
298
+ }
299
+ console.log('─────────────────────────────────────────');
300
+ console.log('');
301
+ const rl = createPromptInterface();
302
+ try {
303
+ // Confirm uninstall
304
+ const confirmUninstall = await promptConfirm(rl, 'Proceed with uninstall?', false);
305
+ if (!confirmUninstall) {
306
+ console.log('');
307
+ console.log('Uninstall cancelled.');
308
+ process.exit(0);
309
+ }
310
+ console.log('');
311
+ // Ask about Linear statuses if configured
312
+ let deleteStatuses = false;
313
+ if (hasLinearConfig) {
314
+ deleteStatuses = await promptConfirm(rl, `Delete ${HORIZON_STATUS_PREFIX} workflow statuses from Linear?`, false);
315
+ }
316
+ console.log('');
317
+ // Step 1: Delete Linear statuses (before we lose the API key!)
318
+ if (deleteStatuses && existingConfig.linearApiKey && existingConfig.linearTeamKey) {
319
+ console.log('Removing Linear workflow statuses...');
320
+ try {
321
+ const client = createLinearClient(existingConfig.linearApiKey);
322
+ // Validate API key still works
323
+ const isValid = await validateApiKey(client);
324
+ if (!isValid) {
325
+ console.log(' Warning: Linear API key is invalid. Skipping status deletion.');
326
+ }
327
+ else {
328
+ // Get team
329
+ const team = await getTeamByKeyOrId(client, existingConfig.linearTeamKey);
330
+ if (!team) {
331
+ console.log(` Warning: Team "${existingConfig.linearTeamKey}" not found. Skipping status deletion.`);
332
+ }
333
+ else {
334
+ const result = await deleteHorizonStatuses(client, team.id);
335
+ // Report results
336
+ if (result.deleted.length > 0) {
337
+ console.log(` Deleted ${result.deleted.length} status(es):`);
338
+ for (const name of result.deleted) {
339
+ console.log(` ✓ ${name}`);
340
+ }
341
+ }
342
+ if (result.skipped.length > 0) {
343
+ console.log('');
344
+ console.log(` Skipped ${result.skipped.length} status(es) with active issues:`);
345
+ for (const { name, issueCount } of result.skipped) {
346
+ console.log(` ⚠ ${name} (${issueCount} issue${issueCount > 1 ? 's' : ''})`);
347
+ }
348
+ console.log('');
349
+ console.log(' To delete these statuses manually:');
350
+ console.log(' 1. Move issues to other statuses in Linear');
351
+ console.log(' 2. Go to Settings → Teams → Workflow');
352
+ console.log(` 3. Delete the ${HORIZON_STATUS_PREFIX} statuses`);
353
+ }
354
+ if (result.errors.length > 0) {
355
+ console.log('');
356
+ console.log(` Errors (${result.errors.length}):`);
357
+ for (const error of result.errors) {
358
+ console.log(` ✗ ${error}`);
359
+ }
360
+ }
361
+ }
362
+ }
363
+ }
364
+ catch (error) {
365
+ const msg = error instanceof Error ? error.message : String(error);
366
+ console.log(` Error connecting to Linear: ${msg}`);
367
+ }
368
+ console.log('');
369
+ }
370
+ // Step 2: Remove .horizon/ directory
371
+ console.log('Removing .horizon/ directory...');
372
+ try {
373
+ rmSync(horizonDir, { recursive: true, force: true });
374
+ console.log(' ✓ Removed .horizon/');
375
+ }
376
+ catch (error) {
377
+ const msg = error instanceof Error ? error.message : String(error);
378
+ console.log(` ✗ Error removing .horizon/: ${msg}`);
379
+ }
380
+ // Step 3: Clean up .gitignore
381
+ console.log('Cleaning up .gitignore...');
382
+ const removedFromGitignore = removeFromGitignore(projectRoot);
383
+ if (removedFromGitignore) {
384
+ console.log(' ✓ Removed .horizon/ from .gitignore');
385
+ }
386
+ else {
387
+ console.log(' (No changes needed)');
388
+ }
389
+ console.log('');
390
+ console.log('✓ Horizon uninstalled');
391
+ }
392
+ finally {
393
+ rl.close();
394
+ }
395
+ }
396
+ /**
397
+ * Removes .horizon/ entry from .gitignore.
398
+ */
399
+ function removeFromGitignore(projectRoot) {
400
+ const gitignorePath = join(projectRoot, '.gitignore');
401
+ if (!existsSync(gitignorePath)) {
402
+ return false;
403
+ }
404
+ const content = readFileSync(gitignorePath, 'utf-8');
405
+ const lines = content.split('\n');
406
+ // Filter out .horizon/ related lines
407
+ const filteredLines = lines.filter((line) => {
408
+ const trimmed = line.trim();
409
+ return trimmed !== '.horizon/' && trimmed !== '.horizon' && trimmed !== '# Horizon runtime data';
410
+ });
411
+ // Only write if we actually removed something
412
+ if (filteredLines.length < lines.length) {
413
+ // Clean up any double newlines that might result
414
+ const newContent = filteredLines.join('\n').replace(/\n{3,}/g, '\n\n');
415
+ writeFileSync(gitignorePath, newContent);
416
+ return true;
417
+ }
418
+ return false;
419
+ }
420
+ //# sourceMappingURL=init-project.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"init-project.js","sourceRoot":"","sources":["../../src/lib/init-project.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,32 @@
1
+ import { LinearClient } from '@linear/sdk';
2
+ import { WorkflowState, HorizonStatusDefinition, InitResult } from '../types.js';
3
+ export declare const HORIZON_STATUS_PREFIX = "\u221E";
4
+ interface HorizonStatusWithColor extends HorizonStatusDefinition {
5
+ color: string;
6
+ }
7
+ export declare const HORIZON_STATUS_DEFINITIONS: HorizonStatusWithColor[];
8
+ export declare function createLinearClient(apiKey: string): LinearClient;
9
+ export declare function createLinearClientWithSignedUrls(apiKey: string, expireInSeconds?: number): LinearClient;
10
+ export declare function listWorkflowStates(client: LinearClient, teamId: string): Promise<WorkflowState[]>;
11
+ export declare function createWorkflowState(client: LinearClient, teamId: string, state: HorizonStatusWithColor): Promise<WorkflowState>;
12
+ export declare function getHorizonStatusNames(): string[];
13
+ export declare function checkHorizonStatusesExist(client: LinearClient, teamId: string): Promise<boolean>;
14
+ export declare function ensureHorizonStatuses(client: LinearClient, teamId: string): Promise<InitResult>;
15
+ export declare function getTeamByKeyOrId(client: LinearClient, keyOrId: string): Promise<{
16
+ id: string;
17
+ name: string;
18
+ key: string;
19
+ } | undefined>;
20
+ export declare function validateApiKey(client: LinearClient): Promise<boolean>;
21
+ export interface DeleteStatusesResult {
22
+ deleted: string[];
23
+ skipped: {
24
+ name: string;
25
+ issueCount: number;
26
+ }[];
27
+ errors: string[];
28
+ }
29
+ export declare function getIssueDescription(client: LinearClient, issueIdentifier: string): Promise<string | null>;
30
+ export declare function deleteHorizonStatuses(client: LinearClient, teamId: string): Promise<DeleteStatusesResult>;
31
+ export {};
32
+ //# sourceMappingURL=linear-api.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"linear-api.d.ts","sourceRoot":"","sources":["../../src/lib/linear-api.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,YAAY,EAAwC,MAAM,aAAa,CAAC;AACjF,OAAO,EAAE,aAAa,EAAE,uBAAuB,EAAE,UAAU,EAAmB,MAAM,aAAa,CAAC;AAGlG,eAAO,MAAM,qBAAqB,WAAM,CAAC;AAYzC,UAAU,sBAAuB,SAAQ,uBAAuB;IAC9D,KAAK,EAAE,MAAM,CAAC;CACf;AAGD,eAAO,MAAM,0BAA0B,EAAE,sBAAsB,EAiB9D,CAAC;AAGF,wBAAgB,kBAAkB,CAAC,MAAM,EAAE,MAAM,GAAG,YAAY,CAE/D;AAKD,wBAAgB,gCAAgC,CAAC,MAAM,EAAE,MAAM,EAAE,eAAe,SAAO,GAAG,YAAY,CAOrG;AAGD,wBAAsB,kBAAkB,CAAC,MAAM,EAAE,YAAY,EAAE,MAAM,EAAE,MAAM,GAAG,OAAO,CAAC,aAAa,EAAE,CAAC,CAYvG;AAGD,wBAAsB,mBAAmB,CACvC,MAAM,EAAE,YAAY,EACpB,MAAM,EAAE,MAAM,EACd,KAAK,EAAE,sBAAsB,GAC5B,OAAO,CAAC,aAAa,CAAC,CAqBxB;AAGD,wBAAgB,qBAAqB,IAAI,MAAM,EAAE,CAEhD;AAGD,wBAAsB,yBAAyB,CAAC,MAAM,EAAE,YAAY,EAAE,MAAM,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC,CAMtG;AAGD,wBAAsB,qBAAqB,CAAC,MAAM,EAAE,YAAY,EAAE,MAAM,EAAE,MAAM,GAAG,OAAO,CAAC,UAAU,CAAC,CAqGrG;AAGD,wBAAsB,gBAAgB,CAAC,MAAM,EAAE,YAAY,EAAE,OAAO,EAAE,MAAM,GAAG,OAAO,CAAC;IAAE,EAAE,EAAE,MAAM,CAAC;IAAC,IAAI,EAAE,MAAM,CAAC;IAAC,GAAG,EAAE,MAAM,CAAA;CAAE,GAAG,SAAS,CAAC,CAc5I;AAGD,wBAAsB,cAAc,CAAC,MAAM,EAAE,YAAY,GAAG,OAAO,CAAC,OAAO,CAAC,CAO3E;AAGD,MAAM,WAAW,oBAAoB;IACnC,OAAO,EAAE,MAAM,EAAE,CAAC;IAClB,OAAO,EAAE;QAAE,IAAI,EAAE,MAAM,CAAC;QAAC,UAAU,EAAE,MAAM,CAAA;KAAE,EAAE,CAAC;IAChD,MAAM,EAAE,MAAM,EAAE,CAAC;CAClB;AAWD,wBAAsB,mBAAmB,CACvC,MAAM,EAAE,YAAY,EACpB,eAAe,EAAE,MAAM,GACtB,OAAO,CAAC,MAAM,GAAG,IAAI,CAAC,CAcxB;AAGD,wBAAsB,qBAAqB,CACzC,MAAM,EAAE,YAAY,EACpB,MAAM,EAAE,MAAM,GACb,OAAO,CAAC,oBAAoB,CAAC,CAoC/B"}