From 6b590b699e8e00303dd3bfe081bb5de28867f3c9 Mon Sep 17 00:00:00 2001 From: Nikolas de Hor Date: Tue, 17 Mar 2026 23:06:11 -0300 Subject: [PATCH 1/2] fix(execution): substitui || por ?? no ResultAggregator para valores falsy-safe MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit waveIndex 0 era tratado como undefined por causa de || (OR lógico que trata 0 como falsy). Substitui todas as ocorrências de || para defaults por ?? (nullish coalescing) que só substitui null/undefined. Afeta: waveIndex, startedAt, rootPath, reportDir, maxHistory, agentId, filesModified, duration, output. --- .../core/execution/result-aggregator.js | 26 +++++++++---------- .aiox-core/install-manifest.yaml | 4 +-- 2 files changed, 15 insertions(+), 15 deletions(-) diff --git a/.aiox-core/core/execution/result-aggregator.js b/.aiox-core/core/execution/result-aggregator.js index 80956fb053..c3d240d28c 100644 --- a/.aiox-core/core/execution/result-aggregator.js +++ b/.aiox-core/core/execution/result-aggregator.js @@ -15,15 +15,15 @@ class ResultAggregator extends EventEmitter { super(); // Root path for reports - this.rootPath = config.rootPath || process.cwd(); - this.reportDir = config.reportDir || path.join(this.rootPath, 'plan'); + this.rootPath = config.rootPath ?? process.cwd(); + this.reportDir = config.reportDir ?? path.join(this.rootPath, 'plan'); // Conflict detection settings this.detectConflicts = config.detectConflicts !== false; // Aggregation history this.history = []; - this.maxHistory = config.maxHistory || 50; + this.maxHistory = config.maxHistory ?? 50; } /** @@ -36,8 +36,8 @@ class ResultAggregator extends EventEmitter { const aggregation = { id: `agg-${Date.now()}-${Math.random().toString(36).substr(2, 9)}`, - waveIndex: waveResults.waveIndex || waveResults.wave, - startedAt: waveResults.startedAt || new Date().toISOString(), + waveIndex: waveResults.waveIndex ?? waveResults.wave, + startedAt: waveResults.startedAt ?? new Date().toISOString(), completedAt: new Date().toISOString(), tasks: [], conflicts: [], @@ -46,15 +46,15 @@ class ResultAggregator extends EventEmitter { }; // Collect task results - const results = waveResults.results || []; + const results = waveResults.results ?? []; for (const result of results) { aggregation.tasks.push({ taskId: result.taskId, - agentId: result.agentId || 'unknown', + agentId: result.agentId ?? 'unknown', success: result.success, - filesModified: result.filesModified || this.extractFilesFromOutput(result.output), - duration: result.duration || 0, - output: this.summarizeOutput(result.output || result.result?.output), + filesModified: result.filesModified ?? this.extractFilesFromOutput(result.output), + duration: result.duration ?? 0, + output: this.summarizeOutput(result.output ?? result.result?.output), error: result.error, }); } @@ -138,7 +138,7 @@ class ResultAggregator extends EventEmitter { const conflicts = []; for (const task of tasks) { - const files = task.filesModified || []; + const files = task.filesModified ?? []; for (const file of files) { if (fileModifications.has(file)) { @@ -304,7 +304,7 @@ class ResultAggregator extends EventEmitter { const tasks = aggregation.tasks; const successful = tasks.filter((t) => t.success).length; const failed = tasks.filter((t) => !t.success).length; - const totalDuration = tasks.reduce((sum, t) => sum + (t.duration || 0), 0); + const totalDuration = tasks.reduce((sum, t) => sum + (t.duration ?? 0), 0); // Calculate wall time const wallTime = Date.now() - startTime; @@ -336,7 +336,7 @@ class ResultAggregator extends EventEmitter { calculateOverallMetrics(consolidated) { const allTasks = consolidated.allTasks; const successful = allTasks.filter((t) => t.success).length; - const totalDuration = allTasks.reduce((sum, t) => sum + (t.duration || 0), 0); + const totalDuration = allTasks.reduce((sum, t) => sum + (t.duration ?? 0), 0); // Calculate wave metrics const waveSuccessRates = consolidated.waves.map((w) => w.metrics.successRate); diff --git a/.aiox-core/install-manifest.yaml b/.aiox-core/install-manifest.yaml index 05816fa4fd..253b89433d 100644 --- a/.aiox-core/install-manifest.yaml +++ b/.aiox-core/install-manifest.yaml @@ -8,7 +8,7 @@ # - File types for categorization # version: 5.0.3 -generated_at: "2026-03-11T15:04:09.395Z" +generated_at: "2026-03-18T02:06:02.978Z" generator: scripts/generate-install-manifest.js file_count: 1090 files: @@ -425,7 +425,7 @@ files: type: core size: 9033 - path: core/execution/result-aggregator.js - hash: sha256:fc662bbc649bf704a8f6e70d0203fab389c664a6b4b2932510f84c251ae26610 + hash: sha256:5346bf5ac07f4e837ba3c44115ac73eede3eeea1d342fae1f30d01663e32240f type: core size: 14553 - path: core/execution/semantic-merge-engine.js From 93f77370bdb9d10e94956b5e528a81f676b56a42 Mon Sep 17 00:00:00 2001 From: Nikolas de Hor Date: Tue, 17 Mar 2026 23:09:42 -0300 Subject: [PATCH 2/2] fix(execution): substitui || por ?? em wave-executor e build-state-manager MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Mesma classe de bug do ResultAggregator: operadores || tratam 0 como falsy, causando defaults incorretos quando o valor real é 0 (ex: duration, totalSubtasks, waveIndex). Corrige 11 ocorrências em 2 módulos. --- .aiox-core/core/execution/build-state-manager.js | 12 ++++++------ .aiox-core/core/execution/wave-executor.js | 10 +++++----- .aiox-core/install-manifest.yaml | 8 ++++---- 3 files changed, 15 insertions(+), 15 deletions(-) diff --git a/.aiox-core/core/execution/build-state-manager.js b/.aiox-core/core/execution/build-state-manager.js index de50cc8fb0..eda3a998fe 100644 --- a/.aiox-core/core/execution/build-state-manager.js +++ b/.aiox-core/core/execution/build-state-manager.js @@ -158,8 +158,8 @@ class BuildStateManager { } this.storyId = storyId; - this.rootPath = options.rootPath || process.cwd(); - this.planDir = options.planDir || path.join(this.rootPath, 'plan'); + this.rootPath = options.rootPath ?? process.cwd(); + this.planDir = options.planDir ?? path.join(this.rootPath, 'plan'); this.config = { ...DEFAULT_CONFIG, ...options.config }; // State file paths @@ -213,7 +213,7 @@ class BuildStateManager { plan: options.plan || null, checkpoints: [], metrics: { - totalSubtasks: options.totalSubtasks || 0, + totalSubtasks: options.totalSubtasks ?? 0, completedSubtasks: 0, totalAttempts: 0, totalFailures: 0, @@ -355,10 +355,10 @@ class BuildStateManager { subtaskId, status: options.status || 'completed', gitCommit: options.gitCommit || null, - filesModified: options.filesModified || [], + filesModified: options.filesModified ?? [], metrics: { - duration: options.duration || 0, - attempts: options.attempts || 1, + duration: options.duration ?? 0, + attempts: options.attempts ?? 1, }, }; diff --git a/.aiox-core/core/execution/wave-executor.js b/.aiox-core/core/execution/wave-executor.js index 51fd8a8a66..82db847c74 100644 --- a/.aiox-core/core/execution/wave-executor.js +++ b/.aiox-core/core/execution/wave-executor.js @@ -64,7 +64,7 @@ class WaveExecutor extends EventEmitter { waves: [ { index: 1, - tasks: context.tasks || [], + tasks: context.tasks ?? [], }, ], }; @@ -101,7 +101,7 @@ class WaveExecutor extends EventEmitter { wave: wave.index, results: waveResult, allSucceeded: waveResult.every((r) => r.success), - duration: waveResult.reduce((sum, r) => sum + (r.duration || 0), 0), + duration: waveResult.reduce((sum, r) => sum + (r.duration ?? 0), 0), }); this.emit('wave_completed', { @@ -148,7 +148,7 @@ class WaveExecutor extends EventEmitter { * @returns {Promise} - Task results */ async executeWave(wave, context) { - const tasks = wave.tasks || []; + const tasks = wave.tasks ?? []; if (tasks.length === 0) { return []; @@ -175,7 +175,7 @@ class WaveExecutor extends EventEmitter { success: result.value.success, result: result.value, critical: task.critical || false, - duration: result.value.duration || 0, + duration: result.value.duration ?? 0, }); } else { allResults.push({ @@ -314,7 +314,7 @@ class WaveExecutor extends EventEmitter { const allTasks = waveResults.flatMap((w) => w.results); const successful = allTasks.filter((t) => t.success).length; const failed = allTasks.filter((t) => !t.success).length; - const totalDuration = allTasks.reduce((sum, t) => sum + (t.duration || 0), 0); + const totalDuration = allTasks.reduce((sum, t) => sum + (t.duration ?? 0), 0); // Calculate wall time (actual elapsed time) const wallTime = waveResults.reduce((sum, w) => { diff --git a/.aiox-core/install-manifest.yaml b/.aiox-core/install-manifest.yaml index 253b89433d..ce25e62189 100644 --- a/.aiox-core/install-manifest.yaml +++ b/.aiox-core/install-manifest.yaml @@ -8,7 +8,7 @@ # - File types for categorization # version: 5.0.3 -generated_at: "2026-03-18T02:06:02.978Z" +generated_at: "2026-03-18T02:09:42.143Z" generator: scripts/generate-install-manifest.js file_count: 1090 files: @@ -405,7 +405,7 @@ files: type: core size: 31780 - path: core/execution/build-state-manager.js - hash: sha256:415fca3ad3d750db1f41f14f33971cf661ee9d6073a570175d695bb3c1be655c + hash: sha256:7b13b18fa3ef9d624ea23ce25b30d88311f0d225125b2b7b07e76bdf57eb30c5 type: core size: 48976 - path: core/execution/context-injector.js @@ -437,7 +437,7 @@ files: type: core size: 25738 - path: core/execution/wave-executor.js - hash: sha256:4e2324edb37ae0729062b5ac029f2891e050e7efd3a48d0f4a1dc4f227a6716b + hash: sha256:950f659dd9d7176b39450c95f1903ea8868efd7324603040b770a80e2063310c type: core size: 11060 - path: core/graph-dashboard/cli.js @@ -1221,7 +1221,7 @@ files: type: data size: 9575 - path: data/entity-registry.yaml - hash: sha256:cc1bf74d3ef4e90b7a396d5b77259e540b2f9bd4a5b4b1da4977fe49ae83525d + hash: sha256:7ab5f897a51bbe4b63db9250ba3496c911462ab761a7655672a0bf50f0a821e8 type: data size: 521869 - path: data/learned-patterns.yaml