@fractary/faber-cli 1.5.42 → 1.5.43

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.
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/commands/plan/index.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAC;AAuDpC;;GAEG;AACH,wBAAgB,iBAAiB,IAAI,OAAO,CA2B3C"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/commands/plan/index.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAC;AAwDpC;;GAEG;AACH,wBAAgB,iBAAiB,IAAI,OAAO,CA4B3C"}
@@ -31,6 +31,7 @@ export function createPlanCommand() {
31
31
  .option('--json', 'Output as JSON (shorthand for --output json)')
32
32
  .option('--limit <n>', 'Maximum number of issues to plan', parseInt)
33
33
  .option('--order-by <strategy>', 'Order issues by: priority|created|updated (default: none)', 'none')
34
+ .option('--force-new', 'Force new plan generation even if a plan already exists')
34
35
  .option('--order-direction <dir>', 'Order direction: asc|desc (default: desc)', 'desc')
35
36
  .action(async (workId, options) => {
36
37
  try {
@@ -330,22 +331,6 @@ async function planSingleIssue(issue, config, repoClient, anthropicClient, optio
330
331
  const { organization, project } = getRepoInfoFromConfig(config);
331
332
  const branch = `feature/${issue.number}`;
332
333
  const worktree = `~/.claude-worktrees/${organization}-${project}-${issue.number}`;
333
- // Generate deterministic plan from resolved workflow
334
- if (outputFormat === 'text') {
335
- console.log(chalk.gray(' → Generating plan...'));
336
- process.stdout.write(''); // Force flush
337
- }
338
- const plan = await anthropicClient.generatePlan({
339
- workflow: issue.workflow,
340
- issueTitle: issue.title,
341
- issueDescription: issue.description,
342
- issueNumber: issue.number,
343
- });
344
- // Apply autonomy override if provided (takes precedence over workflow-level autonomy)
345
- if (options.autonomy) {
346
- plan.autonomy = options.autonomy;
347
- }
348
- const planId = plan.id;
349
334
  // Create branch without checking it out (so it won't conflict with worktree creation)
350
335
  if (!options.noBranch) {
351
336
  if (outputFormat === 'text') {
@@ -408,6 +393,47 @@ async function planSingleIssue(issue, config, repoClient, anthropicClient, optio
408
393
  // Non-fatal: if cleanup fails, workflow-run will handle conflict detection
409
394
  }
410
395
  }
396
+ // Check for existing plan in worktree (skip if found, unless --force-new)
397
+ if (!options.forceNew && !options.noWorktree) {
398
+ const runsDir = path.join(worktreePath, '.fractary', 'faber', 'runs');
399
+ try {
400
+ const entries = await fs.readdir(runsDir);
401
+ for (const entry of entries) {
402
+ const planFile = path.join(runsDir, entry, 'plan.json');
403
+ try {
404
+ await fs.access(planFile);
405
+ // Found existing plan
406
+ if (outputFormat === 'text') {
407
+ console.log(chalk.yellow(` ⚠️ Plan already exists: ${entry} — skipping (use --force-new to regenerate)`));
408
+ }
409
+ return {
410
+ issue,
411
+ planId: entry,
412
+ branch,
413
+ worktree: worktreePath,
414
+ };
415
+ }
416
+ catch { /* no plan.json in this entry */ }
417
+ }
418
+ }
419
+ catch { /* runs dir doesn't exist — proceed with planning */ }
420
+ }
421
+ // Generate deterministic plan from resolved workflow
422
+ if (outputFormat === 'text') {
423
+ console.log(chalk.gray(' → Generating plan...'));
424
+ process.stdout.write(''); // Force flush
425
+ }
426
+ const plan = await anthropicClient.generatePlan({
427
+ workflow: issue.workflow,
428
+ issueTitle: issue.title,
429
+ issueDescription: issue.description,
430
+ issueNumber: issue.number,
431
+ });
432
+ // Apply autonomy override if provided (takes precedence over workflow-level autonomy)
433
+ if (options.autonomy) {
434
+ plan.autonomy = options.autonomy;
435
+ }
436
+ const planId = plan.id;
411
437
  // Write plan to worktree
412
438
  if (!options.noWorktree) {
413
439
  // Validate plan ID format (prevent path traversal via malicious plan IDs)
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@fractary/faber-cli",
3
- "version": "1.5.42",
3
+ "version": "1.5.43",
4
4
  "description": "FABER CLI - Command-line interface for FABER development toolkit",
5
5
  "main": "dist/index.js",
6
6
  "bin": {