claude-autopm 1.17.0 → 1.20.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (76) hide show
  1. package/README.md +159 -0
  2. package/autopm/.claude/agents/core/mcp-manager.md +1 -1
  3. package/autopm/.claude/commands/pm/context.md +11 -0
  4. package/autopm/.claude/commands/pm/epic-decompose.md +25 -2
  5. package/autopm/.claude/commands/pm/epic-oneshot.md +13 -0
  6. package/autopm/.claude/commands/pm/epic-start.md +19 -0
  7. package/autopm/.claude/commands/pm/epic-sync-modular.md +10 -10
  8. package/autopm/.claude/commands/pm/epic-sync.md +14 -14
  9. package/autopm/.claude/commands/pm/issue-start.md +50 -5
  10. package/autopm/.claude/commands/pm/issue-sync.md +15 -15
  11. package/autopm/.claude/commands/pm/what-next.md +11 -0
  12. package/autopm/.claude/mcp/MCP-REGISTRY.md +1 -1
  13. package/autopm/.claude/scripts/azure/active-work.js +2 -2
  14. package/autopm/.claude/scripts/azure/blocked.js +13 -13
  15. package/autopm/.claude/scripts/azure/daily.js +1 -1
  16. package/autopm/.claude/scripts/azure/dashboard.js +1 -1
  17. package/autopm/.claude/scripts/azure/feature-list.js +2 -2
  18. package/autopm/.claude/scripts/azure/feature-status.js +1 -1
  19. package/autopm/.claude/scripts/azure/next-task.js +1 -1
  20. package/autopm/.claude/scripts/azure/search.js +1 -1
  21. package/autopm/.claude/scripts/azure/setup.js +15 -15
  22. package/autopm/.claude/scripts/azure/sprint-report.js +2 -2
  23. package/autopm/.claude/scripts/azure/sync.js +1 -1
  24. package/autopm/.claude/scripts/azure/us-list.js +1 -1
  25. package/autopm/.claude/scripts/azure/us-status.js +1 -1
  26. package/autopm/.claude/scripts/azure/validate.js +13 -13
  27. package/autopm/.claude/scripts/lib/frontmatter-utils.sh +42 -7
  28. package/autopm/.claude/scripts/lib/logging-utils.sh +20 -16
  29. package/autopm/.claude/scripts/lib/validation-utils.sh +1 -1
  30. package/autopm/.claude/scripts/pm/context.js +338 -0
  31. package/autopm/.claude/scripts/pm/issue-sync/format-comment.sh +3 -3
  32. package/autopm/.claude/scripts/pm/lib/README.md +85 -0
  33. package/autopm/.claude/scripts/pm/lib/logger.js +78 -0
  34. package/autopm/.claude/scripts/pm/next.js +25 -1
  35. package/autopm/.claude/scripts/pm/what-next.js +660 -0
  36. package/bin/autopm.js +25 -0
  37. package/bin/commands/team.js +86 -0
  38. package/package.json +1 -1
  39. package/lib/agentExecutor.js.deprecated +0 -101
  40. package/lib/azure/cache.js +0 -80
  41. package/lib/azure/client.js +0 -77
  42. package/lib/azure/formatter.js +0 -177
  43. package/lib/commandHelpers.js +0 -177
  44. package/lib/context/manager.js +0 -290
  45. package/lib/documentation/manager.js +0 -528
  46. package/lib/github/workflow-manager.js +0 -546
  47. package/lib/helpers/azure-batch-api.js +0 -133
  48. package/lib/helpers/azure-cache-manager.js +0 -287
  49. package/lib/helpers/azure-parallel-processor.js +0 -158
  50. package/lib/helpers/azure-work-item-create.js +0 -278
  51. package/lib/helpers/gh-issue-create.js +0 -250
  52. package/lib/helpers/interactive-prompt.js +0 -336
  53. package/lib/helpers/output-manager.js +0 -335
  54. package/lib/helpers/progress-indicator.js +0 -258
  55. package/lib/performance/benchmarker.js +0 -429
  56. package/lib/pm/epic-decomposer.js +0 -273
  57. package/lib/pm/epic-syncer.js +0 -221
  58. package/lib/prdMetadata.js +0 -270
  59. package/lib/providers/azure/index.js +0 -234
  60. package/lib/providers/factory.js +0 -87
  61. package/lib/providers/github/index.js +0 -204
  62. package/lib/providers/interface.js +0 -73
  63. package/lib/python/scaffold-manager.js +0 -576
  64. package/lib/react/scaffold-manager.js +0 -745
  65. package/lib/regression/analyzer.js +0 -578
  66. package/lib/release/manager.js +0 -324
  67. package/lib/tailwind/manager.js +0 -486
  68. package/lib/traefik/manager.js +0 -484
  69. package/lib/utils/colors.js +0 -126
  70. package/lib/utils/config.js +0 -317
  71. package/lib/utils/filesystem.js +0 -316
  72. package/lib/utils/logger.js +0 -135
  73. package/lib/utils/prompts.js +0 -294
  74. package/lib/utils/shell.js +0 -237
  75. package/lib/validators/email-validator.js +0 -337
  76. package/lib/workflow/manager.js +0 -449
