@yemi33/minions 0.1.1903 → 0.1.1904

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/dashboard.js CHANGED
@@ -73,19 +73,9 @@ function ensureConfiguredProjectStateFiles() {
73
73
  const root = p.localPath ? path.resolve(p.localPath) : null;
74
74
  if (!root || !fs.existsSync(root)) continue;
75
75
  try {
76
- const state = shared.ensureProjectStateFiles(p, { migrateLegacy: true, removeLegacy: true });
77
- if (state.migrated.length > 0 || state.removedLegacy.length > 0 || state.legacyDirRemoved) {
78
- const parts = [];
79
- if (state.migrated.length > 0) parts.push(`merged ${state.migrated.join(', ')}`);
80
- if (state.removedLegacy.length > 0) parts.push(`removed ${state.removedLegacy.join(', ')}`);
81
- if (state.legacyDirRemoved) parts.push(`removed legacy .minions dir`);
82
- console.log(`[dashboard] migrated project state for "${p.name}" → projects/${p.name} (${parts.join('; ')})`);
83
- }
84
- if (state.legacyDirRemoveError) {
85
- console.warn(`[dashboard] failed to remove legacy .minions dir for "${p.name}": ${state.legacyDirRemoveError}`);
86
- }
76
+ shared.ensureProjectStateFiles(p);
87
77
  } catch (e) {
88
- console.warn(`[dashboard] project state migration failed for "${p.name}": ${e.message}`);
78
+ console.warn(`[dashboard] project state setup failed for "${p.name}": ${e.message}`);
89
79
  }
90
80
  }
91
81
  }
@@ -5716,9 +5706,8 @@ What would you like to discuss or change? When you're happy, say "approve" and I
5716
5706
  prUrlBase: detected.prUrlBase,
5717
5707
  });
5718
5708
 
5719
- // Create centralized project state and migrate any legacy project-local
5720
- // .minions state without leaving repo-local state files behind.
5721
- shared.ensureProjectStateFiles(project, { migrateLegacy: true, removeLegacy: true });
5709
+ // Create centralized project state files.
5710
+ shared.ensureProjectStateFiles(project);
5722
5711
 
5723
5712
  let duplicate = false;
