@yemi33/minions 0.1.164 → 0.1.166

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 (3) hide show
  1. package/CHANGELOG.md +10 -0
  2. package/engine.js +44 -0
  3. package/package.json +1 -1
package/CHANGELOG.md CHANGED
@@ -1,5 +1,15 @@
1
1
  # Changelog
2
2
 
3
+ ## 0.1.166 (2026-04-02)
4
+
5
+ ### Engine
6
+ - engine.js
7
+
8
+ ## 0.1.165 (2026-04-02)
9
+
10
+ ### Engine
11
+ - engine.js
12
+
3
13
  ## 0.1.164 (2026-04-02)
4
14
 
5
15
  ### Engine
package/engine.js CHANGED
@@ -1521,6 +1521,7 @@ function discoverFromWorkItems(config, project) {
1521
1521
  ].filter(Boolean).join('\n');
1522
1522
  vars.checkpoint_context = cpSummary;
1523
1523
  log('info', `Injecting checkpoint context for ${item.id} (resume #${cpCount})`);
1524
+ try { fs.unlinkSync(cpPath); } catch (ue) { log('warn', `checkpoint cleanup for ${item.id}: ${ue.message}`); }
1524
1525
  }
1525
1526
  } catch (e) { log('warn', `checkpoint read for ${item.id}: ${e.message}`); }
1526
1527
 
@@ -1802,6 +1803,42 @@ function discoverCentralWorkItems(config) {
1802
1803
  assignedProject: projects.length > 0 ? projects[i % projects.length] : null
1803
1804
  }));
1804
1805
 
