ai-factory 2.1.0 → 2.2.1

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 (89) hide show
  1. package/README.md +3 -3
  2. package/dist/cli/commands/extension.d.ts +4 -0
  3. package/dist/cli/commands/extension.d.ts.map +1 -0
  4. package/dist/cli/commands/extension.js +288 -0
  5. package/dist/cli/commands/extension.js.map +1 -0
  6. package/dist/cli/commands/init.d.ts.map +1 -1
  7. package/dist/cli/commands/init.js +30 -40
  8. package/dist/cli/commands/init.js.map +1 -1
  9. package/dist/cli/commands/update.d.ts.map +1 -1
  10. package/dist/cli/commands/update.js +86 -7
  11. package/dist/cli/commands/update.js.map +1 -1
  12. package/dist/cli/commands/upgrade.d.ts.map +1 -1
  13. package/dist/cli/commands/upgrade.js +44 -41
  14. package/dist/cli/commands/upgrade.js.map +1 -1
  15. package/dist/cli/index.js +48 -1
  16. package/dist/cli/index.js.map +1 -1
  17. package/dist/cli/wizard/prompts.d.ts +2 -1
  18. package/dist/cli/wizard/prompts.d.ts.map +1 -1
  19. package/dist/cli/wizard/prompts.js +10 -17
  20. package/dist/cli/wizard/prompts.js.map +1 -1
  21. package/dist/core/config.d.ts +8 -2
  22. package/dist/core/config.d.ts.map +1 -1
  23. package/dist/core/config.js +5 -8
  24. package/dist/core/config.js.map +1 -1
  25. package/dist/core/extension-ops.d.ts +32 -0
  26. package/dist/core/extension-ops.d.ts.map +1 -0
  27. package/dist/core/extension-ops.js +83 -0
  28. package/dist/core/extension-ops.js.map +1 -0
  29. package/dist/core/extensions.d.ts +53 -0
  30. package/dist/core/extensions.d.ts.map +1 -0
  31. package/dist/core/extensions.js +141 -0
  32. package/dist/core/extensions.js.map +1 -0
  33. package/dist/core/injections.d.ts +10 -0
  34. package/dist/core/injections.d.ts.map +1 -0
  35. package/dist/core/injections.js +154 -0
  36. package/dist/core/injections.js.map +1 -0
  37. package/dist/core/installer.d.ts +7 -3
  38. package/dist/core/installer.d.ts.map +1 -1
  39. package/dist/core/installer.js +74 -26
  40. package/dist/core/installer.js.map +1 -1
  41. package/dist/core/mcp.d.ts +12 -0
  42. package/dist/core/mcp.d.ts.map +1 -1
  43. package/dist/core/mcp.js +112 -67
  44. package/dist/core/mcp.js.map +1 -1
  45. package/dist/core/transformer.d.ts +10 -1
  46. package/dist/core/transformer.d.ts.map +1 -1
  47. package/dist/core/transformer.js +15 -1
  48. package/dist/core/transformer.js.map +1 -1
  49. package/dist/core/transformers/antigravity.d.ts +1 -0
  50. package/dist/core/transformers/antigravity.d.ts.map +1 -1
  51. package/dist/core/transformers/antigravity.js +23 -4
  52. package/dist/core/transformers/antigravity.js.map +1 -1
  53. package/dist/core/transformers/codex.d.ts +1 -0
  54. package/dist/core/transformers/codex.d.ts.map +1 -1
  55. package/dist/core/transformers/codex.js +6 -2
  56. package/dist/core/transformers/codex.js.map +1 -1
  57. package/dist/core/transformers/default.d.ts +1 -0
  58. package/dist/core/transformers/default.d.ts.map +1 -1
  59. package/dist/core/transformers/default.js +6 -0
  60. package/dist/core/transformers/default.js.map +1 -1
  61. package/dist/core/transformers/kilocode.js +1 -1
  62. package/dist/core/transformers/kilocode.js.map +1 -1
  63. package/dist/core/transformers/qwen.d.ts +1 -0
  64. package/dist/core/transformers/qwen.d.ts.map +1 -1
  65. package/dist/core/transformers/qwen.js +6 -2
  66. package/dist/core/transformers/qwen.js.map +1 -1
  67. package/dist/utils/fs.d.ts +0 -2
  68. package/dist/utils/fs.d.ts.map +1 -1
  69. package/dist/utils/fs.js +1 -5
  70. package/dist/utils/fs.js.map +1 -1
  71. package/mcp/templates/playwright.json +4 -0
  72. package/package.json +14 -1
  73. package/skills/aif/SKILL.md +33 -53
  74. package/skills/aif-commit/SKILL.md +6 -1
  75. package/skills/aif-implement/SKILL.md +20 -1
  76. package/skills/aif-loop/SKILL.md +2 -2
  77. package/skills/aif-skill-generator/SKILL.md +6 -1
  78. package/skills/aif-skill-generator/references/SECURITY-SCANNING.md +34 -1
  79. package/skills/aif-skill-generator/scripts/security-scan.py +186 -14
  80. package/dist/cli/wizard/detector.d.ts +0 -10
  81. package/dist/cli/wizard/detector.d.ts.map +0 -1
  82. package/dist/cli/wizard/detector.js +0 -231
  83. package/dist/cli/wizard/detector.js.map +0 -1
  84. package/skills/_templates/nextjs/nextjs-patterns/SKILL.md +0 -146
  85. package/skills/_templates/node-api/api-patterns/SKILL.md +0 -245
  86. package/skills/_templates/php/php-patterns/SKILL.md +0 -491
  87. package/skills/_templates/python/python-patterns/SKILL.md +0 -236
  88. package/skills/_templates/react/react-patterns/SKILL.md +0 -181
  89. package/skills/aif-deploy/SKILL.md +0 -138