@@ -1,335 +0,0 @@
1
- #!/usr/bin/env node
2
- /**
3
- * Output Manager
4
- * Handles verbose/quiet output modes and formatting
5
- */
6
-
7
- const chalk = require('chalk');
8
-
9
- class OutputManager {
10
- constructor(options = {}) {
11
- this.mode = options.mode || process.env.OUTPUT_MODE || 'normal'; // quiet, normal, verbose, debug
12
- this.useColor = options.color !== false && process.stdout.isTTY;
13
- this.format = options.format || 'text'; // text, json, csv, table
14
- this.logFile = options.logFile;
15
- this.timestamps = options.timestamps || false;
16
-
17
- // Set up chalk
18
- if (!this.useColor) {
19
- chalk.level = 0;
20
- }
21
-
22
- // Output levels
23
- this.levels = {
24
- debug: 0,
25
- verbose: 1,
26
- normal: 2,
27
- quiet: 3,
28
- silent: 4
29
- };
30
-
31
- this.currentLevel = this.levels[this.mode] || 2;
32
- }
33
-
34
- /**
35
- * Set output mode
36
- */
37
- setMode(mode) {
38
- this.mode = mode;
39
- this.currentLevel = this.levels[mode] || 2;
40
- }
41
-
42
- /**
43
- * Check if should output at level
44
- */
45
- shouldOutput(level) {
46
- return this.currentLevel <= this.levels[level];
47
- }
48
-
49
- /**
50
- * Debug output (only in debug mode)
51
- */
52
- debug(...args) {
53
- if (this.shouldOutput('debug')) {
54
- const message = this.formatMessage('[DEBUG]', ...args);
55
- console.error(this.useColor ? chalk.gray(message) : message);
56
- this.log(message);
57
- }
58
- }
59
-
60
- /**
61
- * Verbose output (verbose and debug modes)
62
- */
63
- verbose(...args) {
64
- if (this.shouldOutput('verbose')) {
65
- const message = this.formatMessage('[VERBOSE]', ...args);
66
- console.log(this.useColor ? chalk.dim(message) : message);
67
- this.log(message);
68
- }
69
- }
70
-
71
- /**
72
- * Normal output (normal, verbose, and debug modes)
73
- */
74
- info(...args) {
75
- if (this.shouldOutput('normal')) {
76
- const message = this.formatMessage(...args);
77
- console.log(message);
78
- this.log(message);
79
- }
80
- }
81
-
82
- /**
83
- * Important output (all modes except silent)
84
- */
85
- important(...args) {
86
- if (this.mode !== 'silent') {
87
- const message = this.formatMessage(...args);
88
- console.log(this.useColor ? chalk.bold(message) : message);
89
- this.log(message);
90
- }
91
- }
92
-
93
- /**
94
- * Success message
95
- */
96
- success(...args) {
97
- if (this.shouldOutput('normal')) {
98
- const message = this.formatMessage('✅', ...args);
99
- console.log(this.useColor ? chalk.green(message) : message);
100
- this.log(message);
101
- }
102
- }
103
-
104
- /**
105
- * Warning message
106
- */
107
- warn(...args) {
108
- if (this.mode !== 'silent') {
109
- const message = this.formatMessage('⚠️', ...args);
110
- console.warn(this.useColor ? chalk.yellow(message) : message);
111
- this.log(message);
112
- }
113
- }
114
-
115
- /**
116
- * Error message
117
- */
118
- error(...args) {
119
- const message = this.formatMessage('❌', ...args);
120
- console.error(this.useColor ? chalk.red(message) : message);
121
- this.log(message);
122
- }
123
-
124
- /**
125
- * Format message with optional timestamp
126
- * @private
127
- */
128
- formatMessage(...args) {
129
- let message = args.join(' ');
130
-
131
- if (this.timestamps) {
132
- const timestamp = new Date().toISOString();
133
- message = `[${timestamp}] ${message}`;
134
- }
135
-
136
- return message;
137
- }
138
-
139
- /**
140
- * Log to file if configured
141
- * @private
142
- */
143
- log(message) {
144
- if (this.logFile) {
145
- const fs = require('fs');
146
- fs.appendFileSync(this.logFile, message + '\n');
147
- }
148
- }
149
-
150
- /**
151
- * Output data in specified format
152
- */
153
- output(data, options = {}) {
154
- const format = options.format || this.format;
155
-
156
- switch (format) {
157
- case 'json':
158
- this.outputJSON(data, options);
159
- break;
160
- case 'table':
161
- this.outputTable(data, options);
162
- break;
163
- case 'csv':
164
- this.outputCSV(data, options);
165
- break;
166
- default:
167
- this.outputText(data, options);
168
- }
169
- }
170
-
171
- /**
172
- * Output as JSON
173
- */
174
- outputJSON(data, options = {}) {
175
- const pretty = options.pretty !== false;
176
- const output = pretty ? JSON.stringify(data, null, 2) : JSON.stringify(data);
177
- console.log(output);
178
- }
179
-
180
- /**
181
- * Output as table
182
- */
183
- outputTable(data, options = {}) {
184
- if (!Array.isArray(data) || data.length === 0) {
185
- console.log('No data to display');
186
- return;
187
- }
188
-
189
- const headers = options.headers || Object.keys(data[0]);
190
- const columnWidths = this.calculateColumnWidths(data, headers);
191
-
192
- // Print header
193
- this.printTableRow(headers, columnWidths, true);
194
- this.printTableSeparator(columnWidths);
195
-
196
- // Print data rows
197
- for (const row of data) {
198
- const values = headers.map(h => row[h]);
199
- this.printTableRow(values, columnWidths);
200
- }
201
- }
202
-
203
- /**
204
- * Output as CSV
205
- */
206
- outputCSV(data, options = {}) {
207
- if (!Array.isArray(data) || data.length === 0) {
208
- return;
209
- }
210
-
211
- const headers = options.headers || Object.keys(data[0]);
212
- console.log(headers.join(','));
213
-
214
- for (const row of data) {
215
- const values = headers.map(h => {
216
- const value = row[h];
217
- // Escape values containing commas or quotes
218
- if (typeof value === 'string' && (value.includes(',') || value.includes('"'))) {
219
- return `"${value.replace(/"/g, '""')}"`;
220
- }
221
- return value;
222
- });
223
- console.log(values.join(','));
224
- }
225
- }
226
-
227
- /**
228
- * Output as text
229
- */
230
- outputText(data, options = {}) {
231
- if (typeof data === 'string') {
232
- console.log(data);
233
- } else if (Array.isArray(data)) {
234
- data.forEach(item => console.log(item));
235
- } else {
236
- console.log(JSON.stringify(data, null, 2));
237
- }
238
- }
239
-
240
- /**
241
- * Calculate column widths for table
242
- * @private
243
- */
244
- calculateColumnWidths(data, headers) {
245
- const widths = {};
246
-
247
- for (const header of headers) {
248
- widths[header] = header.length;
249
-
250
- for (const row of data) {
251
- const value = String(row[header] || '');
252
- widths[header] = Math.max(widths[header], value.length);
253
- }
254
- }
255
-
256
- return widths;
257
- }
258
-
259
- /**
260
- * Print table row
261
- * @private
262
- */
263
- printTableRow(values, widths, isHeader = false) {
264
- const cells = values.map((value, index) => {
265
- const width = widths[Object.keys(widths)[index]];
266
- const str = String(value || '').padEnd(width);
267
- return isHeader && this.useColor ? chalk.bold(str) : str;
268
- });
269
-
270
- console.log('| ' + cells.join(' | ') + ' |');
271
- }
272
-
273
- /**
274
- * Print table separator
275
- * @private
276
- */
277
- printTableSeparator(widths) {
278
- const separators = Object.values(widths).map(w => '-'.repeat(w));
279
- console.log('|-' + separators.join('-|-') + '-|');
280
- }
281
-
282
- /**
283
- * Create section header
284
- */
285
- section(title) {
286
- if (this.shouldOutput('normal')) {
287
- const line = '='.repeat(title.length + 4);
288
- console.log('\n' + (this.useColor ? chalk.cyan(line) : line));
289
- console.log((this.useColor ? chalk.cyan.bold(` ${title} `) : ` ${title} `));
290
- console.log((this.useColor ? chalk.cyan(line) : line) + '\n');
291
- }
292
- }
293
-
294
- /**
295
- * Create subsection header
296
- */
297
- subsection(title) {
298
- if (this.shouldOutput('normal')) {
299
- console.log('\n' + (this.useColor ? chalk.blue.bold(title) : title));
300
- console.log((this.useColor ? chalk.blue('-'.repeat(title.length)) : '-'.repeat(title.length)));
301
- }
302
- }
303
-
304
- /**
305
- * Print list items
306
- */
307
- list(items, options = {}) {
308
- if (!this.shouldOutput('normal')) return;
309
-
310
- const bullet = options.bullet || '•';
311
- const indent = options.indent || 2;
312
-
313
- for (const item of items) {
314
- const padding = ' '.repeat(indent);
315
- console.log(`${padding}${bullet} ${item}`);
316
- }
317
- }
318
-
319
- /**
320
- * Print key-value pairs
321
- */
322
- keyValue(pairs, options = {}) {
323
- if (!this.shouldOutput('normal')) return;
324
-
325
- const maxKeyLength = Math.max(...Object.keys(pairs).map(k => k.length));
326
-
327
- for (const [key, value] of Object.entries(pairs)) {
328
- const paddedKey = key.padEnd(maxKeyLength);
329
- const formattedKey = this.useColor ? chalk.gray(paddedKey + ':') : paddedKey + ':';
330
- console.log(` ${formattedKey} ${value}`);
331
- }
332
- }
333
- }
334
-
335
- module.exports = OutputManager;
@@ -1,258 +0,0 @@
1
- #!/usr/bin/env node
2
- /**
3
- * Progress Indicator Helper
4
- * Provides various progress indicators for long operations
5
- */
6
-
7
- const readline = require('readline');
8
-
9
- class ProgressIndicator {
10
- constructor(options = {}) {
11
- this.total = options.total || 0;
12
- this.current = 0;
13
- this.startTime = Date.now();
14
- this.lastUpdate = 0;
15
- this.updateInterval = options.updateInterval || 100; // ms
16
- this.width = options.width || 40;
17
- this.showETA = options.showETA !== false;
18
- this.showSpeed = options.showSpeed !== false;
19
- this.style = options.style || 'bar'; // bar, dots, spinner
20
- this.message = options.message || 'Processing';
21
- this.spinnerFrames = ['⠋', '⠙', '⠹', '⠸', '⠼', '⠴', '⠦', '⠧', '⠇', '⠏'];
22
- this.spinnerIndex = 0;
23
- }
24
-
25
- /**
26
- * Start progress tracking
27
- */
28
- start(message) {
29
- if (message) this.message = message;
30
- this.startTime = Date.now();
31
- this.current = 0;
32
- this.lastUpdate = 0;
33
-
34
- if (this.style === 'spinner') {
35
- this.startSpinner();
36
- }
37
- }
38
-
39
- /**
40
- * Update progress
41
- */
42
- update(current, message) {
43
- if (current !== undefined) this.current = current;
44
- if (message) this.message = message;
45
-
46
- const now = Date.now();
47
- if (now - this.lastUpdate < this.updateInterval) {
48
- return;
49
- }
50
-
51
- this.lastUpdate = now;
52
-
53
- switch (this.style) {
54
- case 'bar':
55
- this.renderBar();
56
- break;
57
- case 'dots':
58
- this.renderDots();
59
- break;
60
- case 'spinner':
61
- this.renderSpinner();
62
- break;
63
- case 'percentage':
64
- this.renderPercentage();
65
- break;
66
- }
67
- }
68
-
69
- /**
70
- * Increment progress by 1
71
- */
72
- increment(message) {
73
- this.current++;
74
- this.update(this.current, message);
75
- }
76
-
77
- /**
78
- * Complete progress
79
- */
80
- complete(message) {
81
- this.current = this.total;
82
- this.update(this.current, message || 'Complete');
83
- process.stdout.write('\n');
84
-
85
- if (this.spinnerInterval) {
86
- clearInterval(this.spinnerInterval);
87
- this.spinnerInterval = null;
88
- }
89
- }
90
-
91
- /**
92
- * Render progress bar
93
- * @private
94
- */
95
- renderBar() {
96
- const percent = this.total > 0 ? this.current / this.total : 0;
97
- const filled = Math.round(percent * this.width);
98
- const empty = this.width - filled;
99
-
100
- const bar = '█'.repeat(filled) + '░'.repeat(empty);
101
- const percentStr = `${Math.round(percent * 100)}%`;
102
-
103
- let output = `\r${this.message}: ${bar} ${percentStr}`;
104
-
105
- if (this.total > 0) {
106
- output += ` (${this.current}/${this.total})`;
107
- }
108
-
109
- if (this.showETA && this.total > 0 && this.current > 0) {
110
- const eta = this.calculateETA();
111
- output += ` ETA: ${eta}`;
112
- }
113
-
114
- if (this.showSpeed && this.current > 0) {
115
- const speed = this.calculateSpeed();
116
- output += ` ${speed}/s`;
117
- }
118
-
119
- process.stdout.write(output);
120
- }
121
-
122
- /**
123
- * Render dots progress
124
- * @private
125
- */
126
- renderDots() {
127
- const dots = '.'.repeat((this.current % 4) + 1).padEnd(4);
128
- const percent = this.total > 0 ? Math.round((this.current / this.total) * 100) : 0;
129
-
130
- let output = `\r${this.message}${dots}`;
131
-
132
- if (this.total > 0) {
133
- output += ` ${percent}% (${this.current}/${this.total})`;
134
- }
135
-
136
- process.stdout.write(output.padEnd(80));
137
- }
138
-
139
- /**
140
- * Render spinner
141
- * @private
142
- */
143
- renderSpinner() {
144
- const frame = this.spinnerFrames[this.spinnerIndex];
145
- let output = `\r${frame} ${this.message}`;
146
-
147
- if (this.total > 0 && this.current > 0) {
148
- const percent = Math.round((this.current / this.total) * 100);
149
- output += ` ${percent}% (${this.current}/${this.total})`;
150
- }
151
-
152
- process.stdout.write(output.padEnd(80));
153
- }
154
-
155
- /**
156
- * Render percentage only
157
- * @private
158
- */
159
- renderPercentage() {
160
- const percent = this.total > 0 ? Math.round((this.current / this.total) * 100) : 0;
161
- const output = `\r${this.message}: ${percent}% (${this.current}/${this.total})`;
162
- process.stdout.write(output.padEnd(80));
163
- }
164
-
165
- /**
166
- * Start spinner animation
167
- * @private
168
- */
169
- startSpinner() {
170
- this.spinnerInterval = setInterval(() => {
171
- this.spinnerIndex = (this.spinnerIndex + 1) % this.spinnerFrames.length;
172
- this.renderSpinner();
173
- }, 80);
174
- }
175
-
176
- /**
177
- * Calculate ETA
178
- * @private
179
- */
180
- calculateETA() {
181
- const elapsed = Date.now() - this.startTime;
182
- const rate = this.current / elapsed;
183
- const remaining = this.total - this.current;
184
- const eta = remaining / rate;
185
-
186
- return this.formatTime(eta);
187
- }
188
-
189
- /**
190
- * Calculate processing speed
191
- * @private
192
- */
193
- calculateSpeed() {
194
- const elapsed = (Date.now() - this.startTime) / 1000; // seconds
195
- const speed = this.current / elapsed;
196
-
197
- if (speed > 1000) {
198
- return `${(speed / 1000).toFixed(1)}k`;
199
- }
200
- return speed.toFixed(1);
201
- }
202
-
203
- /**
204
- * Format time duration
205
- * @private
206
- */
207
- formatTime(ms) {
208
- const seconds = Math.floor(ms / 1000);
209
- const minutes = Math.floor(seconds / 60);
210
- const hours = Math.floor(minutes / 60);
211
-
212
- if (hours > 0) {
213
- return `${hours}h ${minutes % 60}m`;
214
- }
215
- if (minutes > 0) {
216
- return `${minutes}m ${seconds % 60}s`;
217
- }
218
- return `${seconds}s`;
219
- }
220
-
221
- /**
222
- * Create a simple progress callback
223
- */
224
- static create(total, message = 'Processing') {
225
- const progress = new ProgressIndicator({ total, message });
226
- progress.start();
227
-
228
- return {
229
- update: (current, msg) => progress.update(current, msg),
230
- increment: (msg) => progress.increment(msg),
231
- complete: (msg) => progress.complete(msg)
232
- };
233
- }
234
-
235
- /**
236
- * Wrap an async function with progress tracking
237
- */
238
- static async withProgress(items, processor, message = 'Processing items') {
239
- const progress = new ProgressIndicator({
240
- total: items.length,
241
- message,
242
- style: 'bar'
243
- });
244
-
245
- progress.start();
246
-
247
- const results = [];
248
- for (let i = 0; i < items.length; i++) {
249
- results.push(await processor(items[i], i));
250
- progress.increment();
251
- }
252
-
253
- progress.complete();
254
- return results;
255
- }
256
- }
257
-
258
- module.exports = ProgressIndicator;