pixelcrew 0.2.2 → 0.2.6

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 (173) hide show
  1. package/README.md +389 -315
  2. package/bin/pixel-agents.js +306 -149
  3. package/package.json +3 -1
  4. package/skill/SKILL.md +185 -0
  5. package/skill/references/anti-ai-rubric.md +30 -0
  6. package/skill/references/anti-ai-slop-encyclopedia.md +181 -0
  7. package/skill/references/commands-reference.md +135 -0
  8. package/skill/references/testing-and-qa-strategy.md +25 -0
  9. package/skill/references/token-efficiency.md +20 -0
  10. package/src/adapters/adapter.interface.js +77 -0
  11. package/src/adapters/antigravity.js +138 -0
  12. package/src/adapters/claude-code.js +149 -0
  13. package/src/adapters/codex.js +131 -0
  14. package/src/adapters/cursor.js +133 -0
  15. package/src/adapters/generic.js +63 -0
  16. package/src/adapters/index.js +15 -0
  17. package/src/adapters/kiro.js +134 -0
  18. package/src/adapters/registry.js +150 -0
  19. package/src/backend/analyzer/complexity-analyzer.js +104 -0
  20. package/src/backend/analyzer/requirement-analyzer.js +213 -0
  21. package/src/backend/analyzer/threat-analyzer.js +122 -0
  22. package/src/backend/api/api-designer.js +90 -0
  23. package/src/backend/api/error-contract.js +132 -0
  24. package/src/backend/api/route-generator.js +92 -0
  25. package/src/backend/api/schema-generator.js +64 -0
  26. package/src/backend/architecture/adr-generator.js +62 -0
  27. package/src/backend/architecture/architecture-reasoner.js +119 -0
  28. package/src/backend/architecture/architecture-selector.js +57 -0
  29. package/src/backend/architecture/tradeoff-analyzer.js +92 -0
  30. package/src/backend/data/data-modeler.js +114 -0
  31. package/src/backend/data/index-analyzer.js +93 -0
  32. package/src/backend/data/query-analyzer.js +41 -0
  33. package/src/backend/data/schema-generator.js +92 -0
  34. package/src/backend/data/transaction-analyzer.js +49 -0
  35. package/src/backend/index.js +67 -0
  36. package/src/backend/observability/logging-engine.js +80 -0
  37. package/src/backend/observability/metrics-engine.js +31 -0
  38. package/src/backend/observability/tracing-engine.js +16 -0
  39. package/src/backend/patterns/pattern-registry.js +74 -0
  40. package/src/backend/patterns/pattern-selector.js +39 -0
  41. package/src/backend/patterns/tradeoff-engine.js +17 -0
  42. package/src/backend/performance/cache-analyzer.js +31 -0
  43. package/src/backend/performance/concurrency-analyzer.js +34 -0
  44. package/src/backend/performance/performance-engine.js +98 -0
  45. package/src/backend/performance/query-optimizer.js +16 -0
  46. package/src/backend/reliability/failure-analyzer.js +22 -0
  47. package/src/backend/reliability/idempotency-engine.js +56 -0
  48. package/src/backend/reliability/resilience-engine.js +141 -0
  49. package/src/backend/reliability/retry-analyzer.js +15 -0
  50. package/src/backend/security/auth-selector.js +33 -0
  51. package/src/backend/security/authorization-engine.js +90 -0
  52. package/src/backend/security/policy-engine.js +49 -0
  53. package/src/backend/security/secret-analyzer.js +39 -0
  54. package/src/backend/security/security-engine.js +122 -0
  55. package/src/backend/security/threat-model.js +59 -0
  56. package/src/backend/synthesis/backend-synthesizer.js +98 -0
  57. package/src/backend/synthesis/infrastructure-synthesizer.js +108 -0
  58. package/src/backend/synthesis/module-synthesizer.js +262 -0
  59. package/src/backend/validation/architecture-validator.js +70 -0
  60. package/src/backend/validation/backend-quality-validator.js +71 -0
  61. package/src/backend/validation/dependency-validator.js +20 -0
  62. package/src/backend/validation/performance-validator.js +38 -0
  63. package/src/backend/validation/security-validator.js +73 -0
  64. package/src/commands/adapt.js +105 -0
  65. package/src/commands/add.js +78 -0
  66. package/src/commands/animate.js +48 -0
  67. package/src/commands/assemble.js +57 -0
  68. package/src/commands/audit.js +93 -0
  69. package/src/commands/backend.js +125 -0
  70. package/src/commands/bento.js +25 -0
  71. package/src/commands/blueprint.js +65 -0
  72. package/src/commands/bolder.js +48 -0
  73. package/src/commands/boss-fight.js +60 -0
  74. package/src/commands/build.js +39 -0
  75. package/src/commands/calibrate.js +25 -0
  76. package/src/commands/chromatic.js +25 -0
  77. package/src/commands/clarify.js +52 -0
  78. package/src/commands/colorize.js +57 -0
  79. package/src/commands/command.interface.js +28 -0
  80. package/src/commands/commands.js +84 -0
  81. package/src/commands/craft.js +57 -0
  82. package/src/commands/crew.js +66 -0
  83. package/src/commands/critique.js +25 -0
  84. package/src/commands/de-slop.js +25 -0
  85. package/src/commands/delight.js +46 -0
  86. package/src/commands/deploy.js +42 -0
  87. package/src/commands/distill.js +48 -0
  88. package/src/commands/doctor.js +89 -0
  89. package/src/commands/document.js +83 -0
  90. package/src/commands/eight-bit.js +25 -0
  91. package/src/commands/extract.js +75 -0
  92. package/src/commands/fix.js +46 -0
  93. package/src/commands/harden.js +85 -0
  94. package/src/commands/index.js +67 -0
  95. package/src/commands/install.js +75 -0
  96. package/src/commands/layout.js +48 -0
  97. package/src/commands/live.js +44 -0
  98. package/src/commands/manifest.js +25 -0
  99. package/src/commands/office.js +25 -0
  100. package/src/commands/onboard.js +46 -0
  101. package/src/commands/oneshot.js +60 -0
  102. package/src/commands/optimize.js +46 -0
  103. package/src/commands/overdrive.js +46 -0
  104. package/src/commands/parser.js +143 -0
  105. package/src/commands/pixelcrew.js +96 -0
  106. package/src/commands/plan.js +66 -0
  107. package/src/commands/polish.js +45 -0
  108. package/src/commands/quieter.js +48 -0
  109. package/src/commands/recap.js +358 -0
  110. package/src/commands/registry.js +353 -0
  111. package/src/commands/render.js +26 -0
  112. package/src/commands/retrofit.js +25 -0
  113. package/src/commands/review.js +118 -0
  114. package/src/commands/roster.js +25 -0
  115. package/src/commands/sentinel.js +25 -0
  116. package/src/commands/shape.js +66 -0
  117. package/src/commands/skills.js +57 -0
  118. package/src/commands/status.js +48 -0
  119. package/src/commands/stop.js +50 -0
  120. package/src/commands/sync.js +58 -0
  121. package/src/commands/typeset.js +58 -0
  122. package/src/commands/warp.js +25 -0
  123. package/src/core/agent-runtime.js +94 -0
  124. package/src/core/event-bus.js +98 -0
  125. package/src/core/index.js +9 -0
  126. package/src/core/orchestrator.js +234 -0
  127. package/src/core/scheduler.js +124 -0
  128. package/src/core/task-graph.js +185 -0
  129. package/src/dashboard/app.js +1172 -30
  130. package/src/dashboard/index.html +223 -23
  131. package/src/dashboard/styles.css +870 -0
  132. package/src/index.js +16 -0
  133. package/src/orchestrator/artifact-graph.js +104 -0
  134. package/src/orchestrator/ast-normalizer.js +147 -0
  135. package/src/orchestrator/code-generator.js +846 -0
  136. package/src/orchestrator/design-engine.js +203 -0
  137. package/src/orchestrator/engine.js +318 -39
  138. package/src/orchestrator/oneshot.js +351 -1561
  139. package/src/orchestrator/ontology.js +394 -0
  140. package/src/orchestrator/planner.js +302 -0
  141. package/src/orchestrator/repair-planner.js +67 -0
  142. package/src/orchestrator/requirement-contract.js +177 -0
  143. package/src/orchestrator/requirement-validator.js +39 -0
  144. package/src/orchestrator/semantic-engine.js +582 -0
  145. package/src/orchestrator/semantic-reviewer.js +179 -0
  146. package/src/orchestrator/skills-registry.js +194 -0
  147. package/src/orchestrator/task-planner.js +111 -0
  148. package/src/orchestrator/task-queue.js +128 -0
  149. package/src/orchestrator/telemetry.js +209 -0
  150. package/src/orchestrator/ui-synthesizer.js +245 -0
  151. package/src/orchestrator/visual-critic.js +106 -0
  152. package/src/policies/architecture/layering.policy.js +14 -0
  153. package/src/policies/performance/indexing.policy.js +13 -0
  154. package/src/policies/reliability/resilience.policy.js +13 -0
  155. package/src/policies/security/auth.policy.js +31 -0
  156. package/src/protocol/agent.js +124 -0
  157. package/src/protocol/event.js +78 -0
  158. package/src/protocol/index.js +8 -0
  159. package/src/protocol/skill.js +54 -0
  160. package/src/protocol/task.js +100 -0
  161. package/src/scaffold/claude-generator.js +60 -0
  162. package/src/scaffold/commands-catalog.js +321 -0
  163. package/src/scaffold/cursor-generator.js +74 -0
  164. package/src/scaffold/ide-rules.js +133 -0
  165. package/src/scaffold/init.js +415 -91
  166. package/src/scaffold/installer.js +571 -0
  167. package/src/scaffold/kiro-generator.js +86 -0
  168. package/src/scaffold/skills-bundle.js +520 -0
  169. package/src/scaffold/templates.js +57 -4
  170. package/src/scaffold/workstations.js +364 -0
  171. package/src/server/server.js +292 -42
  172. package/src/utils/fs-safe.js +168 -0
  173. package/src/utils/markdown-report.js +175 -0