package/README.md CHANGED
@@ -28,11 +28,11 @@ ai-factory init
28
28
 
29
29
  ## Why AI Factory?
30
30
 
31
- - **Zero configuration** — detects your stack, installs relevant skills, configures integrations
31
+ - **Zero configuration** — installs relevant skills, configures integrations
32
32
  - **Best practices built-in** — logging, commits, code review, all following industry standards
33
33
  - **Spec-driven development** — AI follows plans, not random exploration. Predictable, resumable, reviewable
34
34
  - **Community skills** — leverage [skills.sh](https://skills.sh) ecosystem or generate custom skills
35
- - **Works with your stack** — Next.js, Laravel, Django, Express, and more
35
+ - **Stack-agnostic** — works with any language, framework, or platform
36
36
  - **Multi-agent support** — Claude Code, Cursor, Windsurf, Roo Code, Kilo Code, Antigravity, OpenCode, Warp, Zencoder, Codex CLI, GitHub Copilot, Gemini CLI, Junie, Qwen Code, or [any agent](docs/getting-started.md#supported-agents)
37
37
 
38
38
  ---
@@ -60,7 +60,6 @@ ai-factory init
60
60
 
61
61
  This will:
62
62
  - Ask which AI agent you use
63
- - Detect your project stack
64
63
  - Install relevant skills
65
64
  - Configure MCP servers (for supported agents)
66
65
 
@@ -144,6 +143,7 @@ AI Factory can generate and maintain your project docs with a single command:
144
143
  | [Core Skills](docs/skills.md) | All slash commands — feature, task, fix, implement, evolve, docs, and more |
145
144
  | [Plan Files](docs/plan-files.md) | Plan files, self-improvement patches, skill acquisition |
146
145
  | [Security](docs/security.md) | Two-level security scanning for external skills |
146
+ | [Extensions](docs/extensions.md) | Writing and installing extensions — commands, injections, MCP, agents |
147
147
  | [Configuration](docs/configuration.md) | `.ai-factory.json`, MCP servers, project structure, best practices |
148
148
 
149
149
  ---
@@ -0,0 +1,4 @@
1
+ export declare function extensionAddCommand(source: string): Promise<void>;
2
+ export declare function extensionRemoveCommand(name: string): Promise<void>;
3
+ export declare function extensionListCommand(): Promise<void>;
4
+ //# sourceMappingURL=extension.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"extension.d.ts","sourceRoot":"","sources":["../../../src/cli/commands/extension.ts"],"names":[],"mappings":"AA2BA,wBAAsB,mBAAmB,CAAC,MAAM,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,CAuKvE;AAED,wBAAsB,sBAAsB,CAAC,IAAI,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,CA4ExE;AAED,wBAAsB,oBAAoB,IAAI,OAAO,CAAC,IAAI,CAAC,CAwC1D"}
@@ -0,0 +1,288 @@
1
+ import chalk from 'chalk';
2
+ import path from 'path';
3
+ import { loadConfig, saveConfig } from '../../core/config.js';
4
+ import { resolveExtension, commitExtensionInstall, removeExtensionFiles, getExtensionsDir, loadExtensionManifest, } from '../../core/extensions.js';
5
+ import { applySingleExtensionInjections, } from '../../core/injections.js';
6
+ import { configureExtensionMcpServers, removeExtensionMcpServers } from '../../core/mcp.js';
7
+ import { installExtensionSkills } from '../../core/installer.js';
8
+ import { readJsonFile } from '../../utils/fs.js';
9
+ import { getAgentConfig } from '../../core/agents.js';
10
+ import { removeSkillsForAllAgents, installExtensionSkillsForAllAgents, collectReplacedSkills, restoreBaseSkills, stripInjectionsForAllAgents, removeCustomSkillsForAllAgents, } from '../../core/extension-ops.js';
11
+ export async function extensionAddCommand(source) {
12
+ const projectDir = process.cwd();
13
+ console.log(chalk.bold.blue('\nšŸ­ AI Factory - Install Extension\n'));
14
+ const config = await loadConfig(projectDir);
15
+ if (!config) {
16
+ console.log(chalk.red('Error: No .ai-factory.json found.'));
17
+ console.log(chalk.dim('Run "ai-factory init" to set up your project first.'));
18
+ process.exit(1);
19
+ }
20
+ console.log(chalk.dim(`Installing from: ${source}\n`));
21
+ try {
22
+ const extensions = config.extensions ?? [];
23
+ // Phase 1: Resolve source — download/clone and validate manifest WITHOUT writing to project
24
+ const resolved = await resolveExtension(projectDir, source);
25
+ const manifest = resolved.manifest;
26
+ try {
27
+ const existIdx = extensions.findIndex(e => e.name === manifest.name);
28
+ const oldRecord = existIdx >= 0 ? { ...extensions[existIdx] } : null;
29
+ // Load old manifest from installed dir (still intact — we haven't overwritten yet)
30
+ const oldManifest = existIdx >= 0
31
+ ? await loadExtensionManifest(path.join(getExtensionsDir(projectDir), manifest.name))
32
+ : null;
33
+ // Block conflicting replacements BEFORE copying any files
34
+ if (manifest.replaces) {
35
+ for (const [, baseSkillName] of Object.entries(manifest.replaces)) {
36
+ for (const other of extensions) {
37
+ if (other.name === manifest.name)
38
+ continue;
39
+ if (other.replacedSkills?.includes(baseSkillName)) {
40
+ throw new Error(`Conflict: skill "${baseSkillName}" is already replaced by extension "${other.name}". Remove it first.`);
41
+ }
42
+ }
43
+ }
44
+ }
45
+ // Phase 2: Commit — copy resolved files to .ai-factory/extensions/<name>/
46
+ await commitExtensionInstall(projectDir, resolved);
47
+ // Clean up old state on re-install
48
+ if (existIdx >= 0) {
49
+ await stripInjectionsForAllAgents(projectDir, config.agents, manifest.name);
50
+ // Remove old replacement skills (installed under base names)
51
+ if (oldRecord?.replacedSkills?.length) {
52
+ await removeSkillsForAllAgents(projectDir, config.agents, oldRecord.replacedSkills);
53
+ await restoreBaseSkills(projectDir, config.agents, oldRecord.replacedSkills, new Set());
54
+ }
55
+ // Remove old extension custom skills using the OLD manifest (not the new one)
56
+ if (oldManifest) {
57
+ await removeCustomSkillsForAllAgents(projectDir, config.agents, oldManifest);
58
+ }
59
+ }
60
+ console.log(chalk.green(`āœ“ Extension "${manifest.name}" v${manifest.version} installed`));
61
+ const extensionDir = path.join(getExtensionsDir(projectDir), manifest.name);
62
+ // Install replacement skills — only track successfully installed ones
63
+ const replacedSkills = [];
64
+ const replacesPaths = new Set();
65
+ if (manifest.replaces && Object.keys(manifest.replaces).length > 0) {
66
+ const nameOverrides = { ...manifest.replaces };
67
+ const replacePaths = Object.keys(manifest.replaces);
68
+ // Track per-agent success: only count as replaced if installed on ALL agents
69
+ const perAgentResults = new Map(); // baseName → success count
70
+ for (const agent of config.agents) {
71
+ const installed = await installExtensionSkills(projectDir, agent, extensionDir, replacePaths, nameOverrides);
72
+ for (const name of installed) {
73
+ perAgentResults.set(name, (perAgentResults.get(name) ?? 0) + 1);
74
+ }
75
+ }
76
+ const agentCount = config.agents.length;
77
+ for (const [extSkillPath, baseSkillName] of Object.entries(manifest.replaces)) {
78
+ replacesPaths.add(extSkillPath);
79
+ const successCount = perAgentResults.get(baseSkillName) ?? 0;
80
+ if (successCount === agentCount) {
81
+ replacedSkills.push(baseSkillName);
82
+ console.log(chalk.green(`āœ“ Replaced skill "${baseSkillName}" with "${path.basename(extSkillPath)}"`));
83
+ }
84
+ else if (successCount > 0) {
85
+ // Rollback: remove the replacement from agents where it did install, restore base skill
86
+ await removeSkillsForAllAgents(projectDir, config.agents, [baseSkillName]);
87
+ await restoreBaseSkills(projectDir, config.agents, [baseSkillName], new Set());
88
+ console.log(chalk.yellow(`⚠ Replacement "${baseSkillName}" only installed on ${successCount}/${agentCount} agents — rolled back, base skill restored`));
89
+ }
90
+ else {
91
+ console.log(chalk.yellow(`⚠ Failed to replace skill "${baseSkillName}" — base skill preserved`));
92
+ }
93
+ }
94
+ }
95
+ // Install extension custom skills (excluding replacements)
96
+ if (manifest.skills?.length) {
97
+ const nonReplacementSkills = manifest.skills.filter(s => !replacesPaths.has(s));
98
+ if (nonReplacementSkills.length > 0) {
99
+ const results = await installExtensionSkillsForAllAgents(projectDir, config.agents, extensionDir, nonReplacementSkills);
100
+ for (const [agentId, installed] of results) {
101
+ if (installed.length > 0) {
102
+ console.log(chalk.green(`āœ“ Skills installed for ${agentId}: ${installed.join(', ')}`));
103
+ }
104
+ }
105
+ }
106
+ }
107
+ // Save config AFTER all installations succeed
108
+ const record = { name: manifest.name, source, version: manifest.version, replacedSkills: replacedSkills.length > 0 ? replacedSkills : undefined };
109
+ if (existIdx >= 0) {
110
+ extensions[existIdx] = record;
111
+ }
112
+ else {
113
+ extensions.push(record);
114
+ }
115
+ config.extensions = extensions;
116
+ await saveConfig(projectDir, config);
117
+ // Apply injections for all agents
118
+ if (manifest.injections?.length) {
119
+ let totalInjections = 0;
120
+ for (const agent of config.agents) {
121
+ const count = await applySingleExtensionInjections(projectDir, agent, extensionDir, manifest);
122
+ totalInjections += count;
123
+ }
124
+ if (totalInjections > 0) {
125
+ console.log(chalk.green(`āœ“ Applied ${totalInjections} injection(s)`));
126
+ }
127
+ }
128
+ // Configure MCP servers for all agents that support it
129
+ if (manifest.mcpServers?.length) {
130
+ const mcpConfigured = await applyExtensionMcp(projectDir, config.agents.map(a => a.id), extensionDir, manifest);
131
+ if (mcpConfigured.length > 0) {
132
+ console.log(chalk.green(`āœ“ MCP servers configured: ${mcpConfigured.join(', ')}`));
133
+ for (const srv of manifest.mcpServers) {
134
+ if (srv.instruction) {
135
+ console.log(chalk.dim(` ${srv.instruction}`));
136
+ }
137
+ }
138
+ }
139
+ }
140
+ if (manifest.agents?.length) {
141
+ console.log(chalk.dim(` Agents provided: ${manifest.agents.map(a => a.displayName).join(', ')}`));
142
+ }
143
+ if (manifest.commands?.length) {
144
+ console.log(chalk.dim(` Commands provided: ${manifest.commands.map(c => c.name).join(', ')}`));
145
+ }
146
+ if (manifest.skills?.length) {
147
+ console.log(chalk.dim(` Skills provided: ${manifest.skills.join(', ')}`));
148
+ }
149
+ console.log('');
150
+ }
151
+ finally {
152
+ await resolved.cleanup();
153
+ }
154
+ }
155
+ catch (error) {
156
+ console.log(chalk.red(`Error installing extension: ${error.message}`));
157
+ process.exit(1);
158
+ }
159
+ }
160
+ export async function extensionRemoveCommand(name) {
161
+ const projectDir = process.cwd();
162
+ console.log(chalk.bold.blue('\nšŸ­ AI Factory - Remove Extension\n'));
163
+ const config = await loadConfig(projectDir);
164
+ if (!config) {
165
+ console.log(chalk.red('Error: No .ai-factory.json found.'));
166
+ process.exit(1);
167
+ }
168
+ const extensions = config.extensions ?? [];
169
+ const index = extensions.findIndex(e => e.name === name);
170
+ if (index < 0) {
171
+ console.log(chalk.red(`Extension "${name}" is not installed.`));
172
+ process.exit(1);
173
+ }
174
+ try {
175
+ const extensionDir = path.join(getExtensionsDir(projectDir), name);
176
+ const manifest = await loadExtensionManifest(extensionDir);
177
+ // Strip injections before removing files
178
+ await stripInjectionsForAllAgents(projectDir, config.agents, name, manifest);
179
+ // Remove replacement skills (installed under base names)
180
+ const extRecord = extensions[index];
181
+ if (extRecord.replacedSkills?.length) {
182
+ const removed = await removeSkillsForAllAgents(projectDir, config.agents, extRecord.replacedSkills);
183
+ for (const [agentId, skills] of removed) {
184
+ if (skills.length > 0) {
185
+ console.log(chalk.green(`āœ“ Replacement skills removed for ${agentId}: ${skills.join(', ')}`));
186
+ }
187
+ }
188
+ }
189
+ // Remove extension custom skills
190
+ if (manifest) {
191
+ const removed = await removeCustomSkillsForAllAgents(projectDir, config.agents, manifest);
192
+ for (const [agentId, skills] of removed) {
193
+ if (skills.length > 0) {
194
+ console.log(chalk.green(`āœ“ Skills removed for ${agentId}: ${skills.join(', ')}`));
195
+ }
196
+ }
197
+ }
198
+ // Restore base skills if no other extension replaces them
199
+ if (extRecord.replacedSkills?.length) {
200
+ const stillReplaced = collectReplacedSkills(extensions, name);
201
+ const restored = await restoreBaseSkills(projectDir, config.agents, extRecord.replacedSkills, stillReplaced);
202
+ if (restored.length > 0) {
203
+ console.log(chalk.green(`āœ“ Restored base skills: ${restored.join(', ')}`));
204
+ }
205
+ }
206
+ // Remove MCP servers
207
+ if (manifest?.mcpServers?.length) {
208
+ const mcpKeys = manifest.mcpServers.map(s => s.key);
209
+ for (const agent of config.agents) {
210
+ await removeExtensionMcpServers(projectDir, agent.id, mcpKeys);
211
+ }
212
+ }
213
+ await removeExtensionFiles(projectDir, name);
214
+ extensions.splice(index, 1);
215
+ config.extensions = extensions;
216
+ await saveConfig(projectDir, config);
217
+ console.log(chalk.green(`āœ“ Extension "${name}" removed`));
218
+ console.log('');
219
+ }
220
+ catch (error) {
221
+ console.log(chalk.red(`Error removing extension: ${error.message}`));
222
+ process.exit(1);
223
+ }
224
+ }
225
+ export async function extensionListCommand() {
226
+ const projectDir = process.cwd();
227
+ const config = await loadConfig(projectDir);
228
+ if (!config) {
229
+ console.log(chalk.red('Error: No .ai-factory.json found.'));
230
+ process.exit(1);
231
+ }
232
+ const extensions = config.extensions ?? [];
233
+ if (extensions.length === 0) {
234
+ console.log(chalk.dim('\nNo extensions installed.\n'));
235
+ return;
236
+ }
237
+ console.log(chalk.bold('\nInstalled extensions:\n'));
238
+ for (const ext of extensions) {
239
+ console.log(` ${chalk.bold(ext.name)} ${chalk.dim(`v${ext.version}`)}`);
240
+ console.log(chalk.dim(` Source: ${ext.source}`));
241
+ const extensionDir = path.join(getExtensionsDir(projectDir), ext.name);
242
+ const manifest = await loadExtensionManifest(extensionDir);
243
+ if (manifest) {
244
+ if (manifest.description) {
245
+ console.log(chalk.dim(` ${manifest.description}`));
246
+ }
247
+ const features = [];
248
+ if (manifest.commands?.length)
249
+ features.push(`${manifest.commands.length} command(s)`);
250
+ if (manifest.agents?.length)
251
+ features.push(`${manifest.agents.length} agent(s)`);
252
+ if (manifest.injections?.length)
253
+ features.push(`${manifest.injections.length} injection(s)`);
254
+ if (manifest.skills?.length)
255
+ features.push(`${manifest.skills.length} skill(s)`);
256
+ if (manifest.mcpServers?.length)
257
+ features.push(`${manifest.mcpServers.length} MCP server(s)`);
258
+ if (features.length > 0) {
259
+ console.log(chalk.dim(` Provides: ${features.join(', ')}`));
260
+ }
261
+ }
262
+ }
263
+ console.log('');
264
+ }
265
+ async function applyExtensionMcp(projectDir, agentIds, extensionDir, manifest) {
266
+ if (!manifest.mcpServers?.length)
267
+ return [];
268
+ const allConfigured = [];
269
+ for (const srv of manifest.mcpServers) {
270
+ const templatePath = path.join(extensionDir, srv.template);
271
+ const template = await readJsonFile(templatePath);
272
+ if (!template)
273
+ continue;
274
+ for (const agentId of agentIds) {
275
+ const agentConfig = getAgentConfig(agentId);
276
+ if (!agentConfig.supportsMcp)
277
+ continue;
278
+ const configured = await configureExtensionMcpServers(projectDir, agentId, [
279
+ { key: srv.key, template },
280
+ ]);
281
+ if (configured.length > 0 && !allConfigured.includes(srv.key)) {
282
+ allConfigured.push(srv.key);
283
+ }
284
+ }
285
+ }
286
+ return allConfigured;
287
+ }
288
+ //# sourceMappingURL=extension.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"extension.js","sourceRoot":"","sources":["../../../src/cli/commands/extension.ts"],"names":[],"mappings":"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"}
@@ -1 +1 @@
1
- {"version":3,"file":"init.d.ts","sourceRoot":"","sources":["../../../src/cli/commands/init.ts"],"names":[],"mappings":"AAqCA,wBAAsB,WAAW,IAAI,OAAO,CAAC,IAAI,CAAC,CAiIjD"}
1
+ {"version":3,"file":"init.d.ts","sourceRoot":"","sources":["../../../src/cli/commands/init.ts"],"names":[],"mappings":"AAgBA,wBAAsB,WAAW,IAAI,OAAO,CAAC,IAAI,CAAC,CA4IjD"}
@@ -5,29 +5,12 @@ import { installSkills } from '../../core/installer.js';
5
5
  import { saveConfig, configExists, loadConfig, getCurrentVersion } from '../../core/config.js';
6
6
  import { configureMcp, getMcpInstructions } from '../../core/mcp.js';
7
7
  import { getAgentConfig } from '../../core/agents.js';
8
- import { getTransformer } from '../../core/transformer.js';
9
- import { WORKFLOW_SKILLS } from '../../core/transformer.js';
10
- import { fileExists, removeDirectory, removeFile } from '../../utils/fs.js';
8
+ import { cleanupAgentSetup, getAgentOnboarding } from '../../core/transformer.js';
9
+ import { removeDirectory } from '../../utils/fs.js';
10
+ import { applyExtensionInjections } from '../../core/injections.js';
11
11
  async function removeAgentSetup(projectDir, agent) {
12
- const agentConfig = getAgentConfig(agent.id);
13
12
  await removeDirectory(path.join(projectDir, agent.skillsDir));
14
- if (agent.id === 'antigravity') {
15
- const workflowsDir = path.join(projectDir, agentConfig.configDir, 'workflows');
16
- for (const workflow of WORKFLOW_SKILLS) {
17
- const workflowFile = path.join(workflowsDir, `${workflow}.md`);
18
- if (await fileExists(workflowFile)) {
19
- await removeFile(workflowFile);
20
- }
21
- }
22
- for (const ruleFile of ['aif-guardrails.md', 'aif-conventions.md']) {
23
- const rulePath = path.join(projectDir, agentConfig.configDir, 'rules', ruleFile);
24
- if (await fileExists(rulePath)) {
25
- await removeFile(rulePath);
26
- }
27
- }
28
- }
29
- // Keep agent settings file intact: it may contain user-managed configuration
30
- // unrelated to AI Factory.
13
+ await cleanupAgentSetup(agent.id, projectDir, agent.skillsDir);
31
14
  }
32
15
  export async function initCommand() {
33
16
  const projectDir = process.cwd();
@@ -40,7 +23,7 @@ export async function initCommand() {
40
23
  }
41
24
  try {
42
25
  const existingAgentIds = existingConfig?.agents.map(agent => agent.id) ?? [];
43
- const answers = await runWizard(projectDir, existingAgentIds);
26
+ const answers = await runWizard(existingAgentIds);
44
27
  const selectedAgentIds = new Set(answers.agents.map(agent => agent.id));
45
28
  const removedAgents = (existingConfig?.agents ?? []).filter(agent => !selectedAgentIds.has(agent.id));
46
29
  if (removedAgents.length > 0) {
@@ -59,7 +42,6 @@ export async function initCommand() {
59
42
  projectDir,
60
43
  skillsDir: agentConfig.skillsDir,
61
44
  skills: answers.selectedSkills,
62
- stack: null, // Stack-specific skills generated by /aif in Claude
63
45
  agentId: agentSelection.id,
64
46
  });
65
47
  const configuredMcp = await configureMcp(projectDir, {
@@ -67,6 +49,7 @@ export async function initCommand() {
67
49
  filesystem: agentSelection.mcpFilesystem,
68
50
  postgres: agentSelection.mcpPostgres,
69
51
  chromeDevtools: agentSelection.mcpChromeDevtools,
52
+ playwright: agentSelection.mcpPlaywright,
70
53
  }, agentSelection.id);
71
54
  if (configuredMcp.length > 0) {
72
55
  mcpSummary[agentSelection.id] = configuredMcp;
@@ -80,13 +63,26 @@ export async function initCommand() {
80
63
  filesystem: agentSelection.mcpFilesystem,
81
64
  postgres: agentSelection.mcpPostgres,
82
65
  chromeDevtools: agentSelection.mcpChromeDevtools,
66
+ playwright: agentSelection.mcpPlaywright,
83
67
  },
84
68
  });
85
69
  }
70
+ const existingExtensions = existingConfig?.extensions ?? [];
86
71
  await saveConfig(projectDir, {
87
72
  version: getCurrentVersion(),
88
73
  agents: installedAgents,
74
+ extensions: existingExtensions,
89
75
  });
76
+ // Re-apply extension injections after skill installation
77
+ if (existingExtensions.length > 0) {
78
+ let totalInjections = 0;
79
+ for (const agent of installedAgents) {
80
+ totalInjections += await applyExtensionInjections(projectDir, agent, existingExtensions);
81
+ }
82
+ if (totalInjections > 0) {
83
+ console.log(chalk.green(`āœ“ Re-applied ${totalInjections} extension injection(s)`));
84
+ }
85
+ }
90
86
  console.log(chalk.green('āœ“ Configuration saved to .ai-factory.json'));
91
87
  console.log(chalk.bold.green('\nāœ… Setup complete!\n'));
92
88
  for (const agent of installedAgents) {
@@ -105,27 +101,21 @@ export async function initCommand() {
105
101
  console.log('');
106
102
  }
107
103
  console.log(chalk.bold('\nNext steps:'));
108
- const includesCodex = installedAgents.some(agent => agent.id === 'codex');
109
- const includesQwen = installedAgents.some(agent => agent.id === 'qwen');
110
- for (const [index, agent] of installedAgents.entries()) {
104
+ const onboardingByAgent = installedAgents.map(agent => ({
105
+ agent,
106
+ onboarding: getAgentOnboarding(agent.id),
107
+ }));
108
+ for (const [index, { agent, onboarding }] of onboardingByAgent.entries()) {
111
109
  const agentConfig = getAgentConfig(agent.id);
112
- const transformer = getTransformer(agent.id);
113
- const welcomeMessage = transformer.getWelcomeMessage?.();
114
110
  console.log(chalk.dim(` ${index + 1}. ${agentConfig.displayName}`));
115
- if (welcomeMessage) {
116
- for (const line of welcomeMessage) {
117
- console.log(chalk.dim(` ${line}`));
118
- }
119
- }
120
- else {
121
- console.log(chalk.dim(' Open the agent in this directory'));
122
- console.log(chalk.dim(' Run /aif to analyze project and generate stack-specific skills'));
111
+ for (const line of onboarding.welcomeMessage) {
112
+ console.log(chalk.dim(` ${line}`));
123
113
  }
124
114
  }
125
- const invocationHints = [
126
- includesCodex ? 'Codex CLI: $aif-plan, $aif-commit' : null,
127
- includesQwen ? 'Qwen Code: /skills aif-plan, /skills aif-commit' : null,
128
- ].filter(Boolean).join('; ');
115
+ const invocationHints = onboardingByAgent
116
+ .map(({ onboarding }) => onboarding.invocationHint)
117
+ .filter(Boolean)
118
+ .join('; ');
129
119
  console.log(chalk.dim(` ${installedAgents.length + 1}. Use /aif-plan and /aif-commit for daily workflow${invocationHints ? ` (${invocationHints})` : ''}`));
130
120
  console.log('');
131
121
  }
@@ -1 +1 @@
1
- {"version":3,"file":"init.js","sourceRoot":"","sources":["../../../src/cli/commands/init.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"init.js","sourceRoot":"","sources":["../../../src/cli/commands/init.ts"],"names":[],"mappings":"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"}
@@ -1 +1 @@
1
- {"version":3,"file":"update.d.ts","sourceRoot":"","sources":["../../../src/cli/commands/update.ts"],"names":[],"mappings":"AAIA,wBAAsB,aAAa,IAAI,OAAO,CAAC,IAAI,CAAC,CAwEnD"}
1
+ {"version":3,"file":"update.d.ts","sourceRoot":"","sources":["../../../src/cli/commands/update.ts"],"names":[],"mappings":"AAYA,wBAAsB,aAAa,IAAI,OAAO,CAAC,IAAI,CAAC,CA0JnD"}
@@ -1,6 +1,10 @@
1
1
  import chalk from 'chalk';
2
- import { loadConfig, saveConfig, getCurrentVersion } from '../../core/config.js';
3
- import { updateSkills, getAvailableSkills } from '../../core/installer.js';
2
+ import path from 'path';
3
+ import { getCurrentVersion, loadConfig, saveConfig } from '../../core/config.js';
4
+ import { getAvailableSkills, partitionSkills, updateSkills } from '../../core/installer.js';
5
+ import { applyExtensionInjections } from '../../core/injections.js';
6
+ import { getExtensionsDir, loadExtensionManifest } from '../../core/extensions.js';
7
+ import { installExtensionSkillsForAllAgents, installSkillsForAllAgents, collectReplacedSkills, } from '../../core/extension-ops.js';
4
8
  export async function updateCommand() {
5
9
  const projectDir = process.cwd();
6
10
  console.log(chalk.bold.blue('\nšŸ­ AI Factory - Update Skills\n'));
@@ -18,19 +22,95 @@ export async function updateCommand() {
18
22
  const availableSkills = await getAvailableSkills();
19
23
  const previousBaseSkillsByAgent = new Map();
20
24
  for (const agent of config.agents) {
21
- const previousBaseSkills = agent.installedSkills.filter(s => !s.includes('/'));
25
+ const { base: previousBaseSkills } = partitionSkills(agent.installedSkills);
22
26
  previousBaseSkillsByAgent.set(agent.id, previousBaseSkills);
23
27
  const newSkills = availableSkills.filter(s => !previousBaseSkills.includes(s));
28
+ const removedSkills = previousBaseSkills.filter(s => !availableSkills.includes(s));
24
29
  if (newSkills.length > 0) {
25
30
  console.log(chalk.cyan(`šŸ“¦ [${agent.id}] New skills available: ${newSkills.join(', ')}`));
26
31
  }
32
+ if (removedSkills.length > 0) {
33
+ console.log(chalk.yellow(`šŸ—‘ļø [${agent.id}] Removed skills: ${removedSkills.join(', ')}`));
34
+ }
27
35
  }
28
36
  if (config.agents.length > 0) {
29
37
  console.log('');
30
38
  }
39
+ // Collect all replaced skills from extensions
40
+ const extensions = config.extensions ?? [];
41
+ const allReplacedSkills = collectReplacedSkills(extensions);
42
+ if (allReplacedSkills.size > 0) {
43
+ console.log(chalk.dim(`Skipping replaced skills: ${[...allReplacedSkills].join(', ')}`));
44
+ }
31
45
  for (const agent of config.agents) {
32
- const updatedSkills = await updateSkills(agent, projectDir);
33
- agent.installedSkills = updatedSkills;
46
+ agent.installedSkills = await updateSkills(agent, projectDir, [...allReplacedSkills]);
47
+ }
48
+ // Re-install replacement skills from extensions
49
+ // Fix 3: If manifest fails to load, fall back to installing the base skill
50
+ const failedReplacements = [];
51
+ for (const ext of extensions) {
52
+ if (!ext.replacedSkills?.length)
53
+ continue;
54
+ const extensionDir = path.join(getExtensionsDir(projectDir), ext.name);
55
+ const manifest = await loadExtensionManifest(extensionDir);
56
+ if (!manifest?.replaces) {
57
+ console.log(chalk.yellow(`⚠ Extension "${ext.name}" manifest missing — restoring base skills: ${ext.replacedSkills.join(', ')}`));
58
+ failedReplacements.push(...ext.replacedSkills);
59
+ ext.replacedSkills = [];
60
+ continue;
61
+ }
62
+ const nameOverrides = { ...manifest.replaces };
63
+ const manifestBaseSkills = new Set(Object.values(manifest.replaces));
64
+ const replacePaths = Object.entries(manifest.replaces)
65
+ .filter(([, baseSkill]) => ext.replacedSkills.includes(baseSkill))
66
+ .map(([extPath]) => extPath);
67
+ // Detect replacedSkills in config that no longer exist in manifest.replaces
68
+ const orphanedReplacements = ext.replacedSkills.filter(s => !manifestBaseSkills.has(s));
69
+ if (orphanedReplacements.length > 0) {
70
+ console.log(chalk.yellow(`⚠ Extension "${ext.name}" no longer replaces: ${orphanedReplacements.join(', ')}`));
71
+ failedReplacements.push(...orphanedReplacements);
72
+ ext.replacedSkills = ext.replacedSkills.filter(s => manifestBaseSkills.has(s));
73
+ }
74
+ if (replacePaths.length > 0) {
75
+ const results = await installExtensionSkillsForAllAgents(projectDir, config.agents, extensionDir, replacePaths, nameOverrides);
76
+ // Detect replacements that failed to install on all agents
77
+ const agentCount = config.agents.length;
78
+ for (const [extPath, baseSkill] of Object.entries(manifest.replaces)) {
79
+ if (!ext.replacedSkills.includes(baseSkill))
80
+ continue;
81
+ if (!replacePaths.includes(extPath))
82
+ continue;
83
+ let successCount = 0;
84
+ for (const installed of results.values()) {
85
+ if (installed.includes(baseSkill))
86
+ successCount++;
87
+ }
88
+ if (successCount < agentCount) {
89
+ console.log(chalk.yellow(`⚠ Extension "${ext.name}" replacement "${baseSkill}" failed to install — restoring base skill`));
90
+ failedReplacements.push(baseSkill);
91
+ ext.replacedSkills = ext.replacedSkills.filter(s => s !== baseSkill);
92
+ }
93
+ }
94
+ }
95
+ }
96
+ // Install base skills that couldn't be replaced due to broken extensions
97
+ // But only if no other extension still replaces them
98
+ if (failedReplacements.length > 0) {
99
+ const stillReplacedByOthers = collectReplacedSkills(extensions);
100
+ const toRestore = failedReplacements.filter(s => !stillReplacedByOthers.has(s));
101
+ if (toRestore.length > 0) {
102
+ await installSkillsForAllAgents(projectDir, config.agents, toRestore);
103
+ }
104
+ }
105
+ // Re-apply extension injections
106
+ if (config.extensions?.length) {
107
+ let totalInjections = 0;
108
+ for (const agent of config.agents) {
109
+ totalInjections += await applyExtensionInjections(projectDir, agent, config.extensions);
110
+ }
111
+ if (totalInjections > 0) {
112
+ console.log(chalk.green(`āœ“ Re-applied ${totalInjections} extension injection(s)`));
113
+ }
34
114
  }
35
115
  config.version = currentVersion;
36
116
  await saveConfig(projectDir, config);
@@ -39,8 +119,7 @@ export async function updateCommand() {
39
119
  for (const agent of config.agents) {
40
120
  const previousBaseSkills = previousBaseSkillsByAgent.get(agent.id) ?? [];
41
121
  const newSkills = availableSkills.filter(s => !previousBaseSkills.includes(s));
42
- const baseSkills = agent.installedSkills.filter(s => !s.includes('/'));
43
- const customSkills = agent.installedSkills.filter(s => s.includes('/'));
122
+ const { base: baseSkills, custom: customSkills } = partitionSkills(agent.installedSkills);
44
123
  console.log(chalk.bold(`\n[${agent.id}] Base skills:`));
45
124
  for (const skill of baseSkills) {
46
125
  const isNew = newSkills.includes(skill);