1806
+ // Inject checkpoint context if agent left a checkpoint.json from a prior run
1807
+ let fanOutCheckpointContext = '';
1808
+ try {
1809
+ const fanFirstProject = projects[0];
1810
+ const fanBranch = item.branch || `work/${item.id}`;
1811
+ const fanWtPath = fanFirstProject?.localPath
1812
+ ? path.resolve(fanFirstProject.localPath, config.engine?.worktreeRoot || '../worktrees', fanBranch)
1813
+ : '';
1814
+ const fanCpPath = fanWtPath ? path.join(fanWtPath, 'checkpoint.json') : '';
1815
+ if (fanCpPath && fs.existsSync(fanCpPath)) {
1816
+ const fanCpData = JSON.parse(fs.readFileSync(fanCpPath, 'utf8'));
1817
+ const fanCpCount = (item._checkpointCount || 0) + 1;
1818
+ if (fanCpCount > 3) {
1819
+ log('warn', `Work item ${item.id} exceeded 3 checkpoint-resumes — marking as needs-human-review`);
1820
+ item.status = 'needs-human-review';
1821
+ item._checkpointCount = fanCpCount;
1822
+ needsWrite = true;
1823
+ continue;
1824
+ }
1825
+ item._checkpointCount = fanCpCount;
1826
+ const fanCpSummary = [
1827
+ `## Checkpoint (Resume #${fanCpCount}/3)`,
1828
+ '',
1829
+ 'A previous agent run timed out but left a checkpoint. Continue from where it left off.',
1830
+ '',
1831
+ Array.isArray(fanCpData.completed) && fanCpData.completed.length > 0 ? `### Completed\n${fanCpData.completed.map(s => '- ' + s).join('\n')}` : '',
1832
+ Array.isArray(fanCpData.remaining) && fanCpData.remaining.length > 0 ? `### Remaining\n${fanCpData.remaining.map(s => '- ' + s).join('\n')}` : '',
1833
+ Array.isArray(fanCpData.blockers) && fanCpData.blockers.length > 0 ? `### Blockers\n${fanCpData.blockers.map(s => '- ' + s).join('\n')}` : '',
1834
+ fanCpData.branch_state ? `### Branch State\n${fanCpData.branch_state}` : '',
1835
+ ].filter(Boolean).join('\n');
1836
+ fanOutCheckpointContext = fanCpSummary;
1837
+ log('info', `Injecting checkpoint context for ${item.id} (resume #${fanCpCount})`);
1838
+ try { fs.unlinkSync(fanCpPath); } catch (ue) { log('warn', `checkpoint cleanup for ${item.id}: ${ue.message}`); }
1839
+ }
1840
+ } catch (e) { log('warn', `checkpoint read for ${item.id}: ${e.message}`); }
1841
+
1805
1842
  for (const { agent, assignedProject } of assignments) {
1806
1843
  const fanKey = `${key}-${agent.id}`;
1807
1844
  if (isAlreadyDispatched(fanKey)) continue;
@@ -1833,6 +1870,10 @@ function discoverCentralWorkItems(config) {
1833
1870
  ? '## Push Branch\n\n**PR creation is skipped for this work item.** Push your branch and report the branch name.\n\n```bash\ngit push -u origin ' + fanBranch + '\n```\n\nInclude the branch name in your completion summary.'
1834
1871
  : '## Create PR (MANDATORY)\n\n**Your task is NOT complete until a pull request exists.** If PR creation fails, retry up to 3 times before reporting the error.\n\n{{pr_create_instructions}}\n- sourceRefName: `refs/heads/' + fanBranch + '`\n- targetRefName: `refs/heads/{{main_branch}}`\n- title: `{{commit_message}}`\n- labels: `["minions:{{agent_id}}"]`\n\nInclude in the PR description:\n- What was built and why\n- Files changed\n- How to build and test, browser URL if applicable\n- Test plan\n\n## Post self-review on PR\n\n{{pr_comment_instructions}}\n- pullRequestId: `<from PR creation>`\n- Re-read your own diff critically before posting\n- Sign: `Built by Minions ({{agent_name}} — {{agent_role}})`';
1835
1872
 
1873
+ // Inject checkpoint context (computed once above the loop)
1874
+ vars.checkpoint_context = fanOutCheckpointContext;
1875
+
1876
+
1836
1877
  if (workType === 'ask') {
1837
1878
  vars.question = item.title + (item.description ? '\n\n' + item.description : '');
1838
1879
  vars.task_id = item.id;
@@ -1878,6 +1919,7 @@ function discoverCentralWorkItems(config) {
1878
1919
  item.dispatched_to = idleAgents.map(a => a.id).join(', ');
1879
1920
  item.scope = 'fan-out';
1880
1921
  item.fanOutAgents = idleAgents.map(a => a.id);
1922
+ delete item._pendingReason;
1881
1923
  needsWrite = true;
1882
1924
  setCooldown(key);
1883
1925
  log('info', `Fan-out: ${item.id} dispatched to ${idleAgents.length} agents: ${idleAgents.map(a => a.name).join(', ')}`);
@@ -1946,6 +1988,7 @@ function discoverCentralWorkItems(config) {
1946
1988
  ].filter(Boolean).join('\n');
1947
1989
  vars.checkpoint_context = cpSummary;
1948
1990
  log('info', `Injecting checkpoint context for ${item.id} (resume #${cpCount})`);
1991
+ try { fs.unlinkSync(cpPath); } catch (ue) { log('warn', `checkpoint cleanup for ${item.id}: ${ue.message}`); }
1949
1992
  }
1950
1993
  } catch (e) { log('warn', `checkpoint read for ${item.id}: ${e.message}`); }
1951
1994
 
@@ -2028,6 +2071,7 @@ function discoverCentralWorkItems(config) {
2028
2071
  item.status = 'dispatched';
2029
2072
  item.dispatched_at = ts();
2030
2073
  item.dispatched_to = agentId;
2074
+ delete item._pendingReason;
2031
2075
  needsWrite = true;
2032
2076
  setCooldown(key);
2033
2077
  }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@yemi33/minions",
3
- "version": "0.1.164",
3
+ "version": "0.1.166",
4
4
  "description": "Multi-agent AI dev team that runs from ~/.minions/ — five autonomous agents share a single engine, dashboard, and knowledge base",
5
5
  "bin": {
6
6
  "minions": "bin/minions.js"