@claude-flow/cli 3.0.0-alpha.13 → 3.0.0-alpha.14
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/package.json +12 -4
- package/.agentic-flow/intelligence.json +0 -17
- package/.claude-flow/agents/store.json +0 -16
- package/.claude-flow/daemon-state.json +0 -123
- package/.claude-flow/daemon-test.log +0 -0
- package/.claude-flow/daemon.log +0 -0
- package/.claude-flow/daemon2.log +0 -0
- package/.claude-flow/daemon3.log +0 -0
- package/.claude-flow/hive-mind/state.json +0 -51
- package/.claude-flow/metrics/agent-metrics.json +0 -1
- package/.claude-flow/metrics/codebase-map.json +0 -11
- package/.claude-flow/metrics/consolidation.json +0 -6
- package/.claude-flow/metrics/performance.json +0 -87
- package/.claude-flow/metrics/security-audit.json +0 -10
- package/.claude-flow/metrics/task-metrics.json +0 -10
- package/.claude-flow/metrics/test-gaps.json +0 -6
- package/__tests__/README.md +0 -140
- package/__tests__/TEST_SUMMARY.md +0 -144
- package/__tests__/cli.test.ts +0 -558
- package/__tests__/commands.test.ts +0 -726
- package/__tests__/config-adapter.test.ts +0 -362
- package/__tests__/config-loading.test.ts +0 -106
- package/__tests__/coverage/.tmp/coverage-0.json +0 -1
- package/__tests__/coverage/.tmp/coverage-1.json +0 -1
- package/__tests__/coverage/.tmp/coverage-2.json +0 -1
- package/__tests__/coverage/.tmp/coverage-3.json +0 -1
- package/__tests__/coverage/.tmp/coverage-4.json +0 -1
- package/__tests__/coverage/.tmp/coverage-5.json +0 -1
- package/__tests__/mcp-client.test.ts +0 -480
- package/__tests__/p1-commands.test.ts +0 -1064
- package/agents/architect.yaml +0 -11
- package/agents/coder.yaml +0 -11
- package/agents/reviewer.yaml +0 -10
- package/agents/security-architect.yaml +0 -10
- package/agents/tester.yaml +0 -10
- package/docs/CONFIG_LOADING.md +0 -236
- package/docs/IMPLEMENTATION_COMPLETE.md +0 -421
- package/docs/MCP_CLIENT_GUIDE.md +0 -620
- package/docs/REFACTORING_SUMMARY.md +0 -247
- package/scripts/publish.sh +0 -46
- package/src/commands/agent.ts +0 -955
- package/src/commands/claims.ts +0 -317
- package/src/commands/completions.ts +0 -558
- package/src/commands/config.ts +0 -452
- package/src/commands/daemon.ts +0 -621
- package/src/commands/deployment.ts +0 -323
- package/src/commands/doctor.ts +0 -382
- package/src/commands/embeddings.ts +0 -686
- package/src/commands/hive-mind.ts +0 -928
- package/src/commands/hooks.ts +0 -2603
- package/src/commands/index.ts +0 -154
- package/src/commands/init.ts +0 -597
- package/src/commands/mcp.ts +0 -753
- package/src/commands/memory.ts +0 -1161
- package/src/commands/migrate.ts +0 -447
- package/src/commands/neural.ts +0 -253
- package/src/commands/performance.ts +0 -292
- package/src/commands/plugins.ts +0 -316
- package/src/commands/process.ts +0 -695
- package/src/commands/providers.ts +0 -259
- package/src/commands/security.ts +0 -288
- package/src/commands/session.ts +0 -891
- package/src/commands/start.ts +0 -457
- package/src/commands/status.ts +0 -736
- package/src/commands/swarm.ts +0 -648
- package/src/commands/task.ts +0 -792
- package/src/commands/workflow.ts +0 -742
- package/src/config-adapter.ts +0 -210
- package/src/index.ts +0 -443
- package/src/infrastructure/in-memory-repositories.ts +0 -310
- package/src/init/claudemd-generator.ts +0 -631
- package/src/init/executor.ts +0 -762
- package/src/init/helpers-generator.ts +0 -628
- package/src/init/index.ts +0 -60
- package/src/init/mcp-generator.ts +0 -83
- package/src/init/settings-generator.ts +0 -284
- package/src/init/statusline-generator.ts +0 -211
- package/src/init/types.ts +0 -447
- package/src/mcp-client.ts +0 -241
- package/src/mcp-server.ts +0 -577
- package/src/mcp-tools/agent-tools.ts +0 -466
- package/src/mcp-tools/config-tools.ts +0 -370
- package/src/mcp-tools/hive-mind-tools.ts +0 -521
- package/src/mcp-tools/hooks-tools.ts +0 -1888
- package/src/mcp-tools/index.ts +0 -16
- package/src/mcp-tools/memory-tools.ts +0 -270
- package/src/mcp-tools/session-tools.ts +0 -359
- package/src/mcp-tools/swarm-tools.ts +0 -105
- package/src/mcp-tools/task-tools.ts +0 -347
- package/src/mcp-tools/types.ts +0 -33
- package/src/mcp-tools/workflow-tools.ts +0 -573
- package/src/output.ts +0 -639
- package/src/parser.ts +0 -417
- package/src/prompt.ts +0 -619
- package/src/services/index.ts +0 -15
- package/src/services/worker-daemon.ts +0 -726
- package/src/suggest.ts +0 -245
- package/src/types.ts +0 -287
- package/tmp.json +0 -0
- package/tsconfig.json +0 -16
- package/tsconfig.tsbuildinfo +0 -1
- package/vitest.config.ts +0 -13
package/src/init/executor.ts
DELETED
|
@@ -1,762 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Init Executor
|
|
3
|
-
* Main execution logic for V3 initialization
|
|
4
|
-
*/
|
|
5
|
-
|
|
6
|
-
import * as fs from 'fs';
|
|
7
|
-
import * as path from 'path';
|
|
8
|
-
import { fileURLToPath } from 'url';
|
|
9
|
-
import { dirname } from 'path';
|
|
10
|
-
|
|
11
|
-
// ESM-compatible __dirname
|
|
12
|
-
const __filename = fileURLToPath(import.meta.url);
|
|
13
|
-
const __dirname = dirname(__filename);
|
|
14
|
-
import type { InitOptions, InitResult, PlatformInfo } from './types.js';
|
|
15
|
-
import { detectPlatform } from './types.js';
|
|
16
|
-
import { generateSettingsJson } from './settings-generator.js';
|
|
17
|
-
import { generateMCPJson } from './mcp-generator.js';
|
|
18
|
-
import { generateStatuslineScript, generateStatuslineHook } from './statusline-generator.js';
|
|
19
|
-
import {
|
|
20
|
-
generatePreCommitHook,
|
|
21
|
-
generatePostCommitHook,
|
|
22
|
-
generateSessionManager,
|
|
23
|
-
generateAgentRouter,
|
|
24
|
-
generateMemoryHelper,
|
|
25
|
-
} from './helpers-generator.js';
|
|
26
|
-
import { generateClaudeMd, generateMinimalClaudeMd } from './claudemd-generator.js';
|
|
27
|
-
|
|
28
|
-
/**
|
|
29
|
-
* Skills to copy based on configuration
|
|
30
|
-
*/
|
|
31
|
-
const SKILLS_MAP: Record<string, string[]> = {
|
|
32
|
-
core: [
|
|
33
|
-
'swarm-orchestration',
|
|
34
|
-
'swarm-advanced',
|
|
35
|
-
'sparc-methodology',
|
|
36
|
-
'hooks-automation',
|
|
37
|
-
'pair-programming',
|
|
38
|
-
'verification-quality',
|
|
39
|
-
'stream-chain',
|
|
40
|
-
'skill-builder',
|
|
41
|
-
],
|
|
42
|
-
agentdb: [
|
|
43
|
-
'agentdb-advanced',
|
|
44
|
-
'agentdb-learning',
|
|
45
|
-
'agentdb-memory-patterns',
|
|
46
|
-
'agentdb-optimization',
|
|
47
|
-
'agentdb-vector-search',
|
|
48
|
-
'reasoningbank-agentdb',
|
|
49
|
-
'reasoningbank-intelligence',
|
|
50
|
-
],
|
|
51
|
-
github: [
|
|
52
|
-
'github-code-review',
|
|
53
|
-
'github-multi-repo',
|
|
54
|
-
'github-project-management',
|
|
55
|
-
'github-release-management',
|
|
56
|
-
'github-workflow-automation',
|
|
57
|
-
],
|
|
58
|
-
flowNexus: [
|
|
59
|
-
'flow-nexus-neural',
|
|
60
|
-
'flow-nexus-platform',
|
|
61
|
-
'flow-nexus-swarm',
|
|
62
|
-
],
|
|
63
|
-
v3: [
|
|
64
|
-
'v3-cli-modernization',
|
|
65
|
-
'v3-core-implementation',
|
|
66
|
-
'v3-ddd-architecture',
|
|
67
|
-
'v3-integration-deep',
|
|
68
|
-
'v3-mcp-optimization',
|
|
69
|
-
'v3-memory-unification',
|
|
70
|
-
'v3-performance-optimization',
|
|
71
|
-
'v3-security-overhaul',
|
|
72
|
-
'v3-swarm-coordination',
|
|
73
|
-
],
|
|
74
|
-
};
|
|
75
|
-
|
|
76
|
-
/**
|
|
77
|
-
* Commands to copy based on configuration
|
|
78
|
-
*/
|
|
79
|
-
const COMMANDS_MAP: Record<string, string[]> = {
|
|
80
|
-
core: ['claude-flow-help.md', 'claude-flow-swarm.md', 'claude-flow-memory.md'],
|
|
81
|
-
analysis: ['analysis'],
|
|
82
|
-
automation: ['automation'],
|
|
83
|
-
github: ['github'],
|
|
84
|
-
hooks: ['hooks'],
|
|
85
|
-
monitoring: ['monitoring'],
|
|
86
|
-
optimization: ['optimization'],
|
|
87
|
-
sparc: ['sparc'],
|
|
88
|
-
};
|
|
89
|
-
|
|
90
|
-
/**
|
|
91
|
-
* Agents to copy based on configuration
|
|
92
|
-
*/
|
|
93
|
-
const AGENTS_MAP: Record<string, string[]> = {
|
|
94
|
-
core: ['core'],
|
|
95
|
-
consensus: ['consensus'],
|
|
96
|
-
github: ['github'],
|
|
97
|
-
hiveMind: ['hive-mind'],
|
|
98
|
-
sparc: ['sparc'],
|
|
99
|
-
swarm: ['swarm'],
|
|
100
|
-
};
|
|
101
|
-
|
|
102
|
-
/**
|
|
103
|
-
* Directory structure to create
|
|
104
|
-
*/
|
|
105
|
-
const DIRECTORIES = {
|
|
106
|
-
claude: [
|
|
107
|
-
'.claude',
|
|
108
|
-
'.claude/skills',
|
|
109
|
-
'.claude/commands',
|
|
110
|
-
'.claude/agents',
|
|
111
|
-
'.claude/helpers',
|
|
112
|
-
],
|
|
113
|
-
runtime: [
|
|
114
|
-
'.claude-flow',
|
|
115
|
-
'.claude-flow/data',
|
|
116
|
-
'.claude-flow/logs',
|
|
117
|
-
'.claude-flow/sessions',
|
|
118
|
-
'.claude-flow/hooks',
|
|
119
|
-
'.claude-flow/agents',
|
|
120
|
-
'.claude-flow/workflows',
|
|
121
|
-
],
|
|
122
|
-
};
|
|
123
|
-
|
|
124
|
-
/**
|
|
125
|
-
* Execute initialization
|
|
126
|
-
*/
|
|
127
|
-
export async function executeInit(options: InitOptions): Promise<InitResult> {
|
|
128
|
-
// Detect platform
|
|
129
|
-
const platform = detectPlatform();
|
|
130
|
-
|
|
131
|
-
const result: InitResult = {
|
|
132
|
-
success: true,
|
|
133
|
-
platform,
|
|
134
|
-
created: {
|
|
135
|
-
directories: [],
|
|
136
|
-
files: [],
|
|
137
|
-
},
|
|
138
|
-
skipped: [],
|
|
139
|
-
errors: [],
|
|
140
|
-
summary: {
|
|
141
|
-
skillsCount: 0,
|
|
142
|
-
commandsCount: 0,
|
|
143
|
-
agentsCount: 0,
|
|
144
|
-
hooksEnabled: 0,
|
|
145
|
-
},
|
|
146
|
-
};
|
|
147
|
-
|
|
148
|
-
const targetDir = options.targetDir;
|
|
149
|
-
|
|
150
|
-
try {
|
|
151
|
-
// Create directory structure
|
|
152
|
-
await createDirectories(targetDir, options, result);
|
|
153
|
-
|
|
154
|
-
// Generate and write settings.json
|
|
155
|
-
if (options.components.settings) {
|
|
156
|
-
await writeSettings(targetDir, options, result);
|
|
157
|
-
}
|
|
158
|
-
|
|
159
|
-
// Generate and write .mcp.json
|
|
160
|
-
if (options.components.mcp) {
|
|
161
|
-
await writeMCPConfig(targetDir, options, result);
|
|
162
|
-
}
|
|
163
|
-
|
|
164
|
-
// Copy skills
|
|
165
|
-
if (options.components.skills) {
|
|
166
|
-
await copySkills(targetDir, options, result);
|
|
167
|
-
}
|
|
168
|
-
|
|
169
|
-
// Copy commands
|
|
170
|
-
if (options.components.commands) {
|
|
171
|
-
await copyCommands(targetDir, options, result);
|
|
172
|
-
}
|
|
173
|
-
|
|
174
|
-
// Copy agents
|
|
175
|
-
if (options.components.agents) {
|
|
176
|
-
await copyAgents(targetDir, options, result);
|
|
177
|
-
}
|
|
178
|
-
|
|
179
|
-
// Generate helpers
|
|
180
|
-
if (options.components.helpers) {
|
|
181
|
-
await writeHelpers(targetDir, options, result);
|
|
182
|
-
}
|
|
183
|
-
|
|
184
|
-
// Generate statusline
|
|
185
|
-
if (options.components.statusline) {
|
|
186
|
-
await writeStatusline(targetDir, options, result);
|
|
187
|
-
}
|
|
188
|
-
|
|
189
|
-
// Generate runtime config
|
|
190
|
-
if (options.components.runtime) {
|
|
191
|
-
await writeRuntimeConfig(targetDir, options, result);
|
|
192
|
-
}
|
|
193
|
-
|
|
194
|
-
// Generate CLAUDE.md
|
|
195
|
-
if (options.components.claudeMd) {
|
|
196
|
-
await writeClaudeMd(targetDir, options, result);
|
|
197
|
-
}
|
|
198
|
-
|
|
199
|
-
// Count enabled hooks
|
|
200
|
-
result.summary.hooksEnabled = countEnabledHooks(options);
|
|
201
|
-
|
|
202
|
-
} catch (error) {
|
|
203
|
-
result.success = false;
|
|
204
|
-
result.errors.push(error instanceof Error ? error.message : String(error));
|
|
205
|
-
}
|
|
206
|
-
|
|
207
|
-
return result;
|
|
208
|
-
}
|
|
209
|
-
|
|
210
|
-
/**
|
|
211
|
-
* Create directory structure
|
|
212
|
-
*/
|
|
213
|
-
async function createDirectories(
|
|
214
|
-
targetDir: string,
|
|
215
|
-
options: InitOptions,
|
|
216
|
-
result: InitResult
|
|
217
|
-
): Promise<void> {
|
|
218
|
-
const dirs = [
|
|
219
|
-
...DIRECTORIES.claude,
|
|
220
|
-
...(options.components.runtime ? DIRECTORIES.runtime : []),
|
|
221
|
-
];
|
|
222
|
-
|
|
223
|
-
for (const dir of dirs) {
|
|
224
|
-
const fullPath = path.join(targetDir, dir);
|
|
225
|
-
if (!fs.existsSync(fullPath)) {
|
|
226
|
-
fs.mkdirSync(fullPath, { recursive: true });
|
|
227
|
-
result.created.directories.push(dir);
|
|
228
|
-
}
|
|
229
|
-
}
|
|
230
|
-
}
|
|
231
|
-
|
|
232
|
-
/**
|
|
233
|
-
* Write settings.json
|
|
234
|
-
*/
|
|
235
|
-
async function writeSettings(
|
|
236
|
-
targetDir: string,
|
|
237
|
-
options: InitOptions,
|
|
238
|
-
result: InitResult
|
|
239
|
-
): Promise<void> {
|
|
240
|
-
const settingsPath = path.join(targetDir, '.claude', 'settings.json');
|
|
241
|
-
|
|
242
|
-
if (fs.existsSync(settingsPath) && !options.force) {
|
|
243
|
-
result.skipped.push('.claude/settings.json');
|
|
244
|
-
return;
|
|
245
|
-
}
|
|
246
|
-
|
|
247
|
-
const content = generateSettingsJson(options);
|
|
248
|
-
fs.writeFileSync(settingsPath, content, 'utf-8');
|
|
249
|
-
result.created.files.push('.claude/settings.json');
|
|
250
|
-
}
|
|
251
|
-
|
|
252
|
-
/**
|
|
253
|
-
* Write .mcp.json
|
|
254
|
-
*/
|
|
255
|
-
async function writeMCPConfig(
|
|
256
|
-
targetDir: string,
|
|
257
|
-
options: InitOptions,
|
|
258
|
-
result: InitResult
|
|
259
|
-
): Promise<void> {
|
|
260
|
-
const mcpPath = path.join(targetDir, '.mcp.json');
|
|
261
|
-
|
|
262
|
-
if (fs.existsSync(mcpPath) && !options.force) {
|
|
263
|
-
result.skipped.push('.mcp.json');
|
|
264
|
-
return;
|
|
265
|
-
}
|
|
266
|
-
|
|
267
|
-
const content = generateMCPJson(options);
|
|
268
|
-
fs.writeFileSync(mcpPath, content, 'utf-8');
|
|
269
|
-
result.created.files.push('.mcp.json');
|
|
270
|
-
}
|
|
271
|
-
|
|
272
|
-
/**
|
|
273
|
-
* Copy skills from source
|
|
274
|
-
*/
|
|
275
|
-
async function copySkills(
|
|
276
|
-
targetDir: string,
|
|
277
|
-
options: InitOptions,
|
|
278
|
-
result: InitResult
|
|
279
|
-
): Promise<void> {
|
|
280
|
-
const skillsConfig = options.skills;
|
|
281
|
-
const targetSkillsDir = path.join(targetDir, '.claude', 'skills');
|
|
282
|
-
|
|
283
|
-
// Determine which skills to copy
|
|
284
|
-
const skillsToCopy: string[] = [];
|
|
285
|
-
|
|
286
|
-
if (skillsConfig.all) {
|
|
287
|
-
// Copy all available skills
|
|
288
|
-
Object.values(SKILLS_MAP).forEach(skills => skillsToCopy.push(...skills));
|
|
289
|
-
} else {
|
|
290
|
-
if (skillsConfig.core) skillsToCopy.push(...SKILLS_MAP.core);
|
|
291
|
-
if (skillsConfig.agentdb) skillsToCopy.push(...SKILLS_MAP.agentdb);
|
|
292
|
-
if (skillsConfig.github) skillsToCopy.push(...SKILLS_MAP.github);
|
|
293
|
-
if (skillsConfig.flowNexus) skillsToCopy.push(...SKILLS_MAP.flowNexus);
|
|
294
|
-
if (skillsConfig.v3) skillsToCopy.push(...SKILLS_MAP.v3);
|
|
295
|
-
}
|
|
296
|
-
|
|
297
|
-
// Find source skills directory
|
|
298
|
-
const sourceSkillsDir = findSourceDir('skills', options.sourceBaseDir);
|
|
299
|
-
if (!sourceSkillsDir) {
|
|
300
|
-
result.errors.push('Could not find source skills directory');
|
|
301
|
-
return;
|
|
302
|
-
}
|
|
303
|
-
|
|
304
|
-
// Copy each skill
|
|
305
|
-
for (const skillName of [...new Set(skillsToCopy)]) {
|
|
306
|
-
const sourcePath = path.join(sourceSkillsDir, skillName);
|
|
307
|
-
const targetPath = path.join(targetSkillsDir, skillName);
|
|
308
|
-
|
|
309
|
-
if (fs.existsSync(sourcePath)) {
|
|
310
|
-
if (!fs.existsSync(targetPath) || options.force) {
|
|
311
|
-
copyDirRecursive(sourcePath, targetPath);
|
|
312
|
-
result.created.files.push(`.claude/skills/${skillName}`);
|
|
313
|
-
result.summary.skillsCount++;
|
|
314
|
-
} else {
|
|
315
|
-
result.skipped.push(`.claude/skills/${skillName}`);
|
|
316
|
-
}
|
|
317
|
-
}
|
|
318
|
-
}
|
|
319
|
-
}
|
|
320
|
-
|
|
321
|
-
/**
|
|
322
|
-
* Copy commands from source
|
|
323
|
-
*/
|
|
324
|
-
async function copyCommands(
|
|
325
|
-
targetDir: string,
|
|
326
|
-
options: InitOptions,
|
|
327
|
-
result: InitResult
|
|
328
|
-
): Promise<void> {
|
|
329
|
-
const commandsConfig = options.commands;
|
|
330
|
-
const targetCommandsDir = path.join(targetDir, '.claude', 'commands');
|
|
331
|
-
|
|
332
|
-
// Determine which commands to copy
|
|
333
|
-
const commandsToCopy: string[] = [];
|
|
334
|
-
|
|
335
|
-
if (commandsConfig.all) {
|
|
336
|
-
Object.values(COMMANDS_MAP).forEach(cmds => commandsToCopy.push(...cmds));
|
|
337
|
-
} else {
|
|
338
|
-
if (commandsConfig.core) commandsToCopy.push(...COMMANDS_MAP.core);
|
|
339
|
-
if (commandsConfig.analysis) commandsToCopy.push(...COMMANDS_MAP.analysis);
|
|
340
|
-
if (commandsConfig.automation) commandsToCopy.push(...COMMANDS_MAP.automation);
|
|
341
|
-
if (commandsConfig.github) commandsToCopy.push(...COMMANDS_MAP.github);
|
|
342
|
-
if (commandsConfig.hooks) commandsToCopy.push(...COMMANDS_MAP.hooks);
|
|
343
|
-
if (commandsConfig.monitoring) commandsToCopy.push(...COMMANDS_MAP.monitoring);
|
|
344
|
-
if (commandsConfig.optimization) commandsToCopy.push(...COMMANDS_MAP.optimization);
|
|
345
|
-
if (commandsConfig.sparc) commandsToCopy.push(...COMMANDS_MAP.sparc);
|
|
346
|
-
}
|
|
347
|
-
|
|
348
|
-
// Find source commands directory
|
|
349
|
-
const sourceCommandsDir = findSourceDir('commands', options.sourceBaseDir);
|
|
350
|
-
if (!sourceCommandsDir) {
|
|
351
|
-
result.errors.push('Could not find source commands directory');
|
|
352
|
-
return;
|
|
353
|
-
}
|
|
354
|
-
|
|
355
|
-
// Copy each command/directory
|
|
356
|
-
for (const cmdName of [...new Set(commandsToCopy)]) {
|
|
357
|
-
const sourcePath = path.join(sourceCommandsDir, cmdName);
|
|
358
|
-
const targetPath = path.join(targetCommandsDir, cmdName);
|
|
359
|
-
|
|
360
|
-
if (fs.existsSync(sourcePath)) {
|
|
361
|
-
if (!fs.existsSync(targetPath) || options.force) {
|
|
362
|
-
if (fs.statSync(sourcePath).isDirectory()) {
|
|
363
|
-
copyDirRecursive(sourcePath, targetPath);
|
|
364
|
-
} else {
|
|
365
|
-
fs.copyFileSync(sourcePath, targetPath);
|
|
366
|
-
}
|
|
367
|
-
result.created.files.push(`.claude/commands/${cmdName}`);
|
|
368
|
-
result.summary.commandsCount++;
|
|
369
|
-
} else {
|
|
370
|
-
result.skipped.push(`.claude/commands/${cmdName}`);
|
|
371
|
-
}
|
|
372
|
-
}
|
|
373
|
-
}
|
|
374
|
-
}
|
|
375
|
-
|
|
376
|
-
/**
|
|
377
|
-
* Copy agents from source
|
|
378
|
-
*/
|
|
379
|
-
async function copyAgents(
|
|
380
|
-
targetDir: string,
|
|
381
|
-
options: InitOptions,
|
|
382
|
-
result: InitResult
|
|
383
|
-
): Promise<void> {
|
|
384
|
-
const agentsConfig = options.agents;
|
|
385
|
-
const targetAgentsDir = path.join(targetDir, '.claude', 'agents');
|
|
386
|
-
|
|
387
|
-
// Determine which agents to copy
|
|
388
|
-
const agentsToCopy: string[] = [];
|
|
389
|
-
|
|
390
|
-
if (agentsConfig.all) {
|
|
391
|
-
Object.values(AGENTS_MAP).forEach(agents => agentsToCopy.push(...agents));
|
|
392
|
-
} else {
|
|
393
|
-
if (agentsConfig.core) agentsToCopy.push(...AGENTS_MAP.core);
|
|
394
|
-
if (agentsConfig.consensus) agentsToCopy.push(...AGENTS_MAP.consensus);
|
|
395
|
-
if (agentsConfig.github) agentsToCopy.push(...AGENTS_MAP.github);
|
|
396
|
-
if (agentsConfig.hiveMind) agentsToCopy.push(...AGENTS_MAP.hiveMind);
|
|
397
|
-
if (agentsConfig.sparc) agentsToCopy.push(...AGENTS_MAP.sparc);
|
|
398
|
-
if (agentsConfig.swarm) agentsToCopy.push(...AGENTS_MAP.swarm);
|
|
399
|
-
}
|
|
400
|
-
|
|
401
|
-
// Find source agents directory
|
|
402
|
-
const sourceAgentsDir = findSourceDir('agents', options.sourceBaseDir);
|
|
403
|
-
if (!sourceAgentsDir) {
|
|
404
|
-
result.errors.push('Could not find source agents directory');
|
|
405
|
-
return;
|
|
406
|
-
}
|
|
407
|
-
|
|
408
|
-
// Copy each agent category
|
|
409
|
-
for (const agentCategory of [...new Set(agentsToCopy)]) {
|
|
410
|
-
const sourcePath = path.join(sourceAgentsDir, agentCategory);
|
|
411
|
-
const targetPath = path.join(targetAgentsDir, agentCategory);
|
|
412
|
-
|
|
413
|
-
if (fs.existsSync(sourcePath)) {
|
|
414
|
-
if (!fs.existsSync(targetPath) || options.force) {
|
|
415
|
-
copyDirRecursive(sourcePath, targetPath);
|
|
416
|
-
// Count agent files
|
|
417
|
-
const agentFiles = countFiles(sourcePath, '.md');
|
|
418
|
-
result.summary.agentsCount += agentFiles;
|
|
419
|
-
result.created.files.push(`.claude/agents/${agentCategory}`);
|
|
420
|
-
} else {
|
|
421
|
-
result.skipped.push(`.claude/agents/${agentCategory}`);
|
|
422
|
-
}
|
|
423
|
-
}
|
|
424
|
-
}
|
|
425
|
-
}
|
|
426
|
-
|
|
427
|
-
/**
|
|
428
|
-
* Write helper scripts
|
|
429
|
-
*/
|
|
430
|
-
async function writeHelpers(
|
|
431
|
-
targetDir: string,
|
|
432
|
-
options: InitOptions,
|
|
433
|
-
result: InitResult
|
|
434
|
-
): Promise<void> {
|
|
435
|
-
const helpersDir = path.join(targetDir, '.claude', 'helpers');
|
|
436
|
-
const sourceBaseDir = options.sourceBaseDir;
|
|
437
|
-
|
|
438
|
-
// Try to copy existing helpers from source first
|
|
439
|
-
if (sourceBaseDir) {
|
|
440
|
-
const sourceHelpersDir = path.join(sourceBaseDir, '.claude', 'helpers');
|
|
441
|
-
if (fs.existsSync(sourceHelpersDir)) {
|
|
442
|
-
const helperFiles = fs.readdirSync(sourceHelpersDir);
|
|
443
|
-
for (const file of helperFiles) {
|
|
444
|
-
const sourcePath = path.join(sourceHelpersDir, file);
|
|
445
|
-
const destPath = path.join(helpersDir, file);
|
|
446
|
-
|
|
447
|
-
// Skip directories and only copy files
|
|
448
|
-
if (!fs.statSync(sourcePath).isFile()) continue;
|
|
449
|
-
|
|
450
|
-
if (!fs.existsSync(destPath) || options.force) {
|
|
451
|
-
fs.copyFileSync(sourcePath, destPath);
|
|
452
|
-
|
|
453
|
-
// Make shell scripts executable
|
|
454
|
-
if (file.endsWith('.sh')) {
|
|
455
|
-
fs.chmodSync(destPath, '755');
|
|
456
|
-
}
|
|
457
|
-
|
|
458
|
-
result.created.files.push(`.claude/helpers/${file}`);
|
|
459
|
-
} else {
|
|
460
|
-
result.skipped.push(`.claude/helpers/${file}`);
|
|
461
|
-
}
|
|
462
|
-
}
|
|
463
|
-
return; // Skip generating if we copied from source
|
|
464
|
-
}
|
|
465
|
-
}
|
|
466
|
-
|
|
467
|
-
// Fall back to generating helpers if source not available
|
|
468
|
-
const helpers: Record<string, string> = {
|
|
469
|
-
'pre-commit': generatePreCommitHook(),
|
|
470
|
-
'post-commit': generatePostCommitHook(),
|
|
471
|
-
'session.js': generateSessionManager(),
|
|
472
|
-
'router.js': generateAgentRouter(),
|
|
473
|
-
'memory.js': generateMemoryHelper(),
|
|
474
|
-
};
|
|
475
|
-
|
|
476
|
-
for (const [name, content] of Object.entries(helpers)) {
|
|
477
|
-
const filePath = path.join(helpersDir, name);
|
|
478
|
-
|
|
479
|
-
if (!fs.existsSync(filePath) || options.force) {
|
|
480
|
-
fs.writeFileSync(filePath, content, 'utf-8');
|
|
481
|
-
|
|
482
|
-
// Make shell scripts executable
|
|
483
|
-
if (!name.endsWith('.js')) {
|
|
484
|
-
fs.chmodSync(filePath, '755');
|
|
485
|
-
}
|
|
486
|
-
|
|
487
|
-
result.created.files.push(`.claude/helpers/${name}`);
|
|
488
|
-
} else {
|
|
489
|
-
result.skipped.push(`.claude/helpers/${name}`);
|
|
490
|
-
}
|
|
491
|
-
}
|
|
492
|
-
}
|
|
493
|
-
|
|
494
|
-
/**
|
|
495
|
-
* Write statusline configuration
|
|
496
|
-
*/
|
|
497
|
-
async function writeStatusline(
|
|
498
|
-
targetDir: string,
|
|
499
|
-
options: InitOptions,
|
|
500
|
-
result: InitResult
|
|
501
|
-
): Promise<void> {
|
|
502
|
-
const claudeDir = path.join(targetDir, '.claude');
|
|
503
|
-
const helpersDir = path.join(targetDir, '.claude', 'helpers');
|
|
504
|
-
|
|
505
|
-
// Try to copy existing advanced statusline files from source
|
|
506
|
-
const sourceBaseDir = options.sourceBaseDir;
|
|
507
|
-
const advancedStatuslineFiles = [
|
|
508
|
-
{ src: 'statusline.sh', dest: 'statusline.sh', dir: claudeDir },
|
|
509
|
-
{ src: 'statusline.mjs', dest: 'statusline.mjs', dir: claudeDir },
|
|
510
|
-
];
|
|
511
|
-
|
|
512
|
-
let copiedAdvanced = false;
|
|
513
|
-
if (sourceBaseDir) {
|
|
514
|
-
for (const file of advancedStatuslineFiles) {
|
|
515
|
-
const sourcePath = path.join(sourceBaseDir, '.claude', file.src);
|
|
516
|
-
const destPath = path.join(file.dir, file.dest);
|
|
517
|
-
|
|
518
|
-
if (fs.existsSync(sourcePath)) {
|
|
519
|
-
if (!fs.existsSync(destPath) || options.force) {
|
|
520
|
-
fs.copyFileSync(sourcePath, destPath);
|
|
521
|
-
// Make shell scripts executable
|
|
522
|
-
if (file.src.endsWith('.sh')) {
|
|
523
|
-
fs.chmodSync(destPath, '755');
|
|
524
|
-
}
|
|
525
|
-
result.created.files.push(`.claude/${file.dest}`);
|
|
526
|
-
copiedAdvanced = true;
|
|
527
|
-
} else {
|
|
528
|
-
result.skipped.push(`.claude/${file.dest}`);
|
|
529
|
-
}
|
|
530
|
-
}
|
|
531
|
-
}
|
|
532
|
-
}
|
|
533
|
-
|
|
534
|
-
// Fall back to generating simple statusline if advanced files not available
|
|
535
|
-
if (!copiedAdvanced) {
|
|
536
|
-
const statuslineScript = generateStatuslineScript(options);
|
|
537
|
-
const statuslineHook = generateStatuslineHook(options);
|
|
538
|
-
|
|
539
|
-
const files: Record<string, string> = {
|
|
540
|
-
'statusline.js': statuslineScript,
|
|
541
|
-
'statusline-hook.sh': statuslineHook,
|
|
542
|
-
};
|
|
543
|
-
|
|
544
|
-
for (const [name, content] of Object.entries(files)) {
|
|
545
|
-
const filePath = path.join(helpersDir, name);
|
|
546
|
-
|
|
547
|
-
if (!fs.existsSync(filePath) || options.force) {
|
|
548
|
-
fs.writeFileSync(filePath, content, 'utf-8');
|
|
549
|
-
result.created.files.push(`.claude/helpers/${name}`);
|
|
550
|
-
} else {
|
|
551
|
-
result.skipped.push(`.claude/helpers/${name}`);
|
|
552
|
-
}
|
|
553
|
-
}
|
|
554
|
-
}
|
|
555
|
-
}
|
|
556
|
-
|
|
557
|
-
/**
|
|
558
|
-
* Write runtime configuration (.claude-flow/)
|
|
559
|
-
*/
|
|
560
|
-
async function writeRuntimeConfig(
|
|
561
|
-
targetDir: string,
|
|
562
|
-
options: InitOptions,
|
|
563
|
-
result: InitResult
|
|
564
|
-
): Promise<void> {
|
|
565
|
-
const configPath = path.join(targetDir, '.claude-flow', 'config.yaml');
|
|
566
|
-
|
|
567
|
-
if (fs.existsSync(configPath) && !options.force) {
|
|
568
|
-
result.skipped.push('.claude-flow/config.yaml');
|
|
569
|
-
return;
|
|
570
|
-
}
|
|
571
|
-
|
|
572
|
-
const config = `# Claude Flow V3 Runtime Configuration
|
|
573
|
-
# Generated: ${new Date().toISOString()}
|
|
574
|
-
|
|
575
|
-
version: "3.0.0"
|
|
576
|
-
|
|
577
|
-
swarm:
|
|
578
|
-
topology: ${options.runtime.topology}
|
|
579
|
-
maxAgents: ${options.runtime.maxAgents}
|
|
580
|
-
autoScale: true
|
|
581
|
-
coordinationStrategy: consensus
|
|
582
|
-
|
|
583
|
-
memory:
|
|
584
|
-
backend: ${options.runtime.memoryBackend}
|
|
585
|
-
enableHNSW: ${options.runtime.enableHNSW}
|
|
586
|
-
persistPath: .claude-flow/data
|
|
587
|
-
cacheSize: 100
|
|
588
|
-
|
|
589
|
-
neural:
|
|
590
|
-
enabled: ${options.runtime.enableNeural}
|
|
591
|
-
modelPath: .claude-flow/neural
|
|
592
|
-
|
|
593
|
-
hooks:
|
|
594
|
-
enabled: true
|
|
595
|
-
autoExecute: true
|
|
596
|
-
|
|
597
|
-
mcp:
|
|
598
|
-
autoStart: ${options.mcp.autoStart}
|
|
599
|
-
port: ${options.mcp.port}
|
|
600
|
-
`;
|
|
601
|
-
|
|
602
|
-
fs.writeFileSync(configPath, config, 'utf-8');
|
|
603
|
-
result.created.files.push('.claude-flow/config.yaml');
|
|
604
|
-
|
|
605
|
-
// Write .gitignore
|
|
606
|
-
const gitignorePath = path.join(targetDir, '.claude-flow', '.gitignore');
|
|
607
|
-
const gitignore = `# Claude Flow runtime files
|
|
608
|
-
data/
|
|
609
|
-
logs/
|
|
610
|
-
sessions/
|
|
611
|
-
neural/
|
|
612
|
-
*.log
|
|
613
|
-
*.tmp
|
|
614
|
-
`;
|
|
615
|
-
|
|
616
|
-
if (!fs.existsSync(gitignorePath) || options.force) {
|
|
617
|
-
fs.writeFileSync(gitignorePath, gitignore, 'utf-8');
|
|
618
|
-
result.created.files.push('.claude-flow/.gitignore');
|
|
619
|
-
}
|
|
620
|
-
}
|
|
621
|
-
|
|
622
|
-
/**
|
|
623
|
-
* Write CLAUDE.md with swarm guidance
|
|
624
|
-
*/
|
|
625
|
-
async function writeClaudeMd(
|
|
626
|
-
targetDir: string,
|
|
627
|
-
options: InitOptions,
|
|
628
|
-
result: InitResult
|
|
629
|
-
): Promise<void> {
|
|
630
|
-
const claudeMdPath = path.join(targetDir, 'CLAUDE.md');
|
|
631
|
-
|
|
632
|
-
if (fs.existsSync(claudeMdPath) && !options.force) {
|
|
633
|
-
result.skipped.push('CLAUDE.md');
|
|
634
|
-
return;
|
|
635
|
-
}
|
|
636
|
-
|
|
637
|
-
// Use minimal version for minimal init, full version otherwise
|
|
638
|
-
const isMinimal = !options.components.commands && !options.components.agents;
|
|
639
|
-
const content = isMinimal ? generateMinimalClaudeMd(options) : generateClaudeMd(options);
|
|
640
|
-
|
|
641
|
-
fs.writeFileSync(claudeMdPath, content, 'utf-8');
|
|
642
|
-
result.created.files.push('CLAUDE.md');
|
|
643
|
-
}
|
|
644
|
-
|
|
645
|
-
/**
|
|
646
|
-
* Find source directory for skills/commands/agents
|
|
647
|
-
*/
|
|
648
|
-
function findSourceDir(type: 'skills' | 'commands' | 'agents', sourceBaseDir?: string): string | null {
|
|
649
|
-
// Build list of possible paths to check
|
|
650
|
-
const possiblePaths: string[] = [];
|
|
651
|
-
|
|
652
|
-
// If explicit source base directory is provided, use it first
|
|
653
|
-
if (sourceBaseDir) {
|
|
654
|
-
possiblePaths.push(path.join(sourceBaseDir, '.claude', type));
|
|
655
|
-
}
|
|
656
|
-
|
|
657
|
-
// From dist/src/init -> go up to project root
|
|
658
|
-
// __dirname is typically /path/to/v3/@claude-flow/cli/dist/src/init
|
|
659
|
-
const distPath = __dirname;
|
|
660
|
-
|
|
661
|
-
// Try to find the project root by looking for .claude directory
|
|
662
|
-
let currentDir = distPath;
|
|
663
|
-
for (let i = 0; i < 10; i++) {
|
|
664
|
-
const parentDir = path.dirname(currentDir);
|
|
665
|
-
const dotClaudePath = path.join(parentDir, '.claude', type);
|
|
666
|
-
if (fs.existsSync(dotClaudePath)) {
|
|
667
|
-
possiblePaths.push(dotClaudePath);
|
|
668
|
-
}
|
|
669
|
-
currentDir = parentDir;
|
|
670
|
-
}
|
|
671
|
-
|
|
672
|
-
// Also check relative to process.cwd() for development
|
|
673
|
-
const cwdBased = [
|
|
674
|
-
path.join(process.cwd(), '.claude', type),
|
|
675
|
-
path.join(process.cwd(), '..', '.claude', type),
|
|
676
|
-
path.join(process.cwd(), '..', '..', '.claude', type),
|
|
677
|
-
];
|
|
678
|
-
possiblePaths.push(...cwdBased);
|
|
679
|
-
|
|
680
|
-
// Check v2 directory for agents
|
|
681
|
-
if (type === 'agents') {
|
|
682
|
-
possiblePaths.push(
|
|
683
|
-
path.join(process.cwd(), 'v2', '.claude', type),
|
|
684
|
-
path.join(process.cwd(), '..', 'v2', '.claude', type),
|
|
685
|
-
);
|
|
686
|
-
}
|
|
687
|
-
|
|
688
|
-
// Plugin directory
|
|
689
|
-
possiblePaths.push(
|
|
690
|
-
path.join(process.cwd(), 'plugin', type),
|
|
691
|
-
path.join(process.cwd(), '..', 'plugin', type),
|
|
692
|
-
);
|
|
693
|
-
|
|
694
|
-
for (const p of possiblePaths) {
|
|
695
|
-
if (fs.existsSync(p)) {
|
|
696
|
-
return p;
|
|
697
|
-
}
|
|
698
|
-
}
|
|
699
|
-
|
|
700
|
-
return null;
|
|
701
|
-
}
|
|
702
|
-
|
|
703
|
-
/**
|
|
704
|
-
* Copy directory recursively
|
|
705
|
-
*/
|
|
706
|
-
function copyDirRecursive(src: string, dest: string): void {
|
|
707
|
-
fs.mkdirSync(dest, { recursive: true });
|
|
708
|
-
|
|
709
|
-
const entries = fs.readdirSync(src, { withFileTypes: true });
|
|
710
|
-
|
|
711
|
-
for (const entry of entries) {
|
|
712
|
-
const srcPath = path.join(src, entry.name);
|
|
713
|
-
const destPath = path.join(dest, entry.name);
|
|
714
|
-
|
|
715
|
-
if (entry.isDirectory()) {
|
|
716
|
-
copyDirRecursive(srcPath, destPath);
|
|
717
|
-
} else {
|
|
718
|
-
fs.copyFileSync(srcPath, destPath);
|
|
719
|
-
}
|
|
720
|
-
}
|
|
721
|
-
}
|
|
722
|
-
|
|
723
|
-
/**
|
|
724
|
-
* Count files with extension in directory
|
|
725
|
-
*/
|
|
726
|
-
function countFiles(dir: string, ext: string): number {
|
|
727
|
-
let count = 0;
|
|
728
|
-
|
|
729
|
-
const entries = fs.readdirSync(dir, { withFileTypes: true });
|
|
730
|
-
|
|
731
|
-
for (const entry of entries) {
|
|
732
|
-
const fullPath = path.join(dir, entry.name);
|
|
733
|
-
|
|
734
|
-
if (entry.isDirectory()) {
|
|
735
|
-
count += countFiles(fullPath, ext);
|
|
736
|
-
} else if (entry.name.endsWith(ext)) {
|
|
737
|
-
count++;
|
|
738
|
-
}
|
|
739
|
-
}
|
|
740
|
-
|
|
741
|
-
return count;
|
|
742
|
-
}
|
|
743
|
-
|
|
744
|
-
/**
|
|
745
|
-
* Count enabled hooks
|
|
746
|
-
*/
|
|
747
|
-
function countEnabledHooks(options: InitOptions): number {
|
|
748
|
-
const hooks = options.hooks;
|
|
749
|
-
let count = 0;
|
|
750
|
-
|
|
751
|
-
if (hooks.preToolUse) count++;
|
|
752
|
-
if (hooks.postToolUse) count++;
|
|
753
|
-
if (hooks.userPromptSubmit) count++;
|
|
754
|
-
if (hooks.sessionStart) count++;
|
|
755
|
-
if (hooks.stop) count++;
|
|
756
|
-
if (hooks.notification) count++;
|
|
757
|
-
if (hooks.permissionRequest) count++;
|
|
758
|
-
|
|
759
|
-
return count;
|
|
760
|
-
}
|
|
761
|
-
|
|
762
|
-
export default executeInit;
|