@@ -1,17 +1,28 @@
1
1
  import fs from 'node:fs/promises';
2
2
  import path from 'node:path';
3
+ import os from 'node:os';
3
4
  import readline from 'node:readline/promises';
4
- import { fileURLToPath } from 'node:url';
5
+ import fsSync from 'node:fs';
5
6
  import { DEFAULT_CONFIG, INITIAL_STATE, AGENT_MARKDOWNS, SKILL_MARKDOWNS } from './templates.js';
6
7
  import { analyzeCodebase, buildAdaptedConfig } from './analyzer.js';
8
+ import { detectActiveIDE, GLOBAL_PROVIDER_PATHS, PROVIDER_PATHS } from './installer.js';
9
+ import { getSkillBundle, getAllCanonicalSkillIds } from './skills-bundle.js';
10
+ import { generateKiroFiles } from './kiro-generator.js';
11
+ import { generateCursorFiles, generateAntigravityFiles, generateClaudeFiles, generateAllIDERules } from './ide-rules.js';
12
+ import { FLOOR42_COMMANDS } from './commands-catalog.js';
13
+ import { safeWriteFile, safeMkdir, DryRunReporter } from '../utils/fs-safe.js';
7
14
 
8
15
  /**
9
- * Initializes a new .pixel-agents workspace adapted to the target directory
16
+ * Initializes a new .pixel-crew workspace adapted to the target directory
10
17
  */
