speccrew 0.7.38 → 0.7.39

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.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "speccrew",
3
- "version": "0.7.38",
3
+ "version": "0.7.39",
4
4
  "description": "Spec-Driven Development toolkit for AI-powered IDEs",
5
5
  "author": "charlesmu99",
6
6
  "repository": {
@@ -616,13 +616,38 @@ function cmdUpdateTask(args) {
616
616
  lockPath = acquireLock(filePath);
617
617
  const data = readJsonFile(filePath);
618
618
 
619
- // Find task
620
- const taskIndex = data.tasks?.findIndex(t => t.id === args.taskId);
621
- if (taskIndex === -1 || taskIndex === undefined) {
622
- outputError(`Task not found: ${args.taskId}`);
619
+ // Find task (support both flat structure and nested stages structure)
620
+ let task = null;
621
+ let taskIndex = -1;
622
+ let taskArray = null;
623
+ let isStageMode = false;
624
+ let targetStage = null;
625
+
626
+ if (args.stage) {
627
+ // Nested structure: stages.{stage}.features
628
+ isStageMode = true;
629
+ if (!data.stages || !data.stages[args.stage]) {
630
+ outputError(`Stage not found: ${args.stage}`);
631
+ }
632
+ targetStage = data.stages[args.stage];
633
+ if (!targetStage.features || !Array.isArray(targetStage.features)) {
634
+ outputError(`Stage has no features array: ${args.stage}`);
635
+ }
636
+ taskArray = targetStage.features;
637
+ taskIndex = taskArray.findIndex(t => t.id === args.taskId);
638
+ if (taskIndex === -1) {
639
+ outputError(`Task not found in stage ${args.stage}: ${args.taskId}`);
640
+ }
641
+ } else {
642
+ // Flat structure: data.tasks
643
+ taskArray = data.tasks;
644
+ taskIndex = taskArray?.findIndex(t => t.id === args.taskId);
645
+ if (taskIndex === -1 || taskIndex === undefined) {
646
+ outputError(`Task not found: ${args.taskId}`);
647
+ }
623
648
  }
624
649
 
625
- const task = data.tasks[taskIndex];
650
+ task = taskArray[taskIndex];
626
651
  const now = getTimestamp();
627
652
 
628
653
  // Update status
@@ -668,11 +693,17 @@ function cmdUpdateTask(args) {
668
693
  }
669
694
 
670
695
  // Update task
671
- data.tasks[taskIndex] = task;
696
+ taskArray[taskIndex] = task;
672
697
  data.updated_at = now;
673
698
 
674
699
  // Recalculate counts
675
- data.counts = calculateCounts(data.tasks);
700
+ if (isStageMode && targetStage.counts) {
701
+ // Update stage-level counts
702
+ targetStage.counts = calculateCounts(taskArray);
703
+ } else {
704
+ // Update global counts
705
+ data.counts = calculateCounts(data.tasks);
706
+ }
676
707
 
677
708
  // Atomic write
678
709
  atomicWriteJson(filePath, data);