multi-agents-cli 1.0.95 → 1.0.96

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.
@@ -836,6 +836,52 @@ const main = async () => {
836
836
 
837
837
  // Soft gate - backend selected but missing prerequisites
838
838
  if (project === 'backend') {
839
+ // Architectural change warning — no backend/ folder + integrated backend config
840
+ const backendFolderExists = fs.existsSync(path.join(ROOT, 'backend'));
841
+ const isIntegrated = config.backend?.type === 'integrated';
842
+
843
+ if (!backendFolderExists) {
844
+ separator();
845
+ console.log(`\n ${yellow('⚠ No backend/ folder detected')}
846
+ `);
847
+ if (isIntegrated) {
848
+ console.log(` This project currently uses ${bold('integrated backend')} (${dim(config.frontend?.type || 'client framework')}).`);
849
+ console.log(` Adding a separate backend will change your project architecture:
850
+ `);
851
+ } else {
852
+ console.log(` A ${bold('backend/')} directory does not exist yet.`);
853
+ console.log(` Proceeding will create it and establish a separate backend:
854
+ `);
855
+ }
856
+ console.log(` ${dim('→')} A new ${bold('backend/')} directory will be created`);
857
+ console.log(` ${dim('→')} Client API calls will need redirecting to the new backend`);
858
+ console.log(` ${dim('→')} CONTRACTS.md will need updating`);
859
+ if (isIntegrated) {
860
+ console.log(` ${dim('→')} Project config will update to ${bold('separate')} backend type
861
+ `);
862
+ }
863
+ console.log('');
864
+
865
+ const archIdx = await arrowSelect('How would you like to proceed?', [
866
+ { label: `${green('→')} Proceed — I want to add a separate backend` },
867
+ { label: `${yellow('←')} Go back — keep current setup ${dim('← recommended')}` },
868
+ ], rl);
869
+
870
+ if (archIdx === 1) continue flowLoop;
871
+
872
+ // Update config to separate if was integrated
873
+ if (isIntegrated) {
874
+ try {
875
+ const cfgPath = path.join(ROOT, '.scaffold', '.config.json');
876
+ const cfg = JSON.parse(fs.readFileSync(cfgPath, 'utf8'));
877
+ cfg.backend.type = 'separate';
878
+ fs.writeFileSync(cfgPath, JSON.stringify(cfg, null, 2), 'utf8');
879
+ console.log(` ${green('✓')} Project config updated to separate backend
880
+ `);
881
+ } catch {}
882
+ }
883
+ }
884
+
839
885
  const clientCompleted = buildEntries.filter(e => e.scope === 'client' && e.status === 'COMPLETED');
840
886
  const clientLogicDone = clientCompleted.some(e => e.agent === 'LOGIC');
841
887
  const missing = [];
@@ -948,6 +994,34 @@ const main = async () => {
948
994
  agent = agentOptions[agentIdx];
949
995
  contractsNote = '';
950
996
 
997
+ // ── Check for OTHER active agents in same scope ───────────────────────────
998
+ const otherActiveInScope = Object.entries(tracking?.[project] || {})
999
+ .filter(([a, data]) => a !== agent && data?.status === 'ACTIVE');
1000
+
1001
+ if (otherActiveInScope.length > 0) {
1002
+ separator();
1003
+ console.log(`\n ${yellow('⚠ Active agent detected in ' + project + ' scope')}
1004
+ `);
1005
+ for (const [a, data] of otherActiveInScope) {
1006
+ console.log(` ${dim('→')} ${bold(a)} is currently ${yellow('ACTIVE')}`);
1007
+ console.log(` Branch : ${dim(data.branch)}`);
1008
+ console.log(` Launched: ${dim(data.launchedAt ? new Date(data.launchedAt).toLocaleString() : 'unknown')}
1009
+ `);
1010
+ }
1011
+ console.log(` ${yellow('Launching')} ${bold(agent)} ${yellow('alongside an active agent in the same scope means:')}`);
1012
+ console.log(` ${dim('→')} Both agents may write to overlapping files`);
1013
+ console.log(` ${dim('→')} Scope violations may occur at merge time`);
1014
+ console.log(` ${dim('→')} CONTRACTS.md may receive conflicting entries
1015
+ `);
1016
+
1017
+ const warningIdx = await arrowSelect('How would you like to proceed?', [
1018
+ { label: `${yellow('→')} Proceed anyway ${dim('— I understand the risks')}` },
1019
+ { label: `${green('←')} Go back — pick a different agent ${dim('← recommended')}` },
1020
+ ], rl);
1021
+
1022
+ if (warningIdx === 1) continue agentLoop;
1023
+ }
1024
+
951
1025
  // Agent already active - decisional block
952
1026
  const { active, slot: activeSlot } = guards.checkAgentActive(tracking, project, agent);
953
1027
  if (active) {
@@ -1095,6 +1169,32 @@ const main = async () => {
1095
1169
  } // end else (argAgent bypass)
1096
1170
  } // end if (project !== 'cloud')
1097
1171
 
1172
+ // ── First-run project context question (UI agent only, no completed agents) ──
1173
+ let projectContext = '';
1174
+ const isFirstRun = project === 'client' && agent === 'UI' && buildEntries.filter(e => e.status === 'COMPLETED').length === 0;
1175
+
1176
+ if (isFirstRun) {
1177
+ separator();
1178
+ console.log(`\n ${bold('Before we begin...')}
1179
+ `);
1180
+
1181
+ if (prompts && process.stdin.isTTY) {
1182
+ const ctxRes = await prompts({
1183
+ type: 'text',
1184
+ name: 'value',
1185
+ message: '* What are you building?',
1186
+ initial: 'e.g. A stock market prediction app with AI insights and portfolio tracking',
1187
+ }, { onCancel: () => process.exit(0) });
1188
+ const rawCtx = (ctxRes.value || '').trim();
1189
+ const isPlaceholderCtx = rawCtx.startsWith('e.g. ');
1190
+ projectContext = isPlaceholderCtx ? '' : rawCtx;
1191
+ } else {
1192
+ console.log(dim(' (optional — helps the agent make better decisions)'));
1193
+ const input = await ask(`\n${bold('* What are you building?')}: `);
1194
+ projectContext = input.trim();
1195
+ }
1196
+ }
1197
+
1098
1198
  // ── Task description ──────────────────────────────────────────────────────────
1099
1199
 
1100
1200
  separator();
@@ -1142,6 +1242,11 @@ const main = async () => {
1142
1242
  let skipped = [];
1143
1243
  contextSection = '';
1144
1244
 
1245
+ // Inject project context if provided on first UI run
1246
+ if (projectContext) {
1247
+ contextSection += `\n---\n\n## Project Context\n\n${projectContext}\n\nUse this as the primary directive for what you are building. All component names, page structure, and UI decisions should align with this project description.\n`;
1248
+ }
1249
+
1145
1250
  if (AGENT_QUESTIONS[agent] && userSeedingContracts) {
1146
1251
  let gathering = true;
1147
1252
  while (gathering) {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "multi-agents-cli",
3
- "version": "1.0.95",
3
+ "version": "1.0.96",
4
4
  "description": "Multi-agent workflow orchestration for Claude Code — isolated git worktrees, structured state tracking, autonomous task chaining",
5
5
  "keywords": [
6
6
  "claude-code",