5724
5713
  mutateDashboardConfig(config => {
@@ -1,10 +1 @@
1
- [
2
- {
3
- "id": "project-local-minions-state",
4
- "summary": "Project-local .minions directories are migrated to central projects/<name>/ state and removed",
5
- "deprecated": "2026-05-06",
6
- "reason": "Project repos should not receive Minions runtime state because .minions can leak into source repositories.",
7
- "locations": ["engine/shared.js ensureProjectStateFiles legacy migration", "dashboard.js handleProjectsAdd/dashboard startup", "minions.js addProject/scanAndAdd", "engine/cli.js start migration", "bin/minions.js user-scoped init root"],
8
- "cleanup": "Remove legacyProjectStateDir/legacyProjectStatePath migration/deletion after existing project-local .minions directories have been migrated."
9
- }
10
- ]
1
+ []
package/engine/cli.js CHANGED
@@ -468,20 +468,9 @@ const commands = {
468
468
  console.log(` WARNING: ${p.name} path not found: ${p.localPath}`);
469
469
  } else {
470
470
  try {
471
- const state = shared.ensureProjectStateFiles(p, { migrateLegacy: true, removeLegacy: true });
472
- if (state.migrated.length > 0 || state.removedLegacy.length > 0 || state.legacyDirRemoved) {
473
- const parts = [];
474
- if (state.migrated.length > 0) parts.push(`merged ${state.migrated.join(', ')}`);
475
- if (state.removedLegacy.length > 0) parts.push(`removed ${state.removedLegacy.join(', ')}`);
476
- if (state.legacyDirRemoved) parts.push(`removed legacy .minions dir`);
477
- e.log('info', `Migrated project state for "${p.name}" → projects/${p.name} (${parts.join('; ')})`);
478
- }
479
- if (state.legacyDirRemoveError) {
480
- e.log('warn', `Failed to remove legacy .minions dir for "${p.name}": ${state.legacyDirRemoveError}`);
481
- console.log(` WARNING: legacy .minions dir for "${p.name}" could not be removed: ${state.legacyDirRemoveError}`);
482
- }
471
+ shared.ensureProjectStateFiles(p);
483
472
  } catch (err) {
484
- e.log('warn', `Project state migration failed for "${p.name}": ${err.message}`);
473
+ e.log('warn', `Project state setup failed for "${p.name}": ${err.message}`);
485
474
  }
486
475
  console.log(` Project: ${p.name} (${root})`);
487
476
  }
package/engine/shared.js CHANGED
@@ -1967,9 +1967,6 @@ function resolveProjectSource(source, projectsOrConfig, options = {}) {
1967
1967
  projectStateDir(project),
1968
1968
  projectWorkItemsPath(project),
1969
1969
  projectPrPath(project),
1970
- legacyProjectStateDir(project),
1971
- legacyProjectStatePath(project, 'work-items.json'),
1972
- legacyProjectStatePath(project, 'pull-requests.json'),
1973
1970
  ].filter(Boolean);
1974
1971
  if (candidates.some(candidate => _sameSourcePath(value, candidate, minionsDir))) {
1975
1972
  return _projectSourceDescriptor(project, value, explicit, minionsDir);
@@ -2023,36 +2020,6 @@ function projectPrPath(project) {
2023
2020
  return path.join(projectStateDir(project), 'pull-requests.json');
2024
2021
  }
2025
2022
 
2026
- function legacyProjectStateDir(project) {
2027
- if (!project?.localPath) return null;
2028
- return path.join(path.resolve(project.localPath), '.minions');
2029
- }
2030
-
2031
- function legacyProjectStatePath(project, fileName) {
2032
- const dir = legacyProjectStateDir(project);
2033
- return dir ? path.join(dir, fileName) : null;
2034
- }
2035
-
2036
- function projectStateRecordKey(record) {
2037
- if (record && typeof record === 'object') {
2038
- const id = record.id ?? record.prId ?? record.workItemId ?? record.url ?? record.number;
2039
- if (id !== undefined && id !== null && String(id).trim()) return String(id);
2040
- }
2041
- try { return JSON.stringify(record); } catch { return String(record); }
2042
- }
2043
-
2044
- function mergeProjectStateArrays(current, legacy) {
2045
- const merged = Array.isArray(current) ? current.slice() : [];
2046
- const seen = new Set(merged.map(projectStateRecordKey));
2047
- for (const entry of Array.isArray(legacy) ? legacy : []) {
2048
- const key = projectStateRecordKey(entry);
2049
- if (seen.has(key)) continue;
2050
- merged.push(entry);
2051
- seen.add(key);
2052
- }
2053
- return merged;
2054
- }
2055
-
2056
2023
  function sameResolvedPath(a, b) {
2057
2024
  if (!a || !b) return false;
2058
2025
  try {
@@ -2064,64 +2031,20 @@ function sameResolvedPath(a, b) {
2064
2031
  }
2065
2032
  }
2066
2033
 
2067
- function removeLegacyProjectStateDir(project) {
2068
- const dir = legacyProjectStateDir(project);
2069
- if (!dir) return { removed: false, error: null };
2070
- if (sameResolvedPath(dir, MINIONS_DIR)) return { removed: false, error: null };
2071
- if (!fs.existsSync(dir)) return { removed: false, error: null };
2072
- try {
2073
- fs.rmSync(dir, { recursive: true, force: true });
2074
- return { removed: true, error: null };
2075
- } catch (err) {
2076
- return { removed: false, error: err && err.message ? err.message : String(err) };
2077
- }
2078
- }
2079
-
2080
- function ensureProjectStateFiles(project, options = {}) {
2081
- const migrateLegacy = options.migrateLegacy !== false;
2082
- const removeLegacy = options.removeLegacy === true;
2034
+ function ensureProjectStateFiles(project) {
2083
2035
  const files = [
2084
2036
  { name: 'pull-requests.json', centralPath: projectPrPath(project) },
2085
2037
  { name: 'work-items.json', centralPath: projectWorkItemsPath(project) },
2086
2038
  ];
2087
- const result = { created: [], migrated: [], removedLegacy: [], legacyDirRemoved: false, legacyDirRemoveError: null };
2039
+ const result = { created: [] };
2088
2040
 
2089
2041
  projectStateDirEnsure(project);
2090
2042
  for (const file of files) {
2091
- const legacyPath = legacyProjectStatePath(project, file.name);
2092
- const hasLegacyState = legacyPath && (fs.existsSync(legacyPath) || fs.existsSync(legacyPath + '.backup'));
2093
- const legacyData = migrateLegacy && hasLegacyState ? safeJson(legacyPath) : null;
2094
-
2095
- if (Array.isArray(legacyData)) {
2096
- let changed = false;
2097
- mutateJsonFileLocked(file.centralPath, current => {
2098
- const merged = mergeProjectStateArrays(Array.isArray(current) ? current : [], legacyData);
2099
- changed = JSON.stringify(merged) !== JSON.stringify(current);
2100
- return merged;
2101
- }, { defaultValue: [], skipWriteIfUnchanged: true });
2102
- if (changed && legacyData.length > 0) result.migrated.push(file.name);
2103
- if (removeLegacy) {
2104
- try {
2105
- fs.unlinkSync(legacyPath);
2106
- result.removedLegacy.push(file.name);
2107
- } catch (err) {
2108
- if (!err || err.code !== 'ENOENT') throw err;
2109
- }
2110
- safeUnlink(legacyPath + '.backup');
2111
- }
2112
- }
2113
-
2114
2043
  if (!fs.existsSync(file.centralPath)) {
2115
2044
  mutateJsonFileLocked(file.centralPath, data => Array.isArray(data) ? data : [], { defaultValue: [] });
2116
2045
  result.created.push(file.name);
2117
2046
  }
2118
2047
  }
2119
-
2120
- if (removeLegacy) {
2121
- const res = removeLegacyProjectStateDir(project);
2122
- result.legacyDirRemoved = res.removed;
2123
- result.legacyDirRemoveError = res.error;
2124
- }
2125
2048
  return result;
2126
2049
  }
2127
2050
 
@@ -3620,12 +3543,8 @@ module.exports = {
3620
3543
  projectStateDirEnsure,
3621
3544
  projectWorkItemsPath,
3622
3545
  projectPrPath,
3623
- legacyProjectStateDir,
3624
- legacyProjectStatePath,
3625
3546
  ensureProjectStateFiles,
3626
3547
  sameResolvedPath,
3627
- projectStateRecordKey, // exported for testing
3628
- mergeProjectStateArrays, // exported for testing
3629
3548
  realPathForComparison, // exported for testing
3630
3549
  prPathComparisonCandidates, // exported for testing
3631
3550
  resolveProjectForPrPath, // exported for testing
package/minions.js CHANGED
@@ -135,14 +135,11 @@ async function addProject(targetDir) {
135
135
  name, description, localPath: target, repoHost, repositoryId, org, project, repoName, mainBranch,
136
136
  prUrlBase: detected.prUrlBase,
137
137
  });
138
- const state = shared.ensureProjectStateFiles(projectEntry, { migrateLegacy: true, removeLegacy: true });
138
+ shared.ensureProjectStateFiles(projectEntry);
139
139
  config.projects.push(projectEntry);
140
140
  saveConfig(config);
141
141
 
142
142
  console.log(`\n Linked "${name}" (${target})`);
143
- if (state.migrated.length > 0 || state.removedLegacy.length > 0) {
144
- console.log(` Migrated project state to ${shared.projectStateDir(projectEntry)}`);
145
- }
146
143
  console.log(` Total projects: ${config.projects.length}`);
147
144
  console.log(`\n Start the minions from anywhere:`);
148
145
  console.log(` node ${MINIONS_HOME}/engine.js # Engine`);
@@ -359,7 +356,7 @@ async function scanAndAdd({ root, depth } = {}) {
359
356
  repoHost: repo.host, repositoryId: repo.repositoryId, org: repo.org, project: repo.project,
360
357
  repoName: repo.repoName, mainBranch: repo.mainBranch, prUrlBase: repo.prUrlBase,
361
358
  });
362
- shared.ensureProjectStateFiles(projectEntry, { migrateLegacy: true, removeLegacy: true });
359
+ shared.ensureProjectStateFiles(projectEntry);
363
360
  config.projects.push(projectEntry);
364
361
  console.log(` + ${name} (${repo.path})`);
365
362
  }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@yemi33/minions",
3
- "version": "0.1.1903",
3
+ "version": "0.1.1904",
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"