11
18
  export async function initializeProject(targetDir = process.cwd(), options = {}) {
12
- const isInteractive = !options.yes && process.stdin.isTTY;
19
+ const isInteractive = !options.yes && !options.dryRun && process.stdin.isTTY;
13
20
  let projectName = options.name || path.basename(targetDir);
14
- let enableDashboard = true;
21
+ const activeIDE = detectActiveIDE(targetDir);
22
+ let installScope = options.scope || (options.global ? 'global' : 'project');
23
+ let chosenProvider = options.provider || null;
24
+ const dryRun = Boolean(options.dryRun);
25
+ const reporter = options.reporter || new DryRunReporter(targetDir);
15
26
 
16
27
  if (isInteractive) {
17
28
  const rl = readline.createInterface({
@@ -21,7 +32,7 @@ export async function initializeProject(targetDir = process.cwd(), options = {})
21
32
 
22
33
  console.log('\n\x1b[36m' + `
23
34
  ╔═══════════════════════════════════════════════════════════╗
24
- ║ PIXEL AGENTS - Multi-Agent Orchestration Framework ║
35
+ ║ PIXEL CREW - Multi-Agent Orchestration Framework ║
25
36
  ║ [ ◉ _ ◉ ] ║
26
37
  ╚═══════════════════════════════════════════════════════════╝
27
38
  ` + '\x1b[0m');
@@ -31,18 +42,88 @@ export async function initializeProject(targetDir = process.cwd(), options = {})
31
42
  projectName = nameAns.trim();
32
43
  }
33
44
 
34
- const dashAns = await rl.question(`? Enable visual pixel dashboard? (Y/n): `);
35
- if (dashAns.trim().toLowerCase() === 'n') {
36
- enableDashboard = false;
45
+
46
+ if (!chosenProvider) {
47
+ const isDetected = activeIDE.id !== 'pixel-crew';
48
+ console.log(`\n\x1b[36mTarget AI IDE Selection:\x1b[0m`);
49
+ console.log(` 1) ${isDetected ? `${activeIDE.name} (Auto-detected)` : 'Kiro AI (.kiro/ & .kirorules)'} [Default]`);
50
+ console.log(` 2) Cursor IDE (.cursor/ & .cursorrules)`);
51
+ console.log(` 3) Google Antigravity (.agents/ & AGENTS.md)`);
52
+ console.log(` 4) Claude Code (.claude/ & CLAUDE.md)`);
53
+ console.log(` 5) Clean CLI only (.pixel-crew/ only — zero extra folders)`);
54
+ console.log(` 6) Multi-IDE (Configure all IDEs)`);
55
+
56
+ const ideAns = await rl.question(`Choice [1-6] (1): `);
57
+ const trimmedIde = ideAns.trim();
58
+ if (trimmedIde === '1' || trimmedIde === '') {
59
+ chosenProvider = isDetected ? activeIDE.id : 'kiro';
60
+ } else if (trimmedIde === '2' || trimmedIde.toLowerCase() === 'cursor') {
61
+ chosenProvider = 'cursor';
62
+ } else if (trimmedIde === '3' || trimmedIde.toLowerCase() === 'antigravity' || trimmedIde.toLowerCase() === 'agents') {
63
+ chosenProvider = 'antigravity';
64
+ } else if (trimmedIde === '4' || trimmedIde.toLowerCase() === 'claude') {
65
+ chosenProvider = 'claude-code';
66
+ } else if (trimmedIde === '5' || trimmedIde.toLowerCase() === 'none' || trimmedIde.toLowerCase() === 'cli') {
67
+ chosenProvider = 'none';
68
+ } else if (trimmedIde === '6' || trimmedIde.toLowerCase() === 'all' || trimmedIde.toLowerCase() === 'multi') {
69
+ chosenProvider = 'all';
70
+ }
71
+ }
72
+
73
+ if (!options.scope && !options.global) {
74
+ console.log(`\nSelect skill installation scope:`);
75
+ console.log(` 1) Project Workspace (.pixel-crew/ and active IDE) [Default]`);
76
+ console.log(` 2) Global (${activeIDE.name}: ${activeIDE.globalPath} — available in ANY folder)`);
77
+ console.log(` 3) Both (Project Workspace + Global config)`);
78
+
79
+ const scopeAns = await rl.question(`Choice [1-3] (1): `);
80
+ const trimmed = scopeAns.trim();
81
+ if (trimmed === '2' || trimmed.toLowerCase() === 'global') installScope = 'global';
82
+ else if (trimmed === '3' || trimmed.toLowerCase() === 'both') installScope = 'both';
83
+ else installScope = 'project';
37
84
  }
38
85
 
39
86
  rl.close();
40
87
  }
41
88
 
42
- console.log('\n\x1b[33mInitializing Pixel Agents in:\x1b[0m', targetDir);
89
+ if (!chosenProvider) {
90
+ if (options.yes) {
91
+ chosenProvider = 'all';
92
+ } else if (activeIDE.id !== 'pixel-crew') {
93
+ chosenProvider = activeIDE.id;
94
+ } else {
95
+ // Check if project workspace already contains specific IDE markers
96
+ const workspaceMarkers = [
97
+ { id: 'kiro', paths: ['.kiro', '.kirorules', 'kiro.json'] },
98
+ { id: 'cursor', paths: ['.cursor', '.cursorrules'] },
99
+ { id: 'antigravity', paths: ['.agents', 'AGENTS.md', '.gemini'] },
100
+ { id: 'claude-code', paths: ['.claude', 'CLAUDE.md'] }
101
+ ];
102
+ const matchedWorkspace = workspaceMarkers.find(m => m.paths.some(p => fsSync.existsSync(path.join(targetDir, p))));
103
+
104
+ if (matchedWorkspace) {
105
+ chosenProvider = matchedWorkspace.id;
106
+ } else {
107
+ // Check if user has global IDEs in home directory
108
+ const home = options.homeDir || process.env.PIXELCREW_HOME || os.homedir();
109
+ const homeMarkers = [
110
+ { id: 'claude-code', path: path.join(home, '.claude') },
111
+ { id: 'cursor', path: path.join(home, '.cursor') },
112
+ { id: 'kiro', path: path.join(home, '.kiro') },
113
+ { id: 'antigravity', path: path.join(home, '.gemini', 'config') }
114
+ ];
115
+ const hasHomeIde = homeMarkers.some(m => fsSync.existsSync(m.path));
116
+ // Default to 'all' so that when opened in ANY AI IDE on this device,
117
+ // slash commands and workflows appear immediately!
118
+ chosenProvider = hasHomeIde ? 'all' : (options.yes ? 'all' : 'none');
119
+ }
120
+ }
121
+ }
122
+
123
+ console.log('\n\x1b[33mInitializing Pixel Crew in:\x1b[0m', targetDir);
43
124
 
44
125
  // 1. Deep Codebase Analysis & Context Extraction
45
- console.log('\x1b[36m🔍 Scanning and analyzing codebase architecture...\x1b[0m');
126
+ console.log('\x1b[36mScanning and analyzing codebase architecture...\x1b[0m');
46
127
  const profile = await analyzeCodebase(targetDir);
47
128
  if (options.name) {
48
129
  profile.projectName = options.name;
@@ -51,105 +132,348 @@ export async function initializeProject(targetDir = process.cwd(), options = {})
51
132
  projectName = profile.projectName;
52
133
  }
53
134
 
54
- console.log(` \x1b[90m• Languages:\x1b[0m ${profile.languages.join(', ') || 'JavaScript'}`);
55
- console.log(` \x1b[90m• Frameworks:\x1b[0m ${profile.frameworks.join(', ') || 'Standard Web'}`);
56
- console.log(` \x1b[90m• Backend:\x1b[0m ${profile.backend.join(', ') || 'Node.js'}`);
57
- console.log(` \x1b[90m• Database:\x1b[0m ${profile.database.join(', ') || 'SQL / Relational'}`);
58
- const pixelAgentsDir = path.join(targetDir, '.pixel-agents');
59
- const agentsDir = path.join(pixelAgentsDir, 'agents');
60
- const skillsDir = path.join(pixelAgentsDir, 'skills');
61
- const reportsDir = path.join(pixelAgentsDir, 'reports');
62
- const dashboardDir = path.join(pixelAgentsDir, 'dashboard');
63
-
64
- // Create directories inside .pixel-agents
65
- await fs.mkdir(pixelAgentsDir, { recursive: true });
66
- await fs.mkdir(agentsDir, { recursive: true });
67
- await fs.mkdir(skillsDir, { recursive: true });
68
- await fs.mkdir(reportsDir, { recursive: true });
69
- if (enableDashboard) {
70
- await fs.mkdir(dashboardDir, { recursive: true });
135
+ const isEmptyDir = profile.files.length === 0 && profile.directories.length === 0;
136
+
137
+ if (isEmptyDir) {
138
+ console.log(` \x1b[90m• Workspace:\x1b[0m Greenfield (Empty Directory)`);
139
+ console.log(` \x1b[90m• Default Stack:\x1b[0m Next.js 14/15 (TypeScript) + Tailwind CSS`);
140
+ console.log(` \x1b[90m• Backend:\x1b[0m TypeScript Route Handlers`);
141
+ } else {
142
+ console.log(` \x1b[90m• Languages:\x1b[0m ${profile.languages.join(', ') || 'JavaScript'}`);
143
+ console.log(` \x1b[90m• Frameworks:\x1b[0m ${profile.frameworks.join(', ') || 'Standard Web'}`);
144
+ console.log(` \x1b[90m• Backend:\x1b[0m ${profile.backend.join(', ') || 'Node.js'}`);
145
+ console.log(` \x1b[90m• Database:\x1b[0m ${profile.database.join(', ') || 'SQL / Relational'}`);
71
146
  }
147
+ const pixelCrewDir = path.join(targetDir, '.pixel-crew');
148
+ const targets = [pixelCrewDir];
72
149
 
73
150
  // 2. Build Context-Adapted Config
74
151
  const adaptedConfig = buildAdaptedConfig(profile, options);
75
152
  adaptedConfig.project = projectName;
76
- adaptedConfig.dashboard.enabled = enableDashboard;
77
-
78
- await fs.writeFile(
79
- path.join(pixelAgentsDir, 'config.json'),
80
- JSON.stringify(adaptedConfig, null, 2),
81
- 'utf-8'
82
- );
83
- console.log(' \x1b[32m✓\x1b[0m Created .pixel-agents/config.json (tailored agent roles & permissions)');
84
-
85
- // 3. Write Codebase Context Cache
86
- await fs.writeFile(
87
- path.join(pixelAgentsDir, 'context.json'),
88
- JSON.stringify(profile, null, 2),
89
- 'utf-8'
90
- );
91
- console.log(' \x1b[32m✓\x1b[0m Created .pixel-agents/context.json (grounded codebase context)');
92
-
93
- // 4. Write state.json
153
+ if (!adaptedConfig.orchestrator) adaptedConfig.orchestrator = {};
154
+ adaptedConfig.orchestrator.runtimeStrategy = options.provider || 'auto';
155
+
156
+ // 4. State & Initial Event
94
157
  const state = JSON.parse(JSON.stringify(INITIAL_STATE));
95
158
  state.startedAt = new Date().toISOString();
96
- await fs.writeFile(
97
- path.join(pixelAgentsDir, 'state.json'),
98
- JSON.stringify(state, null, 2),
99
- 'utf-8'
100
- );
101
- console.log(' \x1b[32m✓\x1b[0m Created .pixel-agents/state.json');
102
-
103
- // 5. Write initial events.jsonl
159
+
104
160
  const initialEvent = {
105
161
  id: 'evt-0',
106
162
  timestamp: Date.now(),
107
163
  agent: 'orchestrator',
108
164
  type: 'spawn',
109
- message: `Pixel Agents swarm initialized & adapted to ${profile.frameworks.join(', ') || 'codebase'}`,
110
- metadata: { version: '0.1.0', profile }
165
+ message: `Pixel Crew swarm initialized & adapted to ${profile.frameworks.join(', ') || 'codebase'}`,
166
+ metadata: { version: '0.2.5', profile }
111
167
  };
112
- await fs.writeFile(
113
- path.join(pixelAgentsDir, 'events.jsonl'),
114
- JSON.stringify(initialEvent) + '\n',
115
- 'utf-8'
116
- );
117
- console.log(' \x1b[32m✓\x1b[0m Created .pixel-agents/events.jsonl');
118
-
119
- // 6. Write agents/*.md
120
- for (const [filename, content] of Object.entries(AGENT_MARKDOWNS)) {
121
- await fs.writeFile(path.join(agentsDir, filename), content.trim() + '\n', 'utf-8');
168
+
169
+ const manifest = {
170
+ name: projectName,
171
+ version: '0.2.5',
172
+ frameworks: profile.frameworks,
173
+ languages: profile.languages,
174
+ installedAt: new Date().toISOString(),
175
+ skills: Object.keys(SKILL_MARKDOWNS).reduce((acc, k) => {
176
+ const sId = k.replace('.md', '');
177
+ acc[sId] = {
178
+ name: sId,
179
+ category: 'core',
180
+ providers: ['pixel-crew'],
181
+ installedAt: new Date().toISOString()
182
+ };
183
+ return acc;
184
+ }, {})
185
+ };
186
+
187
+
188
+ for (const baseDir of targets) {
189
+ const agentsDir = path.join(baseDir, 'agents');
190
+ const skillsDir = path.join(baseDir, 'skills');
191
+ const commandsDir = path.join(baseDir, 'commands');
192
+ const reportsDir = path.join(baseDir, 'reports');
193
+ const tasksDir = path.join(baseDir, 'tasks');
194
+
195
+ await safeMkdir(baseDir, { dryRun, reporter });
196
+ await safeMkdir(agentsDir, { dryRun, reporter });
197
+ await safeMkdir(skillsDir, { dryRun, reporter });
198
+ await safeMkdir(commandsDir, { dryRun, reporter });
199
+ await safeMkdir(reportsDir, { dryRun, reporter });
200
+ await safeMkdir(tasksDir, { dryRun, reporter });
201
+
202
+ await safeWriteFile(path.join(baseDir, 'config.json'), JSON.stringify(adaptedConfig, null, 2), { dryRun, reporter, targetDir });
203
+ await safeWriteFile(path.join(baseDir, 'context.json'), JSON.stringify(profile, null, 2), { dryRun, reporter, targetDir });
204
+ await safeWriteFile(path.join(baseDir, 'state.json'), JSON.stringify(state, null, 2), { dryRun, reporter, targetDir });
205
+ await safeWriteFile(path.join(baseDir, 'events.jsonl'), JSON.stringify(initialEvent) + '\n', { dryRun, reporter, targetDir });
206
+ await safeWriteFile(path.join(baseDir, 'pixel.json'), JSON.stringify(manifest, null, 2) + '\n', { dryRun, reporter, targetDir });
207
+
208
+ for (const [filename, content] of Object.entries(AGENT_MARKDOWNS)) {
209
+ await safeWriteFile(path.join(agentsDir, filename), content.trim() + '\n', { dryRun, reporter, targetDir });
210
+ }
211
+
212
+ for (const [filename, content] of Object.entries(SKILL_MARKDOWNS)) {
213
+ await safeWriteFile(path.join(skillsDir, filename), content.trim() + '\n', { dryRun, reporter, targetDir });
214
+ }
215
+
216
+ // Write all Floor 42 command markdown files
217
+ for (const cmd of FLOOR42_COMMANDS) {
218
+ const cmdContent = `---
219
+ description: ${cmd.description}
220
+ ---
221
+
222
+ # /${cmd.name}
223
+
224
+ ${cmd.prompt}
225
+ `;
226
+ await safeWriteFile(path.join(commandsDir, `${cmd.name}.md`), cmdContent, { dryRun, reporter, targetDir });
227
+ }
228
+
122
229
  }
123
- console.log(` \x1b[32m✓\x1b[0m Created ${Object.keys(AGENT_MARKDOWNS).length} agent definitions in .pixel-agents/agents/`);
124
230
 
125
- // 7. Write skills/*.md
126
- for (const [filename, content] of Object.entries(SKILL_MARKDOWNS)) {
127
- await fs.writeFile(path.join(skillsDir, filename), content.trim() + '\n', 'utf-8');
231
+ // 1. Install skills to IDE project directories (.kiro, .cursor, .agents, .claude)
232
+ let targetIdes = [];
233
+ if (installScope !== 'global') {
234
+ if (chosenProvider === 'all' || chosenProvider === 'multi') {
235
+ targetIdes = ['kiro', 'cursor', 'antigravity', 'claude-code'];
236
+ } else if (chosenProvider && chosenProvider !== 'none' && chosenProvider !== 'pixel-crew' && chosenProvider !== 'cli') {
237
+ const p = chosenProvider.toLowerCase();
238
+ if (p === 'claude') targetIdes = ['claude-code'];
239
+ else if (p === 'agents') targetIdes = ['antigravity'];
240
+ else if (PROVIDER_PATHS[p]) targetIdes = [p];
241
+ }
242
+
243
+ const canonicalSkills = getAllCanonicalSkillIds();
244
+ for (const ideId of targetIdes) {
245
+ const idePathFn = PROVIDER_PATHS[ideId];
246
+ if (!idePathFn) continue;
247
+
248
+ for (const sName of canonicalSkills) {
249
+ const bundle = await getSkillBundle(sName);
250
+ if (!bundle) continue;
251
+ const ideSkillFile = idePathFn(targetDir, sName);
252
+ await safeWriteFile(ideSkillFile, bundle.content.trim() + '\n', { dryRun, reporter, targetDir });
253
+
254
+ if (bundle.references && Object.keys(bundle.references).length > 0) {
255
+ const skillDir = path.dirname(ideSkillFile);
256
+ for (const [refName, refContent] of Object.entries(bundle.references)) {
257
+ const refFullPath = path.join(skillDir, 'references', refName);
258
+ await safeWriteFile(refFullPath, refContent, { dryRun, reporter, targetDir });
259
+ }
260
+ }
261
+ }
262
+ }
263
+
264
+ // Generate Kiro workflows, prompts, and rules
265
+ if (targetIdes.includes('kiro')) {
266
+ const kiroFiles = generateKiroFiles(targetDir, false);
267
+ for (const kf of kiroFiles) {
268
+ await safeWriteFile(kf.path, kf.content, { dryRun, reporter, targetDir });
269
+ }
270
+ }
271
+
272
+ // Generate Cursor rules & Cursor 2.0 rules
273
+ if (targetIdes.includes('cursor')) {
274
+ const cursorFiles = generateCursorFiles(targetDir);
275
+ for (const cf of cursorFiles) {
276
+ await safeWriteFile(cf.path, cf.content, { dryRun, reporter, targetDir });
277
+ }
278
+ }
279
+
280
+ // Generate Antigravity agent instructions & workspace rules
281
+ if (targetIdes.includes('antigravity')) {
282
+ const antigravityFiles = generateAntigravityFiles(targetDir);
283
+ for (const af of antigravityFiles) {
284
+ await safeWriteFile(af.path, af.content, { dryRun, reporter, targetDir });
285
+ }
286
+ }
287
+
288
+ // Generate Claude Code instructions & plugin manifest
289
+ if (targetIdes.includes('claude-code')) {
290
+ const claudeFiles = generateClaudeFiles(targetDir);
291
+ for (const clf of claudeFiles) {
292
+ await safeWriteFile(clf.path, clf.content, { dryRun, reporter, targetDir });
293
+ }
294
+ }
128
295
  }
129
- console.log(` \x1b[32m✓\x1b[0m Created ${Object.keys(SKILL_MARKDOWNS).length} skill definitions in .pixel-agents/skills/`);
130
-
131
- // 8. Copy dashboard static files if enabled
132
- if (enableDashboard) {
133
- const srcDashboardDir = fileURLToPath(new URL('../dashboard', import.meta.url));
134
- try {
135
- const html = await fs.readFile(path.join(srcDashboardDir, 'index.html'), 'utf-8');
136
- const css = await fs.readFile(path.join(srcDashboardDir, 'styles.css'), 'utf-8');
137
- const js = await fs.readFile(path.join(srcDashboardDir, 'app.js'), 'utf-8');
138
-
139
- await fs.writeFile(path.join(dashboardDir, 'index.html'), html, 'utf-8');
140
- await fs.writeFile(path.join(dashboardDir, 'styles.css'), css, 'utf-8');
141
- await fs.writeFile(path.join(dashboardDir, 'app.js'), js, 'utf-8');
142
- console.log(' \x1b[32m✓\x1b[0m Created .pixel-agents/dashboard/ (index.html, styles.css, app.js)');
143
- } catch (err) {
144
- // ignore
296
+
297
+ // 2. Install skills to Global IDE directory if scope is global, both, or all
298
+ if (installScope === 'global' || installScope === 'both' || installScope === 'all') {
299
+ const userHome = options.homeDir || process.env.PIXELCREW_HOME || os.homedir();
300
+ const globalProviders = installScope === 'all'
301
+ ? Object.keys(GLOBAL_PROVIDER_PATHS)
302
+ : (options.provider && options.provider !== 'auto'
303
+ ? (options.provider === 'all' ? Object.keys(GLOBAL_PROVIDER_PATHS) : [options.provider.toLowerCase() === 'claude' ? 'claude-code' : (options.provider.toLowerCase() === 'agents' ? 'antigravity' : options.provider.toLowerCase())])
304
+ : [activeIDE.id]);
305
+
306
+ for (const gp of globalProviders) {
307
+ const globalPathFn = GLOBAL_PROVIDER_PATHS[gp];
308
+ if (!globalPathFn) continue;
309
+
310
+ const canonicalSkills = getAllCanonicalSkillIds();
311
+ for (const sName of canonicalSkills) {
312
+ const bundle = await getSkillBundle(sName);
313
+ if (!bundle) continue;
314
+ const fullGlobalPath = globalPathFn(sName, userHome);
315
+ await safeWriteFile(fullGlobalPath, bundle.content.trim() + '\n', { dryRun, reporter, targetDir: userHome });
316
+
317
+ if (bundle.references && Object.keys(bundle.references).length > 0) {
318
+ const skillDir = path.dirname(fullGlobalPath);
319
+ for (const [refName, refContent] of Object.entries(bundle.references)) {
320
+ const refFullPath = path.join(skillDir, 'references', refName);
321
+ await safeWriteFile(refFullPath, refContent, { dryRun, reporter, targetDir: userHome });
322
+ }
323
+ }
324
+ }
325
+ }
326
+
327
+ if (globalProviders.includes('kiro')) {
328
+ const kiroGlobalFiles = generateKiroFiles(path.join(userHome, '.kiro'), true);
329
+ for (const kf of kiroGlobalFiles) {
330
+ await safeWriteFile(kf.path, kf.content, { dryRun, reporter, targetDir: userHome });
331
+ }
332
+ }
333
+
334
+ if (globalProviders.includes('claude-code')) {
335
+ const claudeGlobalFiles = generateClaudeFiles(path.join(userHome, '.claude'), true);
336
+ for (const clf of claudeGlobalFiles) {
337
+ await safeWriteFile(clf.path, clf.content, { dryRun, reporter, targetDir: userHome });
338
+ }
339
+ }
340
+
341
+ if (globalProviders.includes('cursor')) {
342
+ const cursorGlobalFiles = generateCursorFiles(path.join(userHome, '.cursor'), true);
343
+ for (const cf of cursorGlobalFiles) {
344
+ await safeWriteFile(cf.path, cf.content, { dryRun, reporter, targetDir: userHome });
345
+ }
346
+ }
347
+
348
+ if (globalProviders.includes('antigravity')) {
349
+ const antigravityGlobalFiles = generateAntigravityFiles(path.join(userHome, '.gemini', 'config'), true);
350
+ for (const af of antigravityGlobalFiles) {
351
+ await safeWriteFile(af.path, af.content, { dryRun, reporter, targetDir: userHome });
352
+ }
145
353
  }
146
354
  }
147
355
 
148
- console.log('\n\x1b[32m\x1b[1mPixel Agents initialized & adapted successfully!\x1b[0m\n');
149
- console.log('Next steps:');
150
- console.log(' \x1b[36mnpx pixel-agents start\x1b[0m Launch orchestration server & dashboard');
151
- console.log(' \x1b[36mnpx pixel-agents demo\x1b[0m Run an interactive multi-agent demo');
152
- console.log(' \x1b[36mnpx pixel-agents task "..."\x1b[0m Dispatch a task to the agent swarm\n');
356
+ // Ensure workspace has clean .gitignore rules (ignoring .vite, .next, .turbo, logs, temp)
357
+ const gitignoreResult = await ensureGitignore(targetDir, { dryRun, reporter });
153
358
 
154
- return { pixelAgentsDir, dashboardDir, profile };
359
+ if (dryRun) {
360
+ reporter.print();
361
+ return {
362
+ dryRun: true,
363
+ reporter,
364
+ profile,
365
+ pixelCrewDir,
366
+ activeIDE,
367
+ installScope,
368
+ gitignore: gitignoreResult
369
+ };
370
+ }
371
+
372
+ console.log(' \x1b[32m✓\x1b[0m Created .pixel-crew/ (config.json, context.json, state.json, events.jsonl, pixel.json)');
373
+ console.log(` \x1b[32m✓\x1b[0m Created ${Object.keys(AGENT_MARKDOWNS).length} agent definitions in .pixel-crew/agents/`);
374
+ console.log(` \x1b[32m✓\x1b[0m Created ${Object.keys(SKILL_MARKDOWNS).length} skill definitions in .pixel-crew/skills/`);
375
+ if (installScope !== 'global' && targetIdes.length > 0) {
376
+ if (targetIdes.includes('kiro')) {
377
+ console.log(` \x1b[32m✓\x1b[0m Generated Kiro workflows & prompts (.kiro/workflows/, .kiro/prompts/, .kirorules)`);
378
+ }
379
+ if (targetIdes.includes('cursor')) {
380
+ console.log(` \x1b[32m✓\x1b[0m Generated Cursor rules (.cursorrules, .cursor/rules/pixelcrew.mdc)`);
381
+ }
382
+ if (targetIdes.includes('antigravity')) {
383
+ console.log(` \x1b[32m✓\x1b[0m Generated Antigravity agent instructions (AGENTS.md, GEMINI.md, .agents/rules/)`);
384
+ }
385
+ if (targetIdes.includes('claude-code')) {
386
+ console.log(` \x1b[32m✓\x1b[0m Generated Claude Code instructions (CLAUDE.md, .claude-plugin/)`);
387
+ }
388
+ }
389
+ if (installScope === 'global' || installScope === 'both' || installScope === 'all') {
390
+ console.log(` \x1b[32m✓\x1b[0m Installed skills globally for \x1b[36m${activeIDE.name}\x1b[0m (\x1b[90m${activeIDE.globalPath}\x1b[0m)`);
391
+ }
392
+ if (gitignoreResult.created || gitignoreResult.updated) {
393
+ console.log(' \x1b[32m✓\x1b[0m Clean workspace configured in .gitignore (ignoring .vite/, .next/, build/ & cache directories)');
394
+ }
395
+
396
+ const ideLabel = targetIdes.length === 1
397
+ ? (targetIdes[0] === 'kiro' ? 'Kiro AI' : targetIdes[0] === 'cursor' ? 'Cursor IDE' : targetIdes[0] === 'antigravity' ? 'Antigravity' : 'Claude Code')
398
+ : (targetIdes.length > 1 ? 'AI IDE' : 'Pixel Crew');
399
+
400
+ console.log('\n\x1b[32m\x1b[1mPixel Crew initialized & adapted successfully!\x1b[0m\n');
401
+ console.log(`Ready in ${ideLabel} Chatbox:`);
402
+ console.log(' • Type \x1b[36minit\x1b[0m or \x1b[36m/pixelcrew init\x1b[0m in chat to adapt current workspace');
403
+ console.log(' • Type \x1b[36m/recap\x1b[0m in chat to get a token-optimized session changelog');
404
+ console.log(' • Type \x1b[36m/pixelcrew assemble "..."\x1b[0m to run full-stack multi-agent sprint');
405
+ console.log('\nCLI Commands:');
406
+ console.log(' \x1b[36mnpx pixelcrew start\x1b[0m Launch orchestration server');
407
+ console.log(' \x1b[36mnpx pixelcrew task "..."\x1b[0m Dispatch goal or full-stack task to agents');
408
+ console.log(' \x1b[36mnpx pixelcrew recap\x1b[0m Generate git activity and session recap');
409
+ console.log(' \x1b[36mnpx pixelcrew doctor\x1b[0m Check available coding agent providers');
410
+ console.log(' \x1b[36mnpx pixelcrew demo\x1b[0m Run interactive multi-agent visual demo\n');
411
+
412
+ return { pixelCrewDir, profile, gitignore: gitignoreResult };
413
+ }
414
+
415
+ /**
416
+ * Ensures target workspace has clean ignore rules for .vite, .next, and build/cache folders
417
+ */
418
+ export async function ensureGitignore(targetDir, { dryRun = false, reporter } = {}) {
419
+ const gitignorePath = path.join(targetDir, '.gitignore');
420
+ const requiredPatterns = [
421
+ 'node_modules/',
422
+ '.vite/',
423
+ '.next/',
424
+ '.turbo/',
425
+ 'dist/',
426
+ 'build/',
427
+ '*.log',
428
+ '.DS_Store',
429
+ '.pixel-temp/',
430
+ 'scratch/',
431
+ 'tmp/'
432
+ ];
433
+
434
+ let existingContent = '';
435
+ let exists = false;
436
+ try {
437
+ existingContent = await fs.readFile(gitignorePath, 'utf-8');
438
+ exists = true;
439
+ } catch {}
440
+
441
+ const lines = existingContent.split('\n').map(l => l.trim());
442
+ const missing = requiredPatterns.filter(p => !lines.includes(p));
443
+
444
+ if (!exists) {
445
+ const newContent = [
446
+ '# Dependencies',
447
+ 'node_modules/',
448
+ 'package-lock.json',
449
+ '',
450
+ '# Build and Cache Artifacts',
451
+ '.vite/',
452
+ '.next/',
453
+ '.turbo/',
454
+ 'dist/',
455
+ 'build/',
456
+ '',
457
+ '# Runtime & Workspace Temp',
458
+ '.pixel-temp/',
459
+ 'scratch/',
460
+ 'tmp/',
461
+ '',
462
+ '# Logs & OS',
463
+ '*.log',
464
+ '.DS_Store',
465
+ ''
466
+ ].join('\n');
467
+
468
+ await safeWriteFile(gitignorePath, newContent, { dryRun, reporter, targetDir });
469
+ return { created: true, updated: false, missing: requiredPatterns };
470
+ } else if (missing.length > 0) {
471
+ const addition = `\n# Build Caches & Workspace Temp\n${missing.join('\n')}\n`;
472
+ const updatedContent = existingContent.endsWith('\n') ? existingContent + addition : existingContent + '\n' + addition;
473
+ await safeWriteFile(gitignorePath, updatedContent, { dryRun, reporter, targetDir });
474
+ return { created: false, updated: true, missing };
475
+ }
476
+
477
+ return { created: false, updated: false, missing: [] };
155
478
  }
479
+