moflo 4.8.9 → 4.8.11
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/.claude/agents/core/coder.md +265 -265
- package/.claude/agents/core/planner.md +167 -167
- package/.claude/agents/core/researcher.md +189 -189
- package/.claude/agents/core/reviewer.md +325 -325
- package/.claude/agents/core/tester.md +318 -318
- package/.claude/agents/dual-mode/codex-coordinator.md +224 -224
- package/.claude/agents/dual-mode/codex-worker.md +211 -211
- package/.claude/agents/dual-mode/dual-orchestrator.md +291 -291
- package/.claude/agents/github/code-review-swarm.md +537 -537
- package/.claude/agents/github/github-modes.md +172 -172
- package/.claude/agents/github/issue-tracker.md +318 -318
- package/.claude/agents/github/multi-repo-swarm.md +552 -552
- package/.claude/agents/github/pr-manager.md +190 -190
- package/.claude/agents/github/project-board-sync.md +508 -508
- package/.claude/agents/github/release-manager.md +366 -366
- package/.claude/agents/github/release-swarm.md +582 -582
- package/.claude/agents/github/repo-architect.md +397 -397
- package/.claude/agents/github/swarm-issue.md +572 -572
- package/.claude/agents/github/swarm-pr.md +427 -427
- package/.claude/agents/github/sync-coordinator.md +451 -451
- package/.claude/agents/github/workflow-automation.md +634 -634
- package/.claude/agents/goal/code-goal-planner.md +445 -445
- package/.claude/agents/hive-mind/collective-intelligence-coordinator.md +129 -129
- package/.claude/agents/hive-mind/queen-coordinator.md +202 -202
- package/.claude/agents/hive-mind/scout-explorer.md +241 -241
- package/.claude/agents/hive-mind/swarm-memory-manager.md +192 -192
- package/.claude/agents/hive-mind/worker-specialist.md +216 -216
- package/.claude/agents/neural/safla-neural.md +73 -73
- package/.claude/agents/reasoning/goal-planner.md +72 -72
- package/.claude/agents/swarm/adaptive-coordinator.md +395 -395
- package/.claude/agents/swarm/hierarchical-coordinator.md +326 -326
- package/.claude/agents/swarm/mesh-coordinator.md +391 -391
- package/.claude/agents/templates/migration-plan.md +745 -745
- package/.claude/commands/agents/agent-spawning.md +28 -28
- package/.claude/commands/analysis/COMMAND_COMPLIANCE_REPORT.md +53 -53
- package/.claude/commands/analysis/bottleneck-detect.md +162 -162
- package/.claude/commands/analysis/performance-bottlenecks.md +58 -58
- package/.claude/commands/analysis/token-efficiency.md +44 -44
- package/.claude/commands/automation/auto-agent.md +122 -122
- package/.claude/commands/automation/self-healing.md +105 -105
- package/.claude/commands/automation/session-memory.md +89 -89
- package/.claude/commands/automation/smart-agents.md +72 -72
- package/.claude/commands/coordination/init.md +44 -44
- package/.claude/commands/coordination/orchestrate.md +43 -43
- package/.claude/commands/coordination/spawn.md +45 -45
- package/.claude/commands/coordination/swarm-init.md +85 -85
- package/.claude/commands/github/github-modes.md +146 -146
- package/.claude/commands/github/github-swarm.md +121 -121
- package/.claude/commands/github/issue-tracker.md +291 -291
- package/.claude/commands/github/pr-manager.md +169 -169
- package/.claude/commands/github/release-manager.md +337 -337
- package/.claude/commands/github/repo-architect.md +366 -366
- package/.claude/commands/github/sync-coordinator.md +300 -300
- package/.claude/commands/memory/neural.md +47 -47
- package/.claude/commands/monitoring/agents.md +44 -44
- package/.claude/commands/monitoring/status.md +46 -46
- package/.claude/commands/optimization/auto-topology.md +61 -61
- package/.claude/commands/optimization/parallel-execution.md +49 -49
- package/.claude/commands/sparc/analyzer.md +51 -51
- package/.claude/commands/sparc/architect.md +53 -53
- package/.claude/commands/sparc/ask.md +97 -97
- package/.claude/commands/sparc/batch-executor.md +54 -54
- package/.claude/commands/sparc/code.md +89 -89
- package/.claude/commands/sparc/coder.md +54 -54
- package/.claude/commands/sparc/debug.md +83 -83
- package/.claude/commands/sparc/debugger.md +54 -54
- package/.claude/commands/sparc/designer.md +53 -53
- package/.claude/commands/sparc/devops.md +109 -109
- package/.claude/commands/sparc/docs-writer.md +80 -80
- package/.claude/commands/sparc/documenter.md +54 -54
- package/.claude/commands/sparc/innovator.md +54 -54
- package/.claude/commands/sparc/integration.md +83 -83
- package/.claude/commands/sparc/mcp.md +117 -117
- package/.claude/commands/sparc/memory-manager.md +54 -54
- package/.claude/commands/sparc/optimizer.md +54 -54
- package/.claude/commands/sparc/orchestrator.md +131 -131
- package/.claude/commands/sparc/post-deployment-monitoring-mode.md +83 -83
- package/.claude/commands/sparc/refinement-optimization-mode.md +83 -83
- package/.claude/commands/sparc/researcher.md +54 -54
- package/.claude/commands/sparc/reviewer.md +54 -54
- package/.claude/commands/sparc/security-review.md +80 -80
- package/.claude/commands/sparc/sparc-modes.md +174 -174
- package/.claude/commands/sparc/sparc.md +111 -111
- package/.claude/commands/sparc/spec-pseudocode.md +80 -80
- package/.claude/commands/sparc/supabase-admin.md +348 -348
- package/.claude/commands/sparc/swarm-coordinator.md +54 -54
- package/.claude/commands/sparc/tdd.md +54 -54
- package/.claude/commands/sparc/tester.md +54 -54
- package/.claude/commands/sparc/tutorial.md +79 -79
- package/.claude/commands/sparc/workflow-manager.md +54 -54
- package/.claude/commands/sparc.md +166 -166
- package/.claude/commands/swarm/analysis.md +95 -95
- package/.claude/commands/swarm/development.md +96 -96
- package/.claude/commands/swarm/examples.md +168 -168
- package/.claude/commands/swarm/maintenance.md +102 -102
- package/.claude/commands/swarm/optimization.md +117 -117
- package/.claude/commands/swarm/research.md +136 -136
- package/.claude/commands/swarm/testing.md +131 -131
- package/.claude/commands/training/neural-patterns.md +73 -73
- package/.claude/commands/training/specialization.md +62 -62
- package/.claude/commands/workflows/development.md +77 -77
- package/.claude/commands/workflows/research.md +62 -62
- package/.claude/guidance/{agent-bootstrap.md → shipped/agent-bootstrap.md} +126 -126
- package/.claude/guidance/{guidance-memory-strategy.md → shipped/guidance-memory-strategy.md} +262 -262
- package/.claude/guidance/{memory-strategy.md → shipped/memory-strategy.md} +204 -204
- package/.claude/guidance/{moflo.md → shipped/moflo.md} +45 -31
- package/.claude/guidance/{task-swarm-integration.md → shipped/task-swarm-integration.md} +441 -348
- package/.claude/helpers/gate.cjs +236 -236
- package/.claude/helpers/hook-handler.cjs +42 -46
- package/.claude/settings.json +2 -2
- package/.claude/settings.local.json +3 -3
- package/.claude/skills/fl/SKILL.md +29 -23
- package/.claude/skills/flo/SKILL.md +29 -23
- package/.claude/skills/github-code-review/SKILL.md +4 -4
- package/.claude/skills/github-multi-repo/SKILL.md +8 -8
- package/.claude/skills/github-project-management/SKILL.md +6 -6
- package/.claude/skills/github-release-management/SKILL.md +12 -12
- package/.claude/skills/github-workflow-automation/SKILL.md +6 -6
- package/.claude/skills/hooks-automation/SKILL.md +1201 -1201
- package/.claude/skills/performance-analysis/SKILL.md +563 -563
- package/.claude/skills/sparc-methodology/SKILL.md +64 -64
- package/.claude/skills/swarm-advanced/SKILL.md +77 -77
- package/.claude-plugin/README.md +3 -3
- package/.claude-plugin/docs/PLUGIN_SUMMARY.md +3 -3
- package/.claude-plugin/docs/QUICKSTART.md +4 -4
- package/.claude-plugin/marketplace.json +3 -3
- package/.claude-plugin/plugin.json +3 -3
- package/.claude-plugin/scripts/install.sh +9 -9
- package/.claude-plugin/scripts/verify.sh +7 -7
- package/README.md +311 -116
- package/bin/gate-hook.mjs +50 -0
- package/bin/gate.cjs +138 -0
- package/bin/hook-handler.cjs +83 -0
- package/bin/hooks.mjs +72 -12
- package/bin/index-guidance.mjs +28 -34
- package/bin/index-tests.mjs +710 -0
- package/bin/lib/process-manager.mjs +243 -0
- package/bin/lib/registry-cleanup.cjs +41 -0
- package/bin/prompt-hook.mjs +72 -0
- package/bin/semantic-search.mjs +473 -441
- package/bin/session-start-launcher.mjs +81 -31
- package/bin/setup-project.mjs +13 -10
- package/package.json +4 -2
- package/src/@claude-flow/cli/README.md +1 -1
- package/src/@claude-flow/cli/bin/cli.js +175 -175
- package/src/@claude-flow/cli/dist/src/commands/doctor.js +1091 -736
- package/src/@claude-flow/cli/dist/src/commands/github.d.ts +12 -0
- package/src/@claude-flow/cli/dist/src/commands/github.js +505 -0
- package/src/@claude-flow/cli/dist/src/commands/hive-mind.js +90 -90
- package/src/@claude-flow/cli/dist/src/commands/index.d.ts +1 -0
- package/src/@claude-flow/cli/dist/src/commands/index.js +7 -0
- package/src/@claude-flow/cli/dist/src/config-adapter.js +1 -1
- package/src/@claude-flow/cli/dist/src/init/claudemd-generator.js +1 -1
- package/src/@claude-flow/cli/dist/src/init/executor.js +109 -5
- package/src/@claude-flow/cli/dist/src/init/helpers-generator.d.ts +14 -0
- package/src/@claude-flow/cli/dist/src/init/helpers-generator.js +156 -24
- package/src/@claude-flow/cli/dist/src/init/mcp-generator.js +20 -20
- package/src/@claude-flow/cli/dist/src/init/moflo-init.d.ts +7 -0
- package/src/@claude-flow/cli/dist/src/init/moflo-init.js +72 -10
- package/src/@claude-flow/cli/dist/src/init/settings-generator.js +23 -14
- package/src/@claude-flow/cli/dist/src/mcp-server.js +3 -3
- package/src/@claude-flow/cli/dist/src/plugins/manager.js +9 -8
- package/src/@claude-flow/cli/dist/src/services/worker-daemon.d.ts +1 -0
- package/src/@claude-flow/cli/dist/src/services/worker-daemon.js +3 -1
- package/src/@claude-flow/cli/dist/src/services/workflow-gate.js +10 -10
- package/src/@claude-flow/cli/package.json +1 -1
|
@@ -8,7 +8,7 @@
|
|
|
8
8
|
*/
|
|
9
9
|
|
|
10
10
|
import { spawn } from 'child_process';
|
|
11
|
-
import { existsSync, readFileSync, copyFileSync } from 'fs';
|
|
11
|
+
import { existsSync, readFileSync, copyFileSync, unlinkSync, readdirSync } from 'fs';
|
|
12
12
|
import { resolve, dirname } from 'path';
|
|
13
13
|
import { fileURLToPath } from 'url';
|
|
14
14
|
|
|
@@ -75,54 +75,87 @@ try {
|
|
|
75
75
|
try { cachedVersion = readFileSync(versionStampPath, 'utf-8').trim(); } catch {}
|
|
76
76
|
|
|
77
77
|
if (installedVersion !== cachedVersion) {
|
|
78
|
+
const binDir = resolve(projectRoot, 'node_modules/moflo/bin');
|
|
79
|
+
const manifestPath = resolve(projectRoot, '.claude-flow', 'installed-files.json');
|
|
80
|
+
|
|
81
|
+
// ── Manifest-based auto-update ──────────────────────────────────────
|
|
82
|
+
//
|
|
83
|
+
// IMPORTANT: Every file moflo installs into the destination project
|
|
84
|
+
// MUST be recorded in `currentManifest` via syncFile() or a manual
|
|
85
|
+
// push. On upgrade, files in the OLD manifest but NOT in the new one
|
|
86
|
+
// are deleted — this is how we clean up files from prior versions
|
|
87
|
+
// without accidentally deleting user-created or runtime files.
|
|
88
|
+
//
|
|
89
|
+
// When adding/removing files from the sync lists below:
|
|
90
|
+
// 1. Use syncFile() for copied files (it records automatically)
|
|
91
|
+
// 2. Push to currentManifest manually for generated files
|
|
92
|
+
// 3. That's it — cleanup is automatic on the next upgrade
|
|
93
|
+
// ────────────────────────────────────────────────────────────────────
|
|
94
|
+
|
|
95
|
+
// Load the previous manifest so we can diff after syncing
|
|
96
|
+
let previousManifest = [];
|
|
97
|
+
try { previousManifest = JSON.parse(readFileSync(manifestPath, 'utf-8')); } catch { /* ok */ }
|
|
98
|
+
|
|
99
|
+
// Track every file we install this round
|
|
100
|
+
const currentManifest = [];
|
|
101
|
+
|
|
102
|
+
/** Copy src → dest if src exists, record in manifest. */
|
|
103
|
+
function syncFile(src, dest, manifestKey) {
|
|
104
|
+
if (existsSync(src)) {
|
|
105
|
+
try { copyFileSync(src, dest); currentManifest.push(manifestKey); } catch { /* non-fatal */ }
|
|
106
|
+
}
|
|
107
|
+
}
|
|
108
|
+
|
|
78
109
|
// Version changed — sync scripts from bin/
|
|
79
110
|
if (autoUpdateConfig.scripts) {
|
|
80
|
-
const binDir = resolve(projectRoot, 'node_modules/moflo/bin');
|
|
81
111
|
const scriptsDir = resolve(projectRoot, '.claude/scripts');
|
|
82
112
|
const scriptFiles = [
|
|
83
113
|
'hooks.mjs', 'session-start-launcher.mjs', 'index-guidance.mjs',
|
|
84
114
|
'build-embeddings.mjs', 'generate-code-map.mjs', 'semantic-search.mjs',
|
|
115
|
+
'index-tests.mjs',
|
|
85
116
|
];
|
|
86
117
|
for (const file of scriptFiles) {
|
|
87
|
-
|
|
88
|
-
const dest = resolve(scriptsDir, file);
|
|
89
|
-
if (existsSync(src)) {
|
|
90
|
-
try { copyFileSync(src, dest); } catch { /* non-fatal */ }
|
|
91
|
-
}
|
|
118
|
+
syncFile(resolve(binDir, file), resolve(scriptsDir, file), `.claude/scripts/${file}`);
|
|
92
119
|
}
|
|
93
120
|
}
|
|
94
121
|
|
|
95
|
-
// Sync helpers from source .claude/helpers/
|
|
122
|
+
// Sync helpers from bin/ and source .claude/helpers/
|
|
96
123
|
if (autoUpdateConfig.helpers) {
|
|
97
|
-
const sourceHelpersDir = resolve(projectRoot, 'node_modules/moflo/src/@claude-flow/cli/.claude/helpers');
|
|
98
124
|
const helpersDir = resolve(projectRoot, '.claude/helpers');
|
|
99
|
-
|
|
100
|
-
|
|
125
|
+
if (!existsSync(helpersDir)) mkdirSync(helpersDir, { recursive: true });
|
|
126
|
+
|
|
127
|
+
// Gate and hook helpers — shipped as static files in bin/
|
|
128
|
+
const binHelperFiles = [
|
|
129
|
+
'gate.cjs', 'gate-hook.mjs', 'prompt-hook.mjs', 'hook-handler.cjs',
|
|
101
130
|
];
|
|
102
|
-
for (const file of
|
|
103
|
-
|
|
104
|
-
const dest = resolve(helpersDir, file);
|
|
105
|
-
if (existsSync(src)) {
|
|
106
|
-
try { copyFileSync(src, dest); } catch { /* non-fatal */ }
|
|
107
|
-
}
|
|
131
|
+
for (const file of binHelperFiles) {
|
|
132
|
+
syncFile(resolve(binDir, file), resolve(helpersDir, file), `.claude/helpers/${file}`);
|
|
108
133
|
}
|
|
109
134
|
|
|
110
|
-
//
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
135
|
+
// Other helpers from .claude/helpers/ and CLI .claude/helpers/
|
|
136
|
+
const helperSources = [
|
|
137
|
+
resolve(projectRoot, 'node_modules/moflo/.claude/helpers'),
|
|
138
|
+
resolve(projectRoot, 'node_modules/moflo/src/@claude-flow/cli/.claude/helpers'),
|
|
139
|
+
];
|
|
140
|
+
const sourceHelperFiles = [
|
|
141
|
+
'auto-memory-hook.mjs', 'statusline.cjs', 'intelligence.cjs', 'pre-commit', 'post-commit',
|
|
142
|
+
];
|
|
143
|
+
for (const file of sourceHelperFiles) {
|
|
144
|
+
const dest = resolve(helpersDir, file);
|
|
145
|
+
for (const srcDir of helperSources) {
|
|
146
|
+
const src = resolve(srcDir, file);
|
|
147
|
+
if (existsSync(src)) {
|
|
148
|
+
try { copyFileSync(src, dest); currentManifest.push(`.claude/helpers/${file}`); } catch { /* non-fatal */ }
|
|
149
|
+
break; // first source wins
|
|
150
|
+
}
|
|
151
|
+
}
|
|
120
152
|
}
|
|
121
153
|
}
|
|
122
154
|
|
|
123
155
|
// Sync guidance bootstrap file (moflo-bootstrap.md)
|
|
124
|
-
|
|
125
|
-
const
|
|
156
|
+
const shippedBootstrap = resolve(projectRoot, 'node_modules/moflo/.claude/guidance/shipped/agent-bootstrap.md');
|
|
157
|
+
const legacyBootstrap = resolve(projectRoot, 'node_modules/moflo/.claude/guidance/agent-bootstrap.md');
|
|
158
|
+
const bootstrapSrc = existsSync(shippedBootstrap) ? shippedBootstrap : legacyBootstrap;
|
|
126
159
|
const guidanceDir = resolve(projectRoot, '.claude/guidance');
|
|
127
160
|
const bootstrapDest = resolve(guidanceDir, 'moflo-bootstrap.md');
|
|
128
161
|
if (existsSync(bootstrapSrc)) {
|
|
@@ -131,13 +164,28 @@ try {
|
|
|
131
164
|
const header = '<!-- AUTO-GENERATED by moflo session-start. Do not edit — changes will be overwritten. -->\n<!-- Source: node_modules/moflo/.claude/guidance/agent-bootstrap.md -->\n\n';
|
|
132
165
|
const content = readFileSync(bootstrapSrc, 'utf-8');
|
|
133
166
|
writeFileSync(bootstrapDest, header + content);
|
|
167
|
+
currentManifest.push('.claude/guidance/moflo-bootstrap.md');
|
|
134
168
|
} catch { /* non-fatal */ }
|
|
135
169
|
}
|
|
136
170
|
|
|
137
|
-
//
|
|
171
|
+
// ── Clean up files we installed previously but no longer ship ──
|
|
172
|
+
// Only remove files that are in the OLD manifest but NOT in the new one.
|
|
173
|
+
// This ensures we never delete user-created or runtime-generated files.
|
|
174
|
+
if (previousManifest.length > 0) {
|
|
175
|
+
const currentSet = new Set(currentManifest);
|
|
176
|
+
for (const rel of previousManifest) {
|
|
177
|
+
if (!currentSet.has(rel)) {
|
|
178
|
+
const abs = resolve(projectRoot, rel);
|
|
179
|
+
try { if (existsSync(abs)) unlinkSync(abs); } catch { /* non-fatal */ }
|
|
180
|
+
}
|
|
181
|
+
}
|
|
182
|
+
}
|
|
183
|
+
|
|
184
|
+
// Write updated manifest + version stamp
|
|
138
185
|
try {
|
|
139
186
|
const cfDir = resolve(projectRoot, '.claude-flow');
|
|
140
187
|
if (!existsSync(cfDir)) mkdirSync(cfDir, { recursive: true });
|
|
188
|
+
writeFileSync(manifestPath, JSON.stringify(currentManifest, null, 2));
|
|
141
189
|
writeFileSync(versionStampPath, installedVersion);
|
|
142
190
|
} catch {}
|
|
143
191
|
}
|
|
@@ -149,7 +197,9 @@ try {
|
|
|
149
197
|
// ── 3b. Ensure guidance bootstrap file exists (even without version change) ──
|
|
150
198
|
// Subagents need this file on disk for direct reads without memory search.
|
|
151
199
|
try {
|
|
152
|
-
const
|
|
200
|
+
const shippedBs = resolve(projectRoot, 'node_modules/moflo/.claude/guidance/shipped/agent-bootstrap.md');
|
|
201
|
+
const legacyBs = resolve(projectRoot, 'node_modules/moflo/.claude/guidance/agent-bootstrap.md');
|
|
202
|
+
const bootstrapSrc = existsSync(shippedBs) ? shippedBs : legacyBs;
|
|
153
203
|
const guidanceDir = resolve(projectRoot, '.claude/guidance');
|
|
154
204
|
const bootstrapDest = resolve(guidanceDir, 'moflo-bootstrap.md');
|
|
155
205
|
if (existsSync(bootstrapSrc) && !existsSync(bootstrapDest)) {
|
package/bin/setup-project.mjs
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
#!/usr/bin/env node
|
|
1
|
+
#!/usr/bin/env node
|
|
2
2
|
/**
|
|
3
3
|
* MoFlo Project Setup
|
|
4
4
|
*
|
|
@@ -40,7 +40,7 @@ Your first tool call for every new user prompt MUST be a memory search. Do this
|
|
|
40
40
|
|
|
41
41
|
WHY: Memory contains curated solutions, patterns, and architectural context from previous work. Without it, you will miss existing solutions, repeat mistakes that were already solved, and waste time re-discovering what is already known. Memory search is faster than file scanning.
|
|
42
42
|
|
|
43
|
-
HOW: Use ToolSearch to load \`
|
|
43
|
+
HOW: Use ToolSearch to load \`mcp__moflo__memory_search\`, then call it with a query describing your task. If MCP is unavailable, use:
|
|
44
44
|
\`node bin/semantic-search.mjs "[task description]" --namespace guidance\`
|
|
45
45
|
|
|
46
46
|
### Namespaces to search:
|
|
@@ -59,10 +59,10 @@ For **codebase navigation** (finding where a type/service/component lives), also
|
|
|
59
59
|
|
|
60
60
|
### Primary: MCP Tools (preferred)
|
|
61
61
|
\`\`\`
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
62
|
+
mcp__moflo__memory_search — query, namespace
|
|
63
|
+
mcp__moflo__memory_store — key, value, namespace
|
|
64
|
+
mcp__moflo__memory_retrieve — key, namespace
|
|
65
|
+
mcp__moflo__memory_list — namespace, limit
|
|
66
66
|
\`\`\`
|
|
67
67
|
Load via ToolSearch first: \`+claude-flow memory\`
|
|
68
68
|
|
|
@@ -78,9 +78,9 @@ npx flo-codemap --force # Regenerate code-map
|
|
|
78
78
|
|
|
79
79
|
| Content Type | Destination | How to Write |
|
|
80
80
|
|-------------|-------------|--------------|
|
|
81
|
-
| Debugging lessons (bug found, root cause, fix) | Memory DB — \`patterns\` namespace | \`
|
|
82
|
-
| Architectural decisions (chose X over Y, why) | Memory DB — \`decisions\` namespace | \`
|
|
83
|
-
| Learned patterns (task succeeded/failed, what worked) | Memory DB — \`patterns\` namespace | \`
|
|
81
|
+
| Debugging lessons (bug found, root cause, fix) | Memory DB — \`patterns\` namespace | \`mcp__moflo__memory_store\` |
|
|
82
|
+
| Architectural decisions (chose X over Y, why) | Memory DB — \`decisions\` namespace | \`mcp__moflo__memory_store\` |
|
|
83
|
+
| Learned patterns (task succeeded/failed, what worked) | Memory DB — \`patterns\` namespace | \`mcp__moflo__memory_store\` |
|
|
84
84
|
| Coding rules (always/never do X in code) | \`.claude/guidance/\` files | Edit directly |
|
|
85
85
|
| Process/workflow rules (CI, PR, gates) | \`CLAUDE.md\` | Edit directly |
|
|
86
86
|
|
|
@@ -124,7 +124,10 @@ function findProjectRoot() {
|
|
|
124
124
|
}
|
|
125
125
|
|
|
126
126
|
function copyBootstrap(projectRoot) {
|
|
127
|
-
const
|
|
127
|
+
const shippedSource = join(mofloRoot, '.claude', 'guidance', 'shipped', 'agent-bootstrap.md');
|
|
128
|
+
const source = existsSync(shippedSource)
|
|
129
|
+
? shippedSource
|
|
130
|
+
: join(mofloRoot, '.claude', 'guidance', 'agent-bootstrap.md');
|
|
128
131
|
const targetDir = join(projectRoot, '.claude', 'guidance');
|
|
129
132
|
const target = join(targetDir, 'moflo-bootstrap.md');
|
|
130
133
|
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "moflo",
|
|
3
|
-
"version": "4.8.
|
|
3
|
+
"version": "4.8.11",
|
|
4
4
|
"description": "MoFlo — AI agent orchestration for Claude Code. Forked from ruflo/claude-flow with patches applied to source, plus feature-level orchestration.",
|
|
5
5
|
"main": "dist/index.js",
|
|
6
6
|
"type": "module",
|
|
@@ -11,6 +11,7 @@
|
|
|
11
11
|
"flo-search": "bin/semantic-search.mjs",
|
|
12
12
|
"flo-embeddings": "bin/build-embeddings.mjs",
|
|
13
13
|
"flo-index": "bin/index-guidance.mjs",
|
|
14
|
+
"flo-testmap": "bin/index-tests.mjs",
|
|
14
15
|
"flo-learn": ".claude/helpers/learning-service.mjs",
|
|
15
16
|
"moflo": "bin/cli.js",
|
|
16
17
|
"claude-flow": "bin/cli.js"
|
|
@@ -40,6 +41,7 @@
|
|
|
40
41
|
"src/@claude-flow/memory/package.json",
|
|
41
42
|
".claude-plugin/**",
|
|
42
43
|
".claude/**",
|
|
44
|
+
"!.claude/guidance/internal/**",
|
|
43
45
|
"!.claude/**/*.db",
|
|
44
46
|
"!.claude/**/*.map",
|
|
45
47
|
"README.md",
|
|
@@ -83,7 +85,7 @@
|
|
|
83
85
|
"@types/bcrypt": "^5.0.2",
|
|
84
86
|
"@types/node": "^20.19.37",
|
|
85
87
|
"eslint": "^8.0.0",
|
|
86
|
-
"moflo": "^4.8.
|
|
88
|
+
"moflo": "^4.8.9",
|
|
87
89
|
"tsx": "^4.21.0",
|
|
88
90
|
"typescript": "^5.9.3",
|
|
89
91
|
"vitest": "^4.0.0"
|
|
@@ -433,7 +433,7 @@ MoFlo uses a SQLite database (via sql.js/WASM — no native deps) to store three
|
|
|
433
433
|
|
|
434
434
|
When `flo init` runs, it appends a workflow section to your CLAUDE.md that teaches Claude:
|
|
435
435
|
- Always search memory before Glob/Grep/Read (enforced by gates)
|
|
436
|
-
- Use `
|
|
436
|
+
- Use `mcp__moflo__memory_search` for knowledge retrieval
|
|
437
437
|
- Use `/flo <issue>` (or `/fl`) for issue execution
|
|
438
438
|
- Store learnings after task completion
|
|
439
439
|
|
|
@@ -1,175 +1,175 @@
|
|
|
1
|
-
#!/usr/bin/env node
|
|
2
|
-
/**
|
|
3
|
-
* @claude-flow/cli - CLI Entry Point
|
|
4
|
-
*
|
|
5
|
-
* Claude Flow V3 Command Line Interface
|
|
6
|
-
*
|
|
7
|
-
* Auto-detects MCP mode when stdin is piped and no args provided.
|
|
8
|
-
* This allows: echo '{"jsonrpc":"2.0",...}' | npx @claude-flow/cli
|
|
9
|
-
*/
|
|
10
|
-
|
|
11
|
-
import { randomUUID } from 'crypto';
|
|
12
|
-
|
|
13
|
-
// Check if we should run in MCP server mode
|
|
14
|
-
// Conditions:
|
|
15
|
-
// 1. stdin is being piped AND no CLI arguments provided (auto-detect)
|
|
16
|
-
// 2. stdin is being piped AND args are "mcp start" (explicit, e.g. npx claude-flow@alpha mcp start)
|
|
17
|
-
const cliArgs = process.argv.slice(2);
|
|
18
|
-
const isExplicitMCP = cliArgs.length >= 1 && cliArgs[0] === 'mcp' && (cliArgs.length === 1 || cliArgs[1] === 'start');
|
|
19
|
-
const isMCPMode = !process.stdin.isTTY && (process.argv.length === 2 || isExplicitMCP);
|
|
20
|
-
|
|
21
|
-
if (isMCPMode) {
|
|
22
|
-
// Run MCP server mode
|
|
23
|
-
const { listMCPTools, callMCPTool, hasTool } = await import('../dist/src/mcp-client.js');
|
|
24
|
-
|
|
25
|
-
// Read version from the root moflo package.json dynamically
|
|
26
|
-
const { readFileSync } = await import('fs');
|
|
27
|
-
const { dirname: _dirname, join: _join } = await import('path');
|
|
28
|
-
const { fileURLToPath: _fileURLToPath } = await import('url');
|
|
29
|
-
let VERSION = '4.6.2';
|
|
30
|
-
try {
|
|
31
|
-
const _thisDir = _dirname(_fileURLToPath(import.meta.url));
|
|
32
|
-
// Walk up to find root moflo package.json
|
|
33
|
-
let _dir = _thisDir;
|
|
34
|
-
for (;;) {
|
|
35
|
-
const _candidate = _join(_dir, 'package.json');
|
|
36
|
-
try {
|
|
37
|
-
const _pkg = JSON.parse(readFileSync(_candidate, 'utf8'));
|
|
38
|
-
if (_pkg.name === 'moflo' && _pkg.version) { VERSION = _pkg.version; break; }
|
|
39
|
-
} catch {}
|
|
40
|
-
const _parent = _dirname(_dir);
|
|
41
|
-
if (_parent === _dir) break;
|
|
42
|
-
_dir = _parent;
|
|
43
|
-
}
|
|
44
|
-
} catch {}
|
|
45
|
-
const sessionId = `mcp-${Date.now()}-${randomUUID().slice(0, 8)}`;
|
|
46
|
-
|
|
47
|
-
console.error(
|
|
48
|
-
`[${new Date().toISOString()}] INFO [claude-flow-mcp] (${sessionId}) Starting in stdio mode`
|
|
49
|
-
);
|
|
50
|
-
|
|
51
|
-
let buffer = '';
|
|
52
|
-
process.stdin.setEncoding('utf8');
|
|
53
|
-
process.stdin.on('data', async (chunk) => {
|
|
54
|
-
buffer += chunk;
|
|
55
|
-
let lines = buffer.split('\n');
|
|
56
|
-
buffer = lines.pop() || '';
|
|
57
|
-
|
|
58
|
-
for (const line of lines) {
|
|
59
|
-
if (line.trim()) {
|
|
60
|
-
try {
|
|
61
|
-
const message = JSON.parse(line);
|
|
62
|
-
const response = await handleMessage(message);
|
|
63
|
-
if (response) {
|
|
64
|
-
console.log(JSON.stringify(response));
|
|
65
|
-
}
|
|
66
|
-
} catch (error) {
|
|
67
|
-
console.log(JSON.stringify({
|
|
68
|
-
jsonrpc: '2.0',
|
|
69
|
-
id: null,
|
|
70
|
-
error: { code: -32700, message: 'Parse error' },
|
|
71
|
-
}));
|
|
72
|
-
}
|
|
73
|
-
}
|
|
74
|
-
}
|
|
75
|
-
});
|
|
76
|
-
|
|
77
|
-
process.stdin.on('end', () => {
|
|
78
|
-
process.exit(0);
|
|
79
|
-
});
|
|
80
|
-
|
|
81
|
-
async function handleMessage(message) {
|
|
82
|
-
if (!message.method) {
|
|
83
|
-
return {
|
|
84
|
-
jsonrpc: '2.0',
|
|
85
|
-
id: message.id,
|
|
86
|
-
error: { code: -32600, message: 'Invalid Request: missing method' },
|
|
87
|
-
};
|
|
88
|
-
}
|
|
89
|
-
|
|
90
|
-
const params = message.params || {};
|
|
91
|
-
|
|
92
|
-
switch (message.method) {
|
|
93
|
-
case 'initialize':
|
|
94
|
-
return {
|
|
95
|
-
jsonrpc: '2.0',
|
|
96
|
-
id: message.id,
|
|
97
|
-
result: {
|
|
98
|
-
protocolVersion: '2024-11-05',
|
|
99
|
-
serverInfo: { name: '
|
|
100
|
-
capabilities: {
|
|
101
|
-
tools: { listChanged: true },
|
|
102
|
-
resources: { subscribe: true, listChanged: true },
|
|
103
|
-
},
|
|
104
|
-
},
|
|
105
|
-
};
|
|
106
|
-
|
|
107
|
-
case 'tools/list': {
|
|
108
|
-
const tools = listMCPTools();
|
|
109
|
-
return {
|
|
110
|
-
jsonrpc: '2.0',
|
|
111
|
-
id: message.id,
|
|
112
|
-
result: {
|
|
113
|
-
tools: tools.map(tool => ({
|
|
114
|
-
name: tool.name,
|
|
115
|
-
description: tool.description,
|
|
116
|
-
inputSchema: tool.inputSchema,
|
|
117
|
-
})),
|
|
118
|
-
},
|
|
119
|
-
};
|
|
120
|
-
}
|
|
121
|
-
|
|
122
|
-
case 'tools/call': {
|
|
123
|
-
const toolName = params.name;
|
|
124
|
-
const toolParams = params.arguments || {};
|
|
125
|
-
|
|
126
|
-
if (!hasTool(toolName)) {
|
|
127
|
-
return {
|
|
128
|
-
jsonrpc: '2.0',
|
|
129
|
-
id: message.id,
|
|
130
|
-
error: { code: -32601, message: `Tool not found: ${toolName}` },
|
|
131
|
-
};
|
|
132
|
-
}
|
|
133
|
-
|
|
134
|
-
try {
|
|
135
|
-
const result = await callMCPTool(toolName, toolParams, { sessionId });
|
|
136
|
-
return {
|
|
137
|
-
jsonrpc: '2.0',
|
|
138
|
-
id: message.id,
|
|
139
|
-
result: { content: [{ type: 'text', text: JSON.stringify(result, null, 2) }] },
|
|
140
|
-
};
|
|
141
|
-
} catch (error) {
|
|
142
|
-
return {
|
|
143
|
-
jsonrpc: '2.0',
|
|
144
|
-
id: message.id,
|
|
145
|
-
error: {
|
|
146
|
-
code: -32603,
|
|
147
|
-
message: error instanceof Error ? error.message : 'Tool execution failed',
|
|
148
|
-
},
|
|
149
|
-
};
|
|
150
|
-
}
|
|
151
|
-
}
|
|
152
|
-
|
|
153
|
-
case 'notifications/initialized':
|
|
154
|
-
return null;
|
|
155
|
-
|
|
156
|
-
case 'ping':
|
|
157
|
-
return { jsonrpc: '2.0', id: message.id, result: {} };
|
|
158
|
-
|
|
159
|
-
default:
|
|
160
|
-
return {
|
|
161
|
-
jsonrpc: '2.0',
|
|
162
|
-
id: message.id,
|
|
163
|
-
error: { code: -32601, message: `Method not found: ${message.method}` },
|
|
164
|
-
};
|
|
165
|
-
}
|
|
166
|
-
}
|
|
167
|
-
} else {
|
|
168
|
-
// Run normal CLI mode
|
|
169
|
-
const { CLI } = await import('../dist/src/index.js');
|
|
170
|
-
const cli = new CLI();
|
|
171
|
-
cli.run().catch((error) => {
|
|
172
|
-
console.error('Fatal error:', error.message);
|
|
173
|
-
process.exit(1);
|
|
174
|
-
});
|
|
175
|
-
}
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
/**
|
|
3
|
+
* @claude-flow/cli - CLI Entry Point
|
|
4
|
+
*
|
|
5
|
+
* Claude Flow V3 Command Line Interface
|
|
6
|
+
*
|
|
7
|
+
* Auto-detects MCP mode when stdin is piped and no args provided.
|
|
8
|
+
* This allows: echo '{"jsonrpc":"2.0",...}' | npx @claude-flow/cli
|
|
9
|
+
*/
|
|
10
|
+
|
|
11
|
+
import { randomUUID } from 'crypto';
|
|
12
|
+
|
|
13
|
+
// Check if we should run in MCP server mode
|
|
14
|
+
// Conditions:
|
|
15
|
+
// 1. stdin is being piped AND no CLI arguments provided (auto-detect)
|
|
16
|
+
// 2. stdin is being piped AND args are "mcp start" (explicit, e.g. npx claude-flow@alpha mcp start)
|
|
17
|
+
const cliArgs = process.argv.slice(2);
|
|
18
|
+
const isExplicitMCP = cliArgs.length >= 1 && cliArgs[0] === 'mcp' && (cliArgs.length === 1 || cliArgs[1] === 'start');
|
|
19
|
+
const isMCPMode = !process.stdin.isTTY && (process.argv.length === 2 || isExplicitMCP);
|
|
20
|
+
|
|
21
|
+
if (isMCPMode) {
|
|
22
|
+
// Run MCP server mode
|
|
23
|
+
const { listMCPTools, callMCPTool, hasTool } = await import('../dist/src/mcp-client.js');
|
|
24
|
+
|
|
25
|
+
// Read version from the root moflo package.json dynamically
|
|
26
|
+
const { readFileSync } = await import('fs');
|
|
27
|
+
const { dirname: _dirname, join: _join } = await import('path');
|
|
28
|
+
const { fileURLToPath: _fileURLToPath } = await import('url');
|
|
29
|
+
let VERSION = '4.6.2';
|
|
30
|
+
try {
|
|
31
|
+
const _thisDir = _dirname(_fileURLToPath(import.meta.url));
|
|
32
|
+
// Walk up to find root moflo package.json
|
|
33
|
+
let _dir = _thisDir;
|
|
34
|
+
for (;;) {
|
|
35
|
+
const _candidate = _join(_dir, 'package.json');
|
|
36
|
+
try {
|
|
37
|
+
const _pkg = JSON.parse(readFileSync(_candidate, 'utf8'));
|
|
38
|
+
if (_pkg.name === 'moflo' && _pkg.version) { VERSION = _pkg.version; break; }
|
|
39
|
+
} catch {}
|
|
40
|
+
const _parent = _dirname(_dir);
|
|
41
|
+
if (_parent === _dir) break;
|
|
42
|
+
_dir = _parent;
|
|
43
|
+
}
|
|
44
|
+
} catch {}
|
|
45
|
+
const sessionId = `mcp-${Date.now()}-${randomUUID().slice(0, 8)}`;
|
|
46
|
+
|
|
47
|
+
console.error(
|
|
48
|
+
`[${new Date().toISOString()}] INFO [claude-flow-mcp] (${sessionId}) Starting in stdio mode`
|
|
49
|
+
);
|
|
50
|
+
|
|
51
|
+
let buffer = '';
|
|
52
|
+
process.stdin.setEncoding('utf8');
|
|
53
|
+
process.stdin.on('data', async (chunk) => {
|
|
54
|
+
buffer += chunk;
|
|
55
|
+
let lines = buffer.split('\n');
|
|
56
|
+
buffer = lines.pop() || '';
|
|
57
|
+
|
|
58
|
+
for (const line of lines) {
|
|
59
|
+
if (line.trim()) {
|
|
60
|
+
try {
|
|
61
|
+
const message = JSON.parse(line);
|
|
62
|
+
const response = await handleMessage(message);
|
|
63
|
+
if (response) {
|
|
64
|
+
console.log(JSON.stringify(response));
|
|
65
|
+
}
|
|
66
|
+
} catch (error) {
|
|
67
|
+
console.log(JSON.stringify({
|
|
68
|
+
jsonrpc: '2.0',
|
|
69
|
+
id: null,
|
|
70
|
+
error: { code: -32700, message: 'Parse error' },
|
|
71
|
+
}));
|
|
72
|
+
}
|
|
73
|
+
}
|
|
74
|
+
}
|
|
75
|
+
});
|
|
76
|
+
|
|
77
|
+
process.stdin.on('end', () => {
|
|
78
|
+
process.exit(0);
|
|
79
|
+
});
|
|
80
|
+
|
|
81
|
+
async function handleMessage(message) {
|
|
82
|
+
if (!message.method) {
|
|
83
|
+
return {
|
|
84
|
+
jsonrpc: '2.0',
|
|
85
|
+
id: message.id,
|
|
86
|
+
error: { code: -32600, message: 'Invalid Request: missing method' },
|
|
87
|
+
};
|
|
88
|
+
}
|
|
89
|
+
|
|
90
|
+
const params = message.params || {};
|
|
91
|
+
|
|
92
|
+
switch (message.method) {
|
|
93
|
+
case 'initialize':
|
|
94
|
+
return {
|
|
95
|
+
jsonrpc: '2.0',
|
|
96
|
+
id: message.id,
|
|
97
|
+
result: {
|
|
98
|
+
protocolVersion: '2024-11-05',
|
|
99
|
+
serverInfo: { name: 'moflo', version: VERSION },
|
|
100
|
+
capabilities: {
|
|
101
|
+
tools: { listChanged: true },
|
|
102
|
+
resources: { subscribe: true, listChanged: true },
|
|
103
|
+
},
|
|
104
|
+
},
|
|
105
|
+
};
|
|
106
|
+
|
|
107
|
+
case 'tools/list': {
|
|
108
|
+
const tools = listMCPTools();
|
|
109
|
+
return {
|
|
110
|
+
jsonrpc: '2.0',
|
|
111
|
+
id: message.id,
|
|
112
|
+
result: {
|
|
113
|
+
tools: tools.map(tool => ({
|
|
114
|
+
name: tool.name,
|
|
115
|
+
description: tool.description,
|
|
116
|
+
inputSchema: tool.inputSchema,
|
|
117
|
+
})),
|
|
118
|
+
},
|
|
119
|
+
};
|
|
120
|
+
}
|
|
121
|
+
|
|
122
|
+
case 'tools/call': {
|
|
123
|
+
const toolName = params.name;
|
|
124
|
+
const toolParams = params.arguments || {};
|
|
125
|
+
|
|
126
|
+
if (!hasTool(toolName)) {
|
|
127
|
+
return {
|
|
128
|
+
jsonrpc: '2.0',
|
|
129
|
+
id: message.id,
|
|
130
|
+
error: { code: -32601, message: `Tool not found: ${toolName}` },
|
|
131
|
+
};
|
|
132
|
+
}
|
|
133
|
+
|
|
134
|
+
try {
|
|
135
|
+
const result = await callMCPTool(toolName, toolParams, { sessionId });
|
|
136
|
+
return {
|
|
137
|
+
jsonrpc: '2.0',
|
|
138
|
+
id: message.id,
|
|
139
|
+
result: { content: [{ type: 'text', text: JSON.stringify(result, null, 2) }] },
|
|
140
|
+
};
|
|
141
|
+
} catch (error) {
|
|
142
|
+
return {
|
|
143
|
+
jsonrpc: '2.0',
|
|
144
|
+
id: message.id,
|
|
145
|
+
error: {
|
|
146
|
+
code: -32603,
|
|
147
|
+
message: error instanceof Error ? error.message : 'Tool execution failed',
|
|
148
|
+
},
|
|
149
|
+
};
|
|
150
|
+
}
|
|
151
|
+
}
|
|
152
|
+
|
|
153
|
+
case 'notifications/initialized':
|
|
154
|
+
return null;
|
|
155
|
+
|
|
156
|
+
case 'ping':
|
|
157
|
+
return { jsonrpc: '2.0', id: message.id, result: {} };
|
|
158
|
+
|
|
159
|
+
default:
|
|
160
|
+
return {
|
|
161
|
+
jsonrpc: '2.0',
|
|
162
|
+
id: message.id,
|
|
163
|
+
error: { code: -32601, message: `Method not found: ${message.method}` },
|
|
164
|
+
};
|
|
165
|
+
}
|
|
166
|
+
}
|
|
167
|
+
} else {
|
|
168
|
+
// Run normal CLI mode
|
|
169
|
+
const { CLI } = await import('../dist/src/index.js');
|
|
170
|
+
const cli = new CLI();
|
|
171
|
+
cli.run().catch((error) => {
|
|
172
|
+
console.error('Fatal error:', error.message);
|
|
173
|
+
process.exit(1);
|
|
174
|
+
});
|
|
175
|
+
}
|