aios-core 4.2.5 → 4.2.7
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/.aios-core/core/code-intel/code-intel-client.js +280 -0
- package/.aios-core/core/code-intel/code-intel-enricher.js +159 -0
- package/.aios-core/core/code-intel/index.js +137 -0
- package/.aios-core/core/code-intel/providers/code-graph-provider.js +201 -0
- package/.aios-core/core/code-intel/providers/provider-interface.js +108 -0
- package/.aios-core/core/orchestration/context-manager.js +333 -5
- package/.aios-core/core/orchestration/dashboard-integration.js +17 -1
- package/.aios-core/core/orchestration/execution-profile-resolver.js +107 -0
- package/.aios-core/core/orchestration/index.js +3 -0
- package/.aios-core/core/orchestration/skill-dispatcher.js +2 -0
- package/.aios-core/core/orchestration/subagent-prompt-builder.js +2 -0
- package/.aios-core/core/orchestration/workflow-orchestrator.js +113 -5
- package/.aios-core/data/entity-registry.yaml +44 -22
- package/.aios-core/development/agents/ux-design-expert.md +1 -1
- package/.aios-core/development/checklists/brownfield-compatibility-checklist.md +114 -0
- package/.aios-core/development/scripts/workflow-state-manager.js +128 -1
- package/.aios-core/development/tasks/next.md +36 -5
- package/.aios-core/hooks/ids-post-commit.js +29 -1
- package/.aios-core/hooks/ids-pre-push.js +29 -1
- package/.aios-core/infrastructure/contracts/compatibility/aios-4.0.4.yaml +44 -0
- package/.aios-core/infrastructure/scripts/validate-parity.js +238 -2
- package/.aios-core/install-manifest.yaml +63 -27
- package/.aios-core/product/templates/brownfield-risk-report-tmpl.yaml +277 -0
- package/.aios-core/workflow-intelligence/engine/suggestion-engine.js +114 -5
- package/LICENSE +13 -1
- package/README.md +39 -9
- package/package.json +8 -6
- package/packages/installer/src/wizard/ide-config-generator.js +0 -117
- package/packages/installer/src/wizard/index.js +2 -118
- package/packages/installer/src/wizard/pro-setup.js +58 -12
- package/pro/license/license-api.js +9 -9
- package/scripts/semantic-lint.js +190 -0
package/README.md
CHANGED
|
@@ -12,6 +12,30 @@
|
|
|
12
12
|
|
|
13
13
|
Framework de Desenvolvimento Auto-Modificável Alimentado por IA. Fundado em Desenvolvimento Ágil Dirigido por Agentes, oferecendo capacidades revolucionárias para desenvolvimento dirigido por IA e muito mais. Transforme qualquer domínio com expertise especializada de IA: desenvolvimento de software, entretenimento, escrita criativa, estratégia de negócios, bem-estar pessoal e muito mais.
|
|
14
14
|
|
|
15
|
+
## Comece Aqui (10 Min)
|
|
16
|
+
|
|
17
|
+
Se é sua primeira vez no AIOS, siga este caminho linear:
|
|
18
|
+
|
|
19
|
+
1. Instale em um projeto novo ou existente:
|
|
20
|
+
```bash
|
|
21
|
+
# novo projeto
|
|
22
|
+
npx aios-core init meu-projeto
|
|
23
|
+
|
|
24
|
+
# projeto existente
|
|
25
|
+
cd seu-projeto
|
|
26
|
+
npx aios-core install
|
|
27
|
+
```
|
|
28
|
+
2. Escolha sua IDE/CLI e o caminho de ativação:
|
|
29
|
+
- Claude Code: `/agent-name`
|
|
30
|
+
- Gemini CLI: `/aios-menu` → `/aios-<agent>`
|
|
31
|
+
- Codex CLI: `/skills` → `aios-<agent-id>`
|
|
32
|
+
- Cursor/Copilot/AntiGravity: siga os limites e workarounds em `docs/ide-integration.md`
|
|
33
|
+
3. Ative 1 agente e confirme o greeting.
|
|
34
|
+
4. Rode 1 comando inicial (`*help` ou equivalente) para validar first-value.
|
|
35
|
+
|
|
36
|
+
Definição de first-value (binária): ativação de agente + greeting válido + comando inicial com output útil em <= 10 minutos.
|
|
37
|
+
|
|
38
|
+
|
|
15
39
|
## Compatibilidade de Hooks por IDE (Realidade AIOS 4.0.4)
|
|
16
40
|
|
|
17
41
|
Muitos recursos avançados do AIOS dependem de eventos de ciclo de vida (hooks). A tabela abaixo mostra a paridade real entre IDEs/plataformas:
|
|
@@ -27,11 +51,15 @@ Muitos recursos avançados do AIOS dependem de eventos de ciclo de vida (hooks).
|
|
|
27
51
|
|
|
28
52
|
Impactos e mitigação detalhados: `docs/ide-integration.md`.
|
|
29
53
|
|
|
30
|
-
##
|
|
54
|
+
## Acknowledgments & Attribution
|
|
55
|
+
|
|
56
|
+
Synkra AIOS was originally derived from the [BMad Method](https://github.com/bmad-code-org/BMAD-METHOD), created by [Brian Madison](https://github.com/bmadcode) (BMad Code, LLC). We gratefully acknowledge the BMad Method for providing the foundation from which this project began.
|
|
31
57
|
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
58
|
+
**Important:** This project is **NOT affiliated with, endorsed by, or sanctioned by** the BMad Method or BMad Code, LLC. Contributors appearing in the git history from the original BMad Method repository do not imply active participation in or endorsement of Synkra AIOS.
|
|
59
|
+
|
|
60
|
+
Since its origin, AIOS has evolved significantly with its own architecture, terminology, and features (v4.x+), and does not depend on BMad for current operation. The BMad Method remains an excellent framework in its own right — please visit the [official BMad Method repository](https://github.com/bmad-code-org/BMAD-METHOD) to learn more.
|
|
61
|
+
|
|
62
|
+
BMad, BMad Method, and BMad Core are trademarks of BMad Code, LLC. See [TRADEMARK.md](https://github.com/bmad-code-org/BMAD-METHOD/blob/main/TRADEMARK.md) for usage guidelines.
|
|
35
63
|
|
|
36
64
|
## Visão Geral
|
|
37
65
|
|
|
@@ -104,7 +132,7 @@ Esta abordagem de duas fases elimina tanto a **inconsistência de planejamento**
|
|
|
104
132
|
- **[Criar meus próprios agentes IA](#criando-seu-próprio-squad)** → Construir agentes para seu domínio
|
|
105
133
|
- **[Navegar Squads prontos](docs/guides/squads-overview.md)** → Veja como criar e usar equipes de agentes IA
|
|
106
134
|
- **[Entender a arquitetura](docs/architecture/ARCHITECTURE-INDEX.md)** → Mergulho técnico profundo
|
|
107
|
-
- **[
|
|
135
|
+
- **[Reportar problemas](https://github.com/SynkraAI/aios-core/issues)** → Bug reports e feature requests
|
|
108
136
|
|
|
109
137
|
## Importante: Mantenha Sua Instalação AIOS Atualizada
|
|
110
138
|
|
|
@@ -601,12 +629,10 @@ npm install @aios-fullstack/pro
|
|
|
601
629
|
|
|
602
630
|
Para mais informações, execute `npx aios-core pro --help` após a instalação.
|
|
603
631
|
|
|
604
|
-
## Suporte
|
|
632
|
+
## Suporte
|
|
605
633
|
|
|
606
|
-
-
|
|
607
|
-
- 💬 [Discussões GitHub](https://github.com/SynkraAI/aios-core/discussions) - Hub central da comunidade
|
|
634
|
+
- 🐛 [Rastreador de Issues](https://github.com/SynkraAI/aios-core/issues) - Bug reports e feature requests
|
|
608
635
|
- 💡 [Processo de Features](docs/FEATURE_PROCESS.md) - Como propor novas funcionalidades
|
|
609
|
-
- 🐛 [Rastreador de Issues](https://github.com/SynkraAI/aios-core/issues)
|
|
610
636
|
- 📋 [Como Contribuir](CONTRIBUTING.md)
|
|
611
637
|
- 🗺️ [Roadmap](docs/roadmap.md) - Veja o que estamos construindo
|
|
612
638
|
- 🤖 [Guia de Squads](docs/guides/squads-guide.md) - Crie equipes de agentes IA
|
|
@@ -704,6 +730,10 @@ Veja também:
|
|
|
704
730
|
|
|
705
731
|
## Reconhecimentos
|
|
706
732
|
|
|
733
|
+
This project was originally derived from the [BMad Method](https://github.com/bmad-code-org/BMAD-METHOD) by [Brian Madison](https://github.com/bmadcode). We thank Brian and all BMad Method contributors for the original work that made this project possible.
|
|
734
|
+
|
|
735
|
+
**Note:** Some contributors shown in the GitHub contributors graph are inherited from the original BMad Method git history and do not represent active participation in or endorsement of Synkra AIOS.
|
|
736
|
+
|
|
707
737
|
[](https://github.com/SynkraAI/aios-core/graphs/contributors)
|
|
708
738
|
|
|
709
739
|
<sub>Construído com ❤️ para a comunidade de desenvolvimento assistido por IA</sub>
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "aios-core",
|
|
3
|
-
"version": "4.2.
|
|
3
|
+
"version": "4.2.7",
|
|
4
4
|
"description": "Synkra AIOS: AI-Orchestrated System for Full Stack Development - Core Framework",
|
|
5
5
|
"bin": {
|
|
6
6
|
"aios": "bin/aios.js",
|
|
@@ -56,10 +56,11 @@
|
|
|
56
56
|
"sync:skills:codex": "node .aios-core/infrastructure/scripts/codex-skills-sync/index.js",
|
|
57
57
|
"sync:skills:codex:global": "node .aios-core/infrastructure/scripts/codex-skills-sync/index.js --global --global-only",
|
|
58
58
|
"validate:codex-skills": "node .aios-core/infrastructure/scripts/codex-skills-sync/validate.js --strict",
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
59
|
+
"validate:paths": "node .aios-core/infrastructure/scripts/validate-paths.js",
|
|
60
|
+
"validate:parity": "node .aios-core/infrastructure/scripts/validate-parity.js",
|
|
61
|
+
"validate:semantic-lint": "node scripts/semantic-lint.js",
|
|
62
|
+
"manifest:ensure": "node scripts/ensure-manifest.js",
|
|
63
|
+
"sync:ide:cursor": "node .aios-core/infrastructure/scripts/ide-sync/index.js sync --ide cursor",
|
|
63
64
|
"prepublishOnly": "npm run generate:manifest && npm run validate:manifest",
|
|
64
65
|
"prepare": "husky"
|
|
65
66
|
},
|
|
@@ -139,7 +140,8 @@
|
|
|
139
140
|
"prettier --write"
|
|
140
141
|
],
|
|
141
142
|
"*.md": [
|
|
142
|
-
"prettier --write"
|
|
143
|
+
"prettier --write",
|
|
144
|
+
"node scripts/semantic-lint.js --staged"
|
|
143
145
|
],
|
|
144
146
|
".aios-core/development/agents/*.md": [
|
|
145
147
|
"npm run sync:ide"
|
|
@@ -539,12 +539,6 @@ async function generateIDEConfigs(selectedIDEs, wizardState, options = {}) {
|
|
|
539
539
|
} else {
|
|
540
540
|
spinner.info('Skipped settings.local.json (no hooks to register)');
|
|
541
541
|
}
|
|
542
|
-
|
|
543
|
-
// Silent statusline setup (graceful skip if user already has one)
|
|
544
|
-
const statuslineResult = await setupGlobalStatusline();
|
|
545
|
-
if (statuslineResult.installed) {
|
|
546
|
-
createdFiles.push(...statuslineResult.files);
|
|
547
|
-
}
|
|
548
542
|
}
|
|
549
543
|
|
|
550
544
|
// Gemini parity with Claude Code: copy hooks and configure settings
|
|
@@ -764,7 +758,6 @@ async function createClaudeSettingsLocal(projectRoot) {
|
|
|
764
758
|
}
|
|
765
759
|
|
|
766
760
|
/**
|
|
767
|
-
<<<<<<< HEAD
|
|
768
761
|
* Copy .aios-core/hooks/gemini folder into .gemini/hooks during installation
|
|
769
762
|
* @param {string} projectRoot - Project root directory
|
|
770
763
|
* @returns {Promise<string[]>} List of copied files
|
|
@@ -982,115 +975,6 @@ async function linkGeminiExtension(projectRoot) {
|
|
|
982
975
|
return { status: 'skipped', reason: 'link-failed' };
|
|
983
976
|
}
|
|
984
977
|
|
|
985
|
-
/**
|
|
986
|
-
* Setup global statusline for Claude Code
|
|
987
|
-
*
|
|
988
|
-
* Copies statusline-script.js and track-agent.sh to ~/.claude/
|
|
989
|
-
* and configures ~/.claude/settings.json with statusLine + hook entries.
|
|
990
|
-
*
|
|
991
|
-
* GRACEFUL SKIP: If user already has a statusLine configured, this function
|
|
992
|
-
* returns silently without any output — the user never knows it was checked.
|
|
993
|
-
*
|
|
994
|
-
* @returns {Promise<{installed: boolean, files: string[]}>}
|
|
995
|
-
*/
|
|
996
|
-
async function setupGlobalStatusline() {
|
|
997
|
-
const homeDir = require('os').homedir();
|
|
998
|
-
const globalSettingsPath = path.join(homeDir, '.claude', 'settings.json');
|
|
999
|
-
const result = { installed: false, files: [] };
|
|
1000
|
-
|
|
1001
|
-
// Read existing global settings
|
|
1002
|
-
let settings = {};
|
|
1003
|
-
try {
|
|
1004
|
-
if (await fs.pathExists(globalSettingsPath)) {
|
|
1005
|
-
const content = await fs.readFile(globalSettingsPath, 'utf8');
|
|
1006
|
-
settings = JSON.parse(content);
|
|
1007
|
-
}
|
|
1008
|
-
} catch {
|
|
1009
|
-
// Corrupted or unreadable — treat as empty
|
|
1010
|
-
settings = {};
|
|
1011
|
-
}
|
|
1012
|
-
|
|
1013
|
-
// GRACEFUL SKIP: User already has a statusLine configured
|
|
1014
|
-
if (settings.statusLine) {
|
|
1015
|
-
return result;
|
|
1016
|
-
}
|
|
1017
|
-
|
|
1018
|
-
// Source templates
|
|
1019
|
-
const templatesDir = path.join(__dirname, '..', '..', '..', '..', '.aios-core', 'product', 'templates', 'statusline');
|
|
1020
|
-
|
|
1021
|
-
const scriptSource = path.join(templatesDir, 'statusline-script.js');
|
|
1022
|
-
const hookSource = path.join(templatesDir, 'track-agent.sh');
|
|
1023
|
-
|
|
1024
|
-
// Verify templates exist
|
|
1025
|
-
if (!await fs.pathExists(scriptSource) || !await fs.pathExists(hookSource)) {
|
|
1026
|
-
return result;
|
|
1027
|
-
}
|
|
1028
|
-
|
|
1029
|
-
// Target paths
|
|
1030
|
-
const scriptTarget = path.join(homeDir, '.claude', 'statusline-script.js');
|
|
1031
|
-
const hookTarget = path.join(homeDir, '.claude', 'hooks', 'track-agent.sh');
|
|
1032
|
-
const cacheDir = path.join(homeDir, '.claude', 'session-cache');
|
|
1033
|
-
|
|
1034
|
-
// Copy files
|
|
1035
|
-
try {
|
|
1036
|
-
await fs.ensureDir(path.join(homeDir, '.claude', 'hooks'));
|
|
1037
|
-
await fs.ensureDir(cacheDir);
|
|
1038
|
-
await fs.copy(scriptSource, scriptTarget);
|
|
1039
|
-
await fs.copy(hookSource, hookTarget);
|
|
1040
|
-
result.files.push(scriptTarget, hookTarget);
|
|
1041
|
-
} catch {
|
|
1042
|
-
return result;
|
|
1043
|
-
}
|
|
1044
|
-
|
|
1045
|
-
// Build the statusLine command with platform-appropriate path
|
|
1046
|
-
const scriptPathEscaped = scriptTarget.replace(/\\/g, '\\\\');
|
|
1047
|
-
|
|
1048
|
-
// Add statusLine to settings
|
|
1049
|
-
settings.statusLine = {
|
|
1050
|
-
type: 'command',
|
|
1051
|
-
command: `node "${scriptPathEscaped}"`,
|
|
1052
|
-
};
|
|
1053
|
-
|
|
1054
|
-
// Add track-agent hook to UserPromptSubmit (if not already present)
|
|
1055
|
-
if (!settings.hooks) {
|
|
1056
|
-
settings.hooks = {};
|
|
1057
|
-
}
|
|
1058
|
-
if (!Array.isArray(settings.hooks.UserPromptSubmit)) {
|
|
1059
|
-
settings.hooks.UserPromptSubmit = [];
|
|
1060
|
-
}
|
|
1061
|
-
|
|
1062
|
-
const hookPathEscaped = hookTarget.replace(/\\/g, '\\\\');
|
|
1063
|
-
const alreadyHasTrackAgent = settings.hooks.UserPromptSubmit.some(entry => {
|
|
1064
|
-
if (Array.isArray(entry.hooks)) {
|
|
1065
|
-
return entry.hooks.some(h => h.command && h.command.includes('track-agent'));
|
|
1066
|
-
}
|
|
1067
|
-
return entry.command && entry.command.includes('track-agent');
|
|
1068
|
-
});
|
|
1069
|
-
|
|
1070
|
-
if (!alreadyHasTrackAgent) {
|
|
1071
|
-
settings.hooks.UserPromptSubmit.push({
|
|
1072
|
-
matcher: '',
|
|
1073
|
-
hooks: [
|
|
1074
|
-
{
|
|
1075
|
-
type: 'command',
|
|
1076
|
-
command: `bash "${hookPathEscaped}"`,
|
|
1077
|
-
},
|
|
1078
|
-
],
|
|
1079
|
-
});
|
|
1080
|
-
}
|
|
1081
|
-
|
|
1082
|
-
// Write settings back
|
|
1083
|
-
try {
|
|
1084
|
-
await fs.ensureDir(path.dirname(globalSettingsPath));
|
|
1085
|
-
await fs.writeFile(globalSettingsPath, JSON.stringify(settings, null, 2), 'utf8');
|
|
1086
|
-
result.installed = true;
|
|
1087
|
-
} catch {
|
|
1088
|
-
return result;
|
|
1089
|
-
}
|
|
1090
|
-
|
|
1091
|
-
return result;
|
|
1092
|
-
}
|
|
1093
|
-
|
|
1094
978
|
module.exports = {
|
|
1095
979
|
generateIDEConfigs,
|
|
1096
980
|
showSuccessSummary,
|
|
@@ -1104,5 +988,4 @@ module.exports = {
|
|
|
1104
988
|
copyGeminiHooksFolder,
|
|
1105
989
|
createGeminiSettings,
|
|
1106
990
|
linkGeminiExtension,
|
|
1107
|
-
setupGlobalStatusline,
|
|
1108
991
|
};
|
|
@@ -461,67 +461,7 @@ async function runWizard(options = {}) {
|
|
|
461
461
|
answers.techPresetResult = { preset: 'none', success: true };
|
|
462
462
|
}
|
|
463
463
|
|
|
464
|
-
//
|
|
465
|
-
// Install Squads if selected
|
|
466
|
-
// if (answers.selectedExpansionPacks && answers.selectedExpansionPacks.length > 0) {
|
|
467
|
-
// console.log('\n🎁 Installing Squads...');
|
|
468
|
-
//
|
|
469
|
-
// // Detect source squads directory (npm package location)
|
|
470
|
-
// const possibleSourceDirs = [
|
|
471
|
-
// path.join(__dirname, '..', '..', 'squads'),
|
|
472
|
-
// path.join(__dirname, '..', '..', '..', 'squads'),
|
|
473
|
-
// path.join(process.cwd(), 'node_modules', '@synkra/aios-core', 'squads'),
|
|
474
|
-
// ];
|
|
475
|
-
//
|
|
476
|
-
// let sourceExpansionDir = null;
|
|
477
|
-
// for (const dir of possibleSourceDirs) {
|
|
478
|
-
// if (fse.existsSync(dir)) {
|
|
479
|
-
// sourceExpansionDir = dir;
|
|
480
|
-
// break;
|
|
481
|
-
// }
|
|
482
|
-
// }
|
|
483
|
-
//
|
|
484
|
-
// if (sourceExpansionDir) {
|
|
485
|
-
// const targetExpansionDir = path.join(process.cwd(), 'squads');
|
|
486
|
-
// await fse.ensureDir(targetExpansionDir);
|
|
487
|
-
//
|
|
488
|
-
// const installedPacks = [];
|
|
489
|
-
// const failedPacks = [];
|
|
490
|
-
//
|
|
491
|
-
// for (const pack of answers.selectedExpansionPacks) {
|
|
492
|
-
// const sourcePack = path.join(sourceExpansionDir, pack);
|
|
493
|
-
// const targetPack = path.join(targetExpansionDir, pack);
|
|
494
|
-
//
|
|
495
|
-
// try {
|
|
496
|
-
// if (fse.existsSync(sourcePack)) {
|
|
497
|
-
// await fse.copy(sourcePack, targetPack);
|
|
498
|
-
// installedPacks.push(pack);
|
|
499
|
-
// console.log(` ✅ ${pack}`);
|
|
500
|
-
// } else {
|
|
501
|
-
// failedPacks.push({ pack, reason: 'not found' });
|
|
502
|
-
// console.log(` ⚠️ ${pack} - not found in source`);
|
|
503
|
-
// }
|
|
504
|
-
// } catch (packError) {
|
|
505
|
-
// failedPacks.push({ pack, reason: packError.message });
|
|
506
|
-
// console.log(` ⚠️ ${pack} - ${packError.message}`);
|
|
507
|
-
// }
|
|
508
|
-
// }
|
|
509
|
-
//
|
|
510
|
-
// answers.expansionPacksInstalled = installedPacks.length > 0;
|
|
511
|
-
// answers.expansionPacksResult = {
|
|
512
|
-
// installed: installedPacks,
|
|
513
|
-
// failed: failedPacks,
|
|
514
|
-
// targetDir: targetExpansionDir,
|
|
515
|
-
// };
|
|
516
|
-
//
|
|
517
|
-
// if (installedPacks.length > 0) {
|
|
518
|
-
// console.log(`\n✅ Squads installed (${installedPacks.length}/${answers.selectedExpansionPacks.length})`);
|
|
519
|
-
// }
|
|
520
|
-
// } else {
|
|
521
|
-
// console.log(' ⚠️ Squads source directory not found');
|
|
522
|
-
// answers.expansionPacksInstalled = false;
|
|
523
|
-
// }
|
|
524
|
-
// }
|
|
464
|
+
// Legacy squad installation path removed; unified squads flow is now the only supported path.
|
|
525
465
|
|
|
526
466
|
// Story 1.4: Generate IDE configs if IDEs were selected
|
|
527
467
|
let ideConfigResult = null;
|
|
@@ -545,63 +485,7 @@ async function runWizard(options = {}) {
|
|
|
545
485
|
}
|
|
546
486
|
}
|
|
547
487
|
|
|
548
|
-
//
|
|
549
|
-
// Install squad agents to each selected IDE
|
|
550
|
-
// if (answers.expansionPacksResult && answers.expansionPacksResult.installed.length > 0) {
|
|
551
|
-
// console.log('\n📦 Installing squad agents to IDEs...');
|
|
552
|
-
//
|
|
553
|
-
// for (const packName of answers.expansionPacksResult.installed) {
|
|
554
|
-
// const packAgentsDir = path.join(answers.expansionPacksResult.targetDir, packName, 'agents');
|
|
555
|
-
//
|
|
556
|
-
// if (await fse.pathExists(packAgentsDir)) {
|
|
557
|
-
// const agentFiles = (await fse.readdir(packAgentsDir)).filter(f => f.endsWith('.md'));
|
|
558
|
-
//
|
|
559
|
-
// if (agentFiles.length > 0) {
|
|
560
|
-
// for (const ideKey of answers.selectedIDEs) {
|
|
561
|
-
// const ideConfig = getIDEConfig(ideKey);
|
|
562
|
-
// if (!ideConfig || !ideConfig.agentFolder) continue;
|
|
563
|
-
//
|
|
564
|
-
// const isAntiGravity = ideConfig.specialConfig && ideConfig.specialConfig.type === 'antigravity';
|
|
565
|
-
//
|
|
566
|
-
// // Determine target folder for this squad
|
|
567
|
-
// let targetFolder;
|
|
568
|
-
// if (isAntiGravity) {
|
|
569
|
-
// // AntiGravity: workflows go to .agent/workflows/{packName}/
|
|
570
|
-
// targetFolder = path.join(process.cwd(), ideConfig.agentFolder, packName);
|
|
571
|
-
// // Also need to copy actual agents to .antigravity/agents/{packName}/
|
|
572
|
-
// const agentsTargetFolder = path.join(process.cwd(), ideConfig.specialConfig.agentsFolder, packName);
|
|
573
|
-
// await fse.ensureDir(agentsTargetFolder);
|
|
574
|
-
//
|
|
575
|
-
// for (const agentFile of agentFiles) {
|
|
576
|
-
// const sourcePath = path.join(packAgentsDir, agentFile);
|
|
577
|
-
// const agentName = agentFile.replace('.md', '');
|
|
578
|
-
//
|
|
579
|
-
// // Create workflow file
|
|
580
|
-
// const workflowContent = generateExpansionPackWorkflow(agentName, packName);
|
|
581
|
-
// await fse.ensureDir(targetFolder);
|
|
582
|
-
// await fse.writeFile(path.join(targetFolder, agentFile), workflowContent, 'utf8');
|
|
583
|
-
//
|
|
584
|
-
// // Copy actual agent
|
|
585
|
-
// await fse.copy(sourcePath, path.join(agentsTargetFolder, agentFile));
|
|
586
|
-
// }
|
|
587
|
-
// } else {
|
|
588
|
-
// // Other IDEs: copy directly to agentFolder/{packName}/
|
|
589
|
-
// targetFolder = path.join(process.cwd(), ideConfig.agentFolder, packName);
|
|
590
|
-
// await fse.ensureDir(targetFolder);
|
|
591
|
-
//
|
|
592
|
-
// for (const agentFile of agentFiles) {
|
|
593
|
-
// await fse.copy(
|
|
594
|
-
// path.join(packAgentsDir, agentFile),
|
|
595
|
-
// path.join(targetFolder, agentFile),
|
|
596
|
-
// );
|
|
597
|
-
// }
|
|
598
|
-
// }
|
|
599
|
-
// }
|
|
600
|
-
// console.log(` ✅ ${packName}: ${agentFiles.length} agents installed to ${answers.selectedIDEs.length} IDE(s)`);
|
|
601
|
-
// }
|
|
602
|
-
// }
|
|
603
|
-
// }
|
|
604
|
-
// }
|
|
488
|
+
// Legacy per-squad IDE copy path removed; sync pipeline handles IDE propagation.
|
|
605
489
|
}
|
|
606
490
|
|
|
607
491
|
// Story 1.6: Environment Configuration
|
|
@@ -16,7 +16,7 @@
|
|
|
16
16
|
'use strict';
|
|
17
17
|
|
|
18
18
|
const { createSpinner, showSuccess, showError, showWarning, showInfo } = require('./feedback');
|
|
19
|
-
const { colors,
|
|
19
|
+
const { colors, status } = require('../utils/aios-colors');
|
|
20
20
|
|
|
21
21
|
/**
|
|
22
22
|
* Gold color for Pro branding.
|
|
@@ -386,7 +386,7 @@ async function loginWithRetry(client, email) {
|
|
|
386
386
|
|
|
387
387
|
// Wait for email verification if needed
|
|
388
388
|
if (!loginResult.emailVerified) {
|
|
389
|
-
const verifyResult = await waitForEmailVerification(client, loginResult.sessionToken);
|
|
389
|
+
const verifyResult = await waitForEmailVerification(client, loginResult.sessionToken, email);
|
|
390
390
|
if (!verifyResult.success) {
|
|
391
391
|
return verifyResult;
|
|
392
392
|
}
|
|
@@ -495,7 +495,7 @@ async function createAccountFlow(client, email) {
|
|
|
495
495
|
}
|
|
496
496
|
|
|
497
497
|
if (sessionToken) {
|
|
498
|
-
const verifyResult = await waitForEmailVerification(client, sessionToken);
|
|
498
|
+
const verifyResult = await waitForEmailVerification(client, sessionToken, email);
|
|
499
499
|
if (!verifyResult.success) {
|
|
500
500
|
return verifyResult;
|
|
501
501
|
}
|
|
@@ -516,7 +516,7 @@ async function createAccountFlow(client, email) {
|
|
|
516
516
|
break;
|
|
517
517
|
}
|
|
518
518
|
// Got session but not verified yet — use the verification polling
|
|
519
|
-
const verifyResult = await waitForEmailVerification(client, sessionToken);
|
|
519
|
+
const verifyResult = await waitForEmailVerification(client, sessionToken, email);
|
|
520
520
|
if (!verifyResult.success) {
|
|
521
521
|
return verifyResult;
|
|
522
522
|
}
|
|
@@ -625,7 +625,7 @@ async function authenticateWithEmail(email, password) {
|
|
|
625
625
|
|
|
626
626
|
// Wait for email verification if needed
|
|
627
627
|
if (!emailVerified) {
|
|
628
|
-
const verifyResult = await waitForEmailVerification(client, sessionToken);
|
|
628
|
+
const verifyResult = await waitForEmailVerification(client, sessionToken, email);
|
|
629
629
|
if (!verifyResult.success) {
|
|
630
630
|
return verifyResult;
|
|
631
631
|
}
|
|
@@ -642,10 +642,11 @@ async function authenticateWithEmail(email, password) {
|
|
|
642
642
|
* User can press R to resend verification email.
|
|
643
643
|
*
|
|
644
644
|
* @param {object} client - LicenseApiClient instance
|
|
645
|
-
* @param {string} sessionToken - Session token
|
|
645
|
+
* @param {string} sessionToken - Session token (accessToken)
|
|
646
|
+
* @param {string} email - User email for resend functionality
|
|
646
647
|
* @returns {Promise<Object>} Result with { success }
|
|
647
648
|
*/
|
|
648
|
-
async function waitForEmailVerification(client, sessionToken) {
|
|
649
|
+
async function waitForEmailVerification(client, sessionToken, email) {
|
|
649
650
|
console.log('');
|
|
650
651
|
showInfo('Waiting for email verification...');
|
|
651
652
|
showInfo('Open your email and click the verification link.');
|
|
@@ -692,7 +693,7 @@ async function waitForEmailVerification(client, sessionToken) {
|
|
|
692
693
|
if (resendHint) {
|
|
693
694
|
resendHint = false;
|
|
694
695
|
try {
|
|
695
|
-
await client.resendVerification(
|
|
696
|
+
await client.resendVerification(email);
|
|
696
697
|
showInfo('Verification email resent.');
|
|
697
698
|
} catch (error) {
|
|
698
699
|
showWarning(`Could not resend: ${error.message}`);
|
|
@@ -946,6 +947,55 @@ async function validateKeyWithApi(key) {
|
|
|
946
947
|
async function stepInstallScaffold(targetDir, options = {}) {
|
|
947
948
|
showStep(2, 3, 'Pro Content Installation');
|
|
948
949
|
|
|
950
|
+
const path = require('path');
|
|
951
|
+
const fs = require('fs');
|
|
952
|
+
const { execSync } = require('child_process');
|
|
953
|
+
|
|
954
|
+
const proSourceDir = path.join(targetDir, 'node_modules', '@aios-fullstack', 'pro');
|
|
955
|
+
|
|
956
|
+
// Step 2a: Ensure package.json exists (greenfield projects)
|
|
957
|
+
const packageJsonPath = path.join(targetDir, 'package.json');
|
|
958
|
+
if (!fs.existsSync(packageJsonPath)) {
|
|
959
|
+
const initSpinner = createSpinner('Initializing package.json...');
|
|
960
|
+
initSpinner.start();
|
|
961
|
+
try {
|
|
962
|
+
execSync('npm init -y', { cwd: targetDir, stdio: 'pipe' });
|
|
963
|
+
initSpinner.succeed('package.json created');
|
|
964
|
+
} catch (err) {
|
|
965
|
+
initSpinner.fail('Failed to create package.json');
|
|
966
|
+
return { success: false, error: `npm init failed: ${err.message}` };
|
|
967
|
+
}
|
|
968
|
+
}
|
|
969
|
+
|
|
970
|
+
// Step 2b: Install @aios-fullstack/pro if not present
|
|
971
|
+
if (!fs.existsSync(proSourceDir)) {
|
|
972
|
+
const installSpinner = createSpinner('Installing @aios-fullstack/pro...');
|
|
973
|
+
installSpinner.start();
|
|
974
|
+
try {
|
|
975
|
+
execSync('npm install @aios-fullstack/pro', {
|
|
976
|
+
cwd: targetDir,
|
|
977
|
+
stdio: 'pipe',
|
|
978
|
+
timeout: 120000,
|
|
979
|
+
});
|
|
980
|
+
installSpinner.succeed('Pro package installed');
|
|
981
|
+
} catch (err) {
|
|
982
|
+
installSpinner.fail('Failed to install Pro package');
|
|
983
|
+
return {
|
|
984
|
+
success: false,
|
|
985
|
+
error: `npm install @aios-fullstack/pro failed: ${err.message}. Try manually: npm install @aios-fullstack/pro`,
|
|
986
|
+
};
|
|
987
|
+
}
|
|
988
|
+
|
|
989
|
+
// Validate installation
|
|
990
|
+
if (!fs.existsSync(proSourceDir)) {
|
|
991
|
+
return {
|
|
992
|
+
success: false,
|
|
993
|
+
error: 'Pro package not found after npm install. Check npm output.',
|
|
994
|
+
};
|
|
995
|
+
}
|
|
996
|
+
}
|
|
997
|
+
|
|
998
|
+
// Step 2c: Scaffold pro content
|
|
949
999
|
const scaffolderModule = loadProScaffolder();
|
|
950
1000
|
|
|
951
1001
|
if (!scaffolderModule) {
|
|
@@ -954,10 +1004,6 @@ async function stepInstallScaffold(targetDir, options = {}) {
|
|
|
954
1004
|
}
|
|
955
1005
|
|
|
956
1006
|
const { scaffoldProContent } = scaffolderModule;
|
|
957
|
-
const path = require('path');
|
|
958
|
-
|
|
959
|
-
// Determine pro source directory
|
|
960
|
-
const proSourceDir = path.join(targetDir, 'node_modules', '@aios-fullstack', 'pro');
|
|
961
1007
|
|
|
962
1008
|
const spinner = createSpinner('Scaffolding pro content...');
|
|
963
1009
|
spinner.start();
|
|
@@ -426,7 +426,7 @@ class LicenseApiClient {
|
|
|
426
426
|
});
|
|
427
427
|
|
|
428
428
|
return {
|
|
429
|
-
sessionToken: response.
|
|
429
|
+
sessionToken: response.accessToken,
|
|
430
430
|
userId: response.userId,
|
|
431
431
|
emailVerified: response.emailVerified !== false,
|
|
432
432
|
};
|
|
@@ -455,11 +455,11 @@ class LicenseApiClient {
|
|
|
455
455
|
async checkEmailVerified(sessionToken) {
|
|
456
456
|
try {
|
|
457
457
|
const response = await this._request('POST', '/api/v1/auth/verify-status', {
|
|
458
|
-
sessionToken,
|
|
458
|
+
accessToken: sessionToken,
|
|
459
459
|
});
|
|
460
460
|
|
|
461
461
|
return {
|
|
462
|
-
verified: response.
|
|
462
|
+
verified: response.emailVerified === true,
|
|
463
463
|
email: response.email,
|
|
464
464
|
};
|
|
465
465
|
} catch (error) {
|
|
@@ -487,7 +487,7 @@ class LicenseApiClient {
|
|
|
487
487
|
async activateByAuth(sessionToken, machineId, aiosCoreVersion) {
|
|
488
488
|
try {
|
|
489
489
|
const response = await this._request('POST', '/api/v1/auth/activate-pro', {
|
|
490
|
-
sessionToken,
|
|
490
|
+
accessToken: sessionToken,
|
|
491
491
|
machineId,
|
|
492
492
|
aiosCoreVersion,
|
|
493
493
|
});
|
|
@@ -500,9 +500,9 @@ class LicenseApiClient {
|
|
|
500
500
|
}
|
|
501
501
|
|
|
502
502
|
return {
|
|
503
|
-
key: response.key,
|
|
503
|
+
key: response.licenseKey || response.key,
|
|
504
504
|
features: response.features,
|
|
505
|
-
seats: response.seats || { used: 1, max:
|
|
505
|
+
seats: response.seats || { used: 1, max: 3 },
|
|
506
506
|
expiresAt: response.expiresAt,
|
|
507
507
|
cacheValidDays: response.cacheValidDays || 30,
|
|
508
508
|
gracePeriodDays: response.gracePeriodDays || 7,
|
|
@@ -541,14 +541,14 @@ class LicenseApiClient {
|
|
|
541
541
|
/**
|
|
542
542
|
* Resend email verification.
|
|
543
543
|
*
|
|
544
|
-
* @param {string}
|
|
544
|
+
* @param {string} email - User email address
|
|
545
545
|
* @returns {Promise<object>} Result with { message }
|
|
546
546
|
* @throws {AuthError} On failure
|
|
547
547
|
*/
|
|
548
|
-
async resendVerification(
|
|
548
|
+
async resendVerification(email) {
|
|
549
549
|
try {
|
|
550
550
|
const response = await this._request('POST', '/api/v1/auth/resend-verification', {
|
|
551
|
-
|
|
551
|
+
email,
|
|
552
552
|
});
|
|
553
553
|
|
|
554
554
|
return {
|