@claude-flow/cli 3.0.0-alpha.2 → 3.0.0-alpha.7
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.agentic-flow/intelligence.json +4 -3
- package/.claude-flow/agents/store.json +16 -0
- package/.claude-flow/daemon-state.json +123 -0
- package/.claude-flow/hive-mind/state.json +51 -0
- package/.claude-flow/metrics/codebase-map.json +11 -0
- package/.claude-flow/metrics/consolidation.json +6 -0
- package/.claude-flow/metrics/performance.json +3 -3
- package/.claude-flow/metrics/security-audit.json +10 -0
- package/.claude-flow/metrics/task-metrics.json +3 -3
- package/.claude-flow/metrics/test-gaps.json +6 -0
- package/agents/architect.yaml +11 -0
- package/agents/coder.yaml +11 -0
- package/agents/reviewer.yaml +10 -0
- package/agents/security-architect.yaml +10 -0
- package/agents/tester.yaml +10 -0
- package/bin/cli.js +0 -0
- package/dist/src/commands/agent.d.ts.map +1 -1
- package/dist/src/commands/agent.js +43 -27
- package/dist/src/commands/agent.js.map +1 -1
- package/dist/src/commands/config.js +2 -2
- package/dist/src/commands/config.js.map +1 -1
- package/dist/src/commands/daemon.d.ts +8 -0
- package/dist/src/commands/daemon.d.ts.map +1 -0
- package/dist/src/commands/daemon.js +351 -0
- package/dist/src/commands/daemon.js.map +1 -0
- package/dist/src/commands/hive-mind.d.ts.map +1 -1
- package/dist/src/commands/hive-mind.js +252 -35
- package/dist/src/commands/hive-mind.js.map +1 -1
- package/dist/src/commands/hooks.js +1 -1
- package/dist/src/commands/hooks.js.map +1 -1
- package/dist/src/commands/index.d.ts +1 -0
- package/dist/src/commands/index.d.ts.map +1 -1
- package/dist/src/commands/index.js +4 -1
- package/dist/src/commands/index.js.map +1 -1
- package/dist/src/commands/mcp.js +1 -1
- package/dist/src/commands/mcp.js.map +1 -1
- package/dist/src/commands/memory.d.ts.map +1 -1
- package/dist/src/commands/memory.js +234 -168
- package/dist/src/commands/memory.js.map +1 -1
- package/dist/src/commands/migrate.js +1 -1
- package/dist/src/commands/migrate.js.map +1 -1
- package/dist/src/commands/process.d.ts.map +1 -1
- package/dist/src/commands/process.js +95 -20
- package/dist/src/commands/process.js.map +1 -1
- package/dist/src/commands/start.js +2 -2
- package/dist/src/commands/start.js.map +1 -1
- package/dist/src/commands/status.d.ts.map +1 -1
- package/dist/src/commands/status.js +26 -2
- package/dist/src/commands/status.js.map +1 -1
- package/dist/src/commands/swarm.js +6 -6
- package/dist/src/commands/swarm.js.map +1 -1
- package/dist/src/index.d.ts +1 -1
- package/dist/src/index.d.ts.map +1 -1
- package/dist/src/index.js +23 -3
- package/dist/src/index.js.map +1 -1
- package/dist/src/init/executor.d.ts.map +1 -1
- package/dist/src/init/executor.js +5 -0
- package/dist/src/init/executor.js.map +1 -1
- package/dist/src/init/settings-generator.d.ts.map +1 -1
- package/dist/src/init/settings-generator.js +22 -12
- package/dist/src/init/settings-generator.js.map +1 -1
- package/dist/src/mcp-client.d.ts.map +1 -1
- package/dist/src/mcp-client.js +15 -1
- package/dist/src/mcp-client.js.map +1 -1
- package/dist/src/mcp-server.d.ts.map +1 -1
- package/dist/src/mcp-server.js +5 -0
- package/dist/src/mcp-server.js.map +1 -1
- package/dist/src/mcp-tools/agent-tools.d.ts +1 -1
- package/dist/src/mcp-tools/agent-tools.d.ts.map +1 -1
- package/dist/src/mcp-tools/agent-tools.js +350 -14
- package/dist/src/mcp-tools/agent-tools.js.map +1 -1
- package/dist/src/mcp-tools/config-tools.d.ts +1 -1
- package/dist/src/mcp-tools/config-tools.d.ts.map +1 -1
- package/dist/src/mcp-tools/config-tools.js +262 -15
- package/dist/src/mcp-tools/config-tools.js.map +1 -1
- package/dist/src/mcp-tools/hive-mind-tools.d.ts +8 -0
- package/dist/src/mcp-tools/hive-mind-tools.d.ts.map +1 -0
- package/dist/src/mcp-tools/hive-mind-tools.js +447 -0
- package/dist/src/mcp-tools/hive-mind-tools.js.map +1 -0
- package/dist/src/mcp-tools/hooks-tools.d.ts.map +1 -1
- package/dist/src/mcp-tools/hooks-tools.js +80 -15
- package/dist/src/mcp-tools/hooks-tools.js.map +1 -1
- package/dist/src/mcp-tools/index.d.ts +4 -0
- package/dist/src/mcp-tools/index.d.ts.map +1 -1
- package/dist/src/mcp-tools/index.js +4 -0
- package/dist/src/mcp-tools/index.js.map +1 -1
- package/dist/src/mcp-tools/memory-tools.d.ts +1 -1
- package/dist/src/mcp-tools/memory-tools.d.ts.map +1 -1
- package/dist/src/mcp-tools/memory-tools.js +157 -9
- package/dist/src/mcp-tools/memory-tools.js.map +1 -1
- package/dist/src/mcp-tools/session-tools.d.ts +8 -0
- package/dist/src/mcp-tools/session-tools.d.ts.map +1 -0
- package/dist/src/mcp-tools/session-tools.js +315 -0
- package/dist/src/mcp-tools/session-tools.js.map +1 -0
- package/dist/src/mcp-tools/swarm-tools.d.ts.map +1 -1
- package/dist/src/mcp-tools/swarm-tools.js +37 -2
- package/dist/src/mcp-tools/swarm-tools.js.map +1 -1
- package/dist/src/mcp-tools/task-tools.d.ts +8 -0
- package/dist/src/mcp-tools/task-tools.d.ts.map +1 -0
- package/dist/src/mcp-tools/task-tools.js +302 -0
- package/dist/src/mcp-tools/task-tools.js.map +1 -0
- package/dist/src/mcp-tools/workflow-tools.d.ts +8 -0
- package/dist/src/mcp-tools/workflow-tools.d.ts.map +1 -0
- package/dist/src/mcp-tools/workflow-tools.js +481 -0
- package/dist/src/mcp-tools/workflow-tools.js.map +1 -0
- package/dist/src/services/index.d.ts +7 -0
- package/dist/src/services/index.d.ts.map +1 -0
- package/dist/src/services/index.js +6 -0
- package/dist/src/services/index.js.map +1 -0
- package/dist/src/services/worker-daemon.d.ts +126 -0
- package/dist/src/services/worker-daemon.d.ts.map +1 -0
- package/dist/src/services/worker-daemon.js +464 -0
- package/dist/src/services/worker-daemon.js.map +1 -0
- package/dist/tsconfig.tsbuildinfo +1 -1
- package/package.json +1 -1
- package/src/commands/agent.ts +43 -29
- package/src/commands/config.ts +2 -2
- package/src/commands/daemon.ts +395 -0
- package/src/commands/hive-mind.ts +229 -63
- package/src/commands/hooks.ts +1 -1
- package/src/commands/index.ts +4 -1
- package/src/commands/mcp.ts +1 -1
- package/src/commands/memory.ts +279 -181
- package/src/commands/migrate.ts +1 -1
- package/src/commands/process.ts +98 -20
- package/src/commands/start.ts +2 -2
- package/src/commands/status.ts +33 -2
- package/src/commands/swarm.ts +6 -6
- package/src/index.ts +23 -3
- package/src/init/executor.ts +6 -0
- package/src/init/settings-generator.ts +22 -12
- package/src/mcp-client.ts +15 -1
- package/src/mcp-server.ts +6 -0
- package/src/mcp-tools/agent-tools.ts +388 -14
- package/src/mcp-tools/config-tools.ts +297 -15
- package/src/mcp-tools/hive-mind-tools.ts +521 -0
- package/src/mcp-tools/hooks-tools.ts +84 -15
- package/src/mcp-tools/index.ts +4 -0
- package/src/mcp-tools/memory-tools.ts +190 -9
- package/src/mcp-tools/session-tools.ts +359 -0
- package/src/mcp-tools/swarm-tools.ts +38 -2
- package/src/mcp-tools/task-tools.ts +347 -0
- package/src/mcp-tools/workflow-tools.ts +573 -0
- package/src/services/index.ts +15 -0
- package/src/services/worker-daemon.ts +594 -0
|
@@ -3,9 +3,11 @@
|
|
|
3
3
|
* Provides intelligent hooks functionality via MCP protocol
|
|
4
4
|
*/
|
|
5
5
|
|
|
6
|
+
import { mkdirSync, writeFileSync, existsSync } from 'fs';
|
|
7
|
+
import { join, resolve } from 'path';
|
|
6
8
|
import type { MCPTool } from './types.js';
|
|
7
9
|
|
|
8
|
-
//
|
|
10
|
+
// Agent routing configuration - maps file types to recommended agents
|
|
9
11
|
const AGENT_PATTERNS: Record<string, string[]> = {
|
|
10
12
|
'.ts': ['coder', 'architect', 'tester'],
|
|
11
13
|
'.tsx': ['coder', 'architect', 'reviewer'],
|
|
@@ -534,7 +536,7 @@ export const hooksPretrain: MCPTool = {
|
|
|
534
536
|
const depth = (params.depth as string) || 'medium';
|
|
535
537
|
const startTime = Date.now();
|
|
536
538
|
|
|
537
|
-
//
|
|
539
|
+
// Scale analysis results by depth level
|
|
538
540
|
const multiplier = depth === 'deep' ? 3 : depth === 'shallow' ? 1 : 2;
|
|
539
541
|
|
|
540
542
|
return {
|
|
@@ -568,19 +570,21 @@ export const hooksBuildAgents: MCPTool = {
|
|
|
568
570
|
outputDir: { type: 'string', description: 'Output directory for configs' },
|
|
569
571
|
focus: { type: 'string', description: 'Focus area (v3-implementation, security, performance, all)' },
|
|
570
572
|
format: { type: 'string', description: 'Config format (yaml, json)' },
|
|
573
|
+
persist: { type: 'boolean', description: 'Write configs to disk' },
|
|
571
574
|
},
|
|
572
575
|
},
|
|
573
576
|
handler: async (params: Record<string, unknown>) => {
|
|
574
|
-
const outputDir = (params.outputDir as string) || './agents';
|
|
577
|
+
const outputDir = resolve((params.outputDir as string) || './agents');
|
|
575
578
|
const focus = (params.focus as string) || 'all';
|
|
576
579
|
const format = (params.format as string) || 'yaml';
|
|
580
|
+
const persist = params.persist !== false; // Default to true
|
|
577
581
|
|
|
578
582
|
const agents = [
|
|
579
|
-
{ type: 'coder', configFile:
|
|
580
|
-
{ type: 'architect', configFile:
|
|
581
|
-
{ type: 'tester', configFile:
|
|
582
|
-
{ type: 'security-architect', configFile:
|
|
583
|
-
{ type: 'reviewer', configFile:
|
|
583
|
+
{ type: 'coder', configFile: join(outputDir, `coder.${format}`), capabilities: ['code-generation', 'refactoring', 'debugging'], optimizations: ['flash-attention', 'token-reduction'] },
|
|
584
|
+
{ type: 'architect', configFile: join(outputDir, `architect.${format}`), capabilities: ['system-design', 'api-design', 'documentation'], optimizations: ['context-caching', 'memory-persistence'] },
|
|
585
|
+
{ type: 'tester', configFile: join(outputDir, `tester.${format}`), capabilities: ['unit-testing', 'integration-testing', 'coverage'], optimizations: ['parallel-execution'] },
|
|
586
|
+
{ type: 'security-architect', configFile: join(outputDir, `security-architect.${format}`), capabilities: ['threat-modeling', 'vulnerability-analysis', 'security-review'], optimizations: ['pattern-matching'] },
|
|
587
|
+
{ type: 'reviewer', configFile: join(outputDir, `reviewer.${format}`), capabilities: ['code-review', 'quality-analysis', 'best-practices'], optimizations: ['incremental-analysis'] },
|
|
584
588
|
];
|
|
585
589
|
|
|
586
590
|
const filteredAgents = focus === 'all' ? agents :
|
|
@@ -588,9 +592,35 @@ export const hooksBuildAgents: MCPTool = {
|
|
|
588
592
|
focus === 'performance' ? agents.filter(a => ['coder', 'tester'].includes(a.type)) :
|
|
589
593
|
agents;
|
|
590
594
|
|
|
595
|
+
// Persist configs to disk if requested
|
|
596
|
+
if (persist) {
|
|
597
|
+
// Ensure output directory exists
|
|
598
|
+
if (!existsSync(outputDir)) {
|
|
599
|
+
mkdirSync(outputDir, { recursive: true });
|
|
600
|
+
}
|
|
601
|
+
|
|
602
|
+
// Write each agent config
|
|
603
|
+
for (const agent of filteredAgents) {
|
|
604
|
+
const config = {
|
|
605
|
+
type: agent.type,
|
|
606
|
+
capabilities: agent.capabilities,
|
|
607
|
+
optimizations: agent.optimizations,
|
|
608
|
+
version: '3.0.0',
|
|
609
|
+
createdAt: new Date().toISOString(),
|
|
610
|
+
};
|
|
611
|
+
|
|
612
|
+
const content = format === 'json'
|
|
613
|
+
? JSON.stringify(config, null, 2)
|
|
614
|
+
: `# ${agent.type} agent configuration\ntype: ${agent.type}\nversion: "3.0.0"\ncapabilities:\n${agent.capabilities.map(c => ` - ${c}`).join('\n')}\noptimizations:\n${agent.optimizations.map(o => ` - ${o}`).join('\n')}\ncreatedAt: "${config.createdAt}"\n`;
|
|
615
|
+
|
|
616
|
+
writeFileSync(agent.configFile, content, 'utf-8');
|
|
617
|
+
}
|
|
618
|
+
}
|
|
619
|
+
|
|
591
620
|
return {
|
|
592
621
|
outputDir,
|
|
593
622
|
focus,
|
|
623
|
+
persisted: persist,
|
|
594
624
|
agents: filteredAgents,
|
|
595
625
|
stats: {
|
|
596
626
|
configsGenerated: filteredAgents.length,
|
|
@@ -653,20 +683,42 @@ export const hooksTransfer: MCPTool = {
|
|
|
653
683
|
},
|
|
654
684
|
};
|
|
655
685
|
|
|
656
|
-
// Session start hook
|
|
686
|
+
// Session start hook - auto-starts daemon
|
|
657
687
|
export const hooksSessionStart: MCPTool = {
|
|
658
688
|
name: 'hooks/session-start',
|
|
659
|
-
description: 'Initialize a new session',
|
|
689
|
+
description: 'Initialize a new session and auto-start daemon',
|
|
660
690
|
inputSchema: {
|
|
661
691
|
type: 'object',
|
|
662
692
|
properties: {
|
|
663
693
|
sessionId: { type: 'string', description: 'Optional session ID' },
|
|
664
694
|
restoreLatest: { type: 'boolean', description: 'Restore latest session state' },
|
|
695
|
+
startDaemon: { type: 'boolean', description: 'Auto-start worker daemon (default: true)' },
|
|
665
696
|
},
|
|
666
697
|
},
|
|
667
698
|
handler: async (params: Record<string, unknown>) => {
|
|
668
699
|
const sessionId = (params.sessionId as string) || `session-${Date.now()}`;
|
|
669
700
|
const restoreLatest = params.restoreLatest as boolean;
|
|
701
|
+
const shouldStartDaemon = params.startDaemon !== false;
|
|
702
|
+
|
|
703
|
+
// Auto-start daemon if enabled
|
|
704
|
+
let daemonStatus: { started: boolean; pid?: number; error?: string } = { started: false };
|
|
705
|
+
if (shouldStartDaemon) {
|
|
706
|
+
try {
|
|
707
|
+
// Dynamic import to avoid circular dependencies
|
|
708
|
+
const { startDaemon } = await import('../services/worker-daemon.js');
|
|
709
|
+
const daemon = await startDaemon(process.cwd());
|
|
710
|
+
const status = daemon.getStatus();
|
|
711
|
+
daemonStatus = {
|
|
712
|
+
started: true,
|
|
713
|
+
pid: status.pid,
|
|
714
|
+
};
|
|
715
|
+
} catch (error) {
|
|
716
|
+
daemonStatus = {
|
|
717
|
+
started: false,
|
|
718
|
+
error: error instanceof Error ? error.message : String(error),
|
|
719
|
+
};
|
|
720
|
+
}
|
|
721
|
+
}
|
|
670
722
|
|
|
671
723
|
return {
|
|
672
724
|
sessionId,
|
|
@@ -676,7 +728,9 @@ export const hooksSessionStart: MCPTool = {
|
|
|
676
728
|
intelligenceEnabled: true,
|
|
677
729
|
hooksEnabled: true,
|
|
678
730
|
memoryPersistence: true,
|
|
731
|
+
daemonEnabled: shouldStartDaemon,
|
|
679
732
|
},
|
|
733
|
+
daemon: daemonStatus,
|
|
680
734
|
previousSession: restoreLatest ? {
|
|
681
735
|
id: `session-${Date.now() - 86400000}`,
|
|
682
736
|
tasksRestored: 3,
|
|
@@ -686,25 +740,40 @@ export const hooksSessionStart: MCPTool = {
|
|
|
686
740
|
},
|
|
687
741
|
};
|
|
688
742
|
|
|
689
|
-
// Session end hook
|
|
743
|
+
// Session end hook - stops daemon
|
|
690
744
|
export const hooksSessionEnd: MCPTool = {
|
|
691
745
|
name: 'hooks/session-end',
|
|
692
|
-
description: 'End current session and persist state',
|
|
746
|
+
description: 'End current session, stop daemon, and persist state',
|
|
693
747
|
inputSchema: {
|
|
694
748
|
type: 'object',
|
|
695
749
|
properties: {
|
|
696
750
|
saveState: { type: 'boolean', description: 'Save session state' },
|
|
697
751
|
exportMetrics: { type: 'boolean', description: 'Export session metrics' },
|
|
752
|
+
stopDaemon: { type: 'boolean', description: 'Stop worker daemon (default: true)' },
|
|
698
753
|
},
|
|
699
754
|
},
|
|
700
755
|
handler: async (params: Record<string, unknown>) => {
|
|
701
756
|
const saveState = params.saveState !== false;
|
|
702
|
-
const
|
|
757
|
+
const shouldStopDaemon = params.stopDaemon !== false;
|
|
758
|
+
const sessionId = `session-${Date.now() - 3600000}`; // Default session (1 hour ago)
|
|
759
|
+
|
|
760
|
+
// Stop daemon if enabled
|
|
761
|
+
let daemonStopped = false;
|
|
762
|
+
if (shouldStopDaemon) {
|
|
763
|
+
try {
|
|
764
|
+
const { stopDaemon } = await import('../services/worker-daemon.js');
|
|
765
|
+
await stopDaemon();
|
|
766
|
+
daemonStopped = true;
|
|
767
|
+
} catch {
|
|
768
|
+
// Daemon may not be running
|
|
769
|
+
}
|
|
770
|
+
}
|
|
703
771
|
|
|
704
772
|
return {
|
|
705
773
|
sessionId,
|
|
706
774
|
duration: 3600000, // 1 hour in ms
|
|
707
775
|
statePath: saveState ? `.claude/sessions/${sessionId}.json` : undefined,
|
|
776
|
+
daemon: { stopped: daemonStopped },
|
|
708
777
|
summary: {
|
|
709
778
|
tasksExecuted: 12,
|
|
710
779
|
tasksSucceeded: 10,
|
|
@@ -1568,7 +1637,7 @@ export const hooksWorkerDispatch: MCPTool = {
|
|
|
1568
1637
|
|
|
1569
1638
|
activeWorkers.set(workerId, worker);
|
|
1570
1639
|
|
|
1571
|
-
//
|
|
1640
|
+
// Update worker progress in background
|
|
1572
1641
|
if (background) {
|
|
1573
1642
|
setTimeout(() => {
|
|
1574
1643
|
const w = activeWorkers.get(workerId);
|
|
@@ -1715,7 +1784,7 @@ export const hooksWorkerDetect: MCPTool = {
|
|
|
1715
1784
|
});
|
|
1716
1785
|
dispatched.push(workerId);
|
|
1717
1786
|
|
|
1718
|
-
//
|
|
1787
|
+
// Mark worker completion after processing
|
|
1719
1788
|
setTimeout(() => {
|
|
1720
1789
|
const w = activeWorkers.get(workerId);
|
|
1721
1790
|
if (w) {
|
package/src/mcp-tools/index.ts
CHANGED
|
@@ -10,3 +10,7 @@ export { swarmTools } from './swarm-tools.js';
|
|
|
10
10
|
export { memoryTools } from './memory-tools.js';
|
|
11
11
|
export { configTools } from './config-tools.js';
|
|
12
12
|
export { hooksTools } from './hooks-tools.js';
|
|
13
|
+
export { taskTools } from './task-tools.js';
|
|
14
|
+
export { sessionTools } from './session-tools.js';
|
|
15
|
+
export { hiveMindTools } from './hive-mind-tools.js';
|
|
16
|
+
export { workflowTools } from './workflow-tools.js';
|
|
@@ -1,15 +1,64 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* Memory MCP Tools for CLI
|
|
3
3
|
*
|
|
4
|
-
* Tool definitions for memory management.
|
|
4
|
+
* Tool definitions for memory management with file-based persistence.
|
|
5
5
|
*/
|
|
6
6
|
|
|
7
|
+
import { existsSync, mkdirSync, readFileSync, writeFileSync } from 'fs';
|
|
8
|
+
import { join, resolve } from 'path';
|
|
7
9
|
import type { MCPTool } from './types.js';
|
|
8
10
|
|
|
11
|
+
// Simple file-based memory store
|
|
12
|
+
interface MemoryEntry {
|
|
13
|
+
key: string;
|
|
14
|
+
value: unknown;
|
|
15
|
+
metadata?: Record<string, unknown>;
|
|
16
|
+
storedAt: string;
|
|
17
|
+
accessCount: number;
|
|
18
|
+
lastAccessed: string;
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
interface MemoryStore {
|
|
22
|
+
entries: Record<string, MemoryEntry>;
|
|
23
|
+
version: string;
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
const MEMORY_DIR = '.claude-flow/memory';
|
|
27
|
+
const MEMORY_FILE = 'store.json';
|
|
28
|
+
|
|
29
|
+
function getMemoryPath(): string {
|
|
30
|
+
return resolve(join(MEMORY_DIR, MEMORY_FILE));
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
function ensureMemoryDir(): void {
|
|
34
|
+
const dir = resolve(MEMORY_DIR);
|
|
35
|
+
if (!existsSync(dir)) {
|
|
36
|
+
mkdirSync(dir, { recursive: true });
|
|
37
|
+
}
|
|
38
|
+
}
|
|
39
|
+
|
|
40
|
+
function loadMemoryStore(): MemoryStore {
|
|
41
|
+
try {
|
|
42
|
+
const path = getMemoryPath();
|
|
43
|
+
if (existsSync(path)) {
|
|
44
|
+
const data = readFileSync(path, 'utf-8');
|
|
45
|
+
return JSON.parse(data);
|
|
46
|
+
}
|
|
47
|
+
} catch {
|
|
48
|
+
// Return empty store on error
|
|
49
|
+
}
|
|
50
|
+
return { entries: {}, version: '3.0.0' };
|
|
51
|
+
}
|
|
52
|
+
|
|
53
|
+
function saveMemoryStore(store: MemoryStore): void {
|
|
54
|
+
ensureMemoryDir();
|
|
55
|
+
writeFileSync(getMemoryPath(), JSON.stringify(store, null, 2), 'utf-8');
|
|
56
|
+
}
|
|
57
|
+
|
|
9
58
|
export const memoryTools: MCPTool[] = [
|
|
10
59
|
{
|
|
11
60
|
name: 'memory/store',
|
|
12
|
-
description: 'Store a value in memory',
|
|
61
|
+
description: 'Store a value in memory (persisted to disk)',
|
|
13
62
|
category: 'memory',
|
|
14
63
|
inputSchema: {
|
|
15
64
|
type: 'object',
|
|
@@ -21,10 +70,27 @@ export const memoryTools: MCPTool[] = [
|
|
|
21
70
|
required: ['key', 'value'],
|
|
22
71
|
},
|
|
23
72
|
handler: async (input) => {
|
|
73
|
+
const store = loadMemoryStore();
|
|
74
|
+
const now = new Date().toISOString();
|
|
75
|
+
|
|
76
|
+
const entry: MemoryEntry = {
|
|
77
|
+
key: input.key as string,
|
|
78
|
+
value: input.value,
|
|
79
|
+
metadata: (input.metadata as Record<string, unknown>) || {},
|
|
80
|
+
storedAt: now,
|
|
81
|
+
accessCount: 0,
|
|
82
|
+
lastAccessed: now,
|
|
83
|
+
};
|
|
84
|
+
|
|
85
|
+
store.entries[input.key as string] = entry;
|
|
86
|
+
saveMemoryStore(store);
|
|
87
|
+
|
|
24
88
|
return {
|
|
25
89
|
success: true,
|
|
26
90
|
key: input.key,
|
|
27
91
|
stored: true,
|
|
92
|
+
storedAt: now,
|
|
93
|
+
totalEntries: Object.keys(store.entries).length,
|
|
28
94
|
};
|
|
29
95
|
},
|
|
30
96
|
},
|
|
@@ -40,8 +106,28 @@ export const memoryTools: MCPTool[] = [
|
|
|
40
106
|
required: ['key'],
|
|
41
107
|
},
|
|
42
108
|
handler: async (input) => {
|
|
109
|
+
const store = loadMemoryStore();
|
|
110
|
+
const key = input.key as string;
|
|
111
|
+
const entry = store.entries[key];
|
|
112
|
+
|
|
113
|
+
if (entry) {
|
|
114
|
+
// Update access stats
|
|
115
|
+
entry.accessCount++;
|
|
116
|
+
entry.lastAccessed = new Date().toISOString();
|
|
117
|
+
saveMemoryStore(store);
|
|
118
|
+
|
|
119
|
+
return {
|
|
120
|
+
key,
|
|
121
|
+
value: entry.value,
|
|
122
|
+
metadata: entry.metadata,
|
|
123
|
+
storedAt: entry.storedAt,
|
|
124
|
+
accessCount: entry.accessCount,
|
|
125
|
+
found: true,
|
|
126
|
+
};
|
|
127
|
+
}
|
|
128
|
+
|
|
43
129
|
return {
|
|
44
|
-
key
|
|
130
|
+
key,
|
|
45
131
|
value: null,
|
|
46
132
|
found: false,
|
|
47
133
|
};
|
|
@@ -49,7 +135,7 @@ export const memoryTools: MCPTool[] = [
|
|
|
49
135
|
},
|
|
50
136
|
{
|
|
51
137
|
name: 'memory/search',
|
|
52
|
-
description: 'Search memory',
|
|
138
|
+
description: 'Search memory by keyword',
|
|
53
139
|
category: 'memory',
|
|
54
140
|
inputSchema: {
|
|
55
141
|
type: 'object',
|
|
@@ -60,10 +146,33 @@ export const memoryTools: MCPTool[] = [
|
|
|
60
146
|
required: ['query'],
|
|
61
147
|
},
|
|
62
148
|
handler: async (input) => {
|
|
149
|
+
const store = loadMemoryStore();
|
|
150
|
+
const query = (input.query as string).toLowerCase();
|
|
151
|
+
const limit = (input.limit as number) || 10;
|
|
152
|
+
const startTime = performance.now();
|
|
153
|
+
|
|
154
|
+
const results = Object.values(store.entries)
|
|
155
|
+
.filter(entry => {
|
|
156
|
+
const keyMatch = entry.key.toLowerCase().includes(query);
|
|
157
|
+
const valueStr = typeof entry.value === 'string' ? entry.value.toLowerCase() : JSON.stringify(entry.value).toLowerCase();
|
|
158
|
+
const valueMatch = valueStr.includes(query);
|
|
159
|
+
return keyMatch || valueMatch;
|
|
160
|
+
})
|
|
161
|
+
.slice(0, limit)
|
|
162
|
+
.map(entry => ({
|
|
163
|
+
key: entry.key,
|
|
164
|
+
value: entry.value,
|
|
165
|
+
score: 1.0, // Simple keyword match
|
|
166
|
+
storedAt: entry.storedAt,
|
|
167
|
+
}));
|
|
168
|
+
|
|
169
|
+
const duration = performance.now() - startTime;
|
|
170
|
+
|
|
63
171
|
return {
|
|
64
172
|
query: input.query,
|
|
65
|
-
results
|
|
66
|
-
total:
|
|
173
|
+
results,
|
|
174
|
+
total: results.length,
|
|
175
|
+
searchTime: `${duration.toFixed(2)}ms`,
|
|
67
176
|
};
|
|
68
177
|
},
|
|
69
178
|
},
|
|
@@ -79,10 +188,82 @@ export const memoryTools: MCPTool[] = [
|
|
|
79
188
|
required: ['key'],
|
|
80
189
|
},
|
|
81
190
|
handler: async (input) => {
|
|
191
|
+
const store = loadMemoryStore();
|
|
192
|
+
const key = input.key as string;
|
|
193
|
+
const existed = key in store.entries;
|
|
194
|
+
|
|
195
|
+
if (existed) {
|
|
196
|
+
delete store.entries[key];
|
|
197
|
+
saveMemoryStore(store);
|
|
198
|
+
}
|
|
199
|
+
|
|
82
200
|
return {
|
|
83
|
-
success:
|
|
84
|
-
key
|
|
85
|
-
deleted:
|
|
201
|
+
success: existed,
|
|
202
|
+
key,
|
|
203
|
+
deleted: existed,
|
|
204
|
+
remainingEntries: Object.keys(store.entries).length,
|
|
205
|
+
};
|
|
206
|
+
},
|
|
207
|
+
},
|
|
208
|
+
{
|
|
209
|
+
name: 'memory/list',
|
|
210
|
+
description: 'List all memory entries',
|
|
211
|
+
category: 'memory',
|
|
212
|
+
inputSchema: {
|
|
213
|
+
type: 'object',
|
|
214
|
+
properties: {
|
|
215
|
+
limit: { type: 'number', description: 'Result limit' },
|
|
216
|
+
offset: { type: 'number', description: 'Result offset' },
|
|
217
|
+
},
|
|
218
|
+
},
|
|
219
|
+
handler: async (input) => {
|
|
220
|
+
const store = loadMemoryStore();
|
|
221
|
+
const limit = (input.limit as number) || 50;
|
|
222
|
+
const offset = (input.offset as number) || 0;
|
|
223
|
+
|
|
224
|
+
const allEntries = Object.values(store.entries);
|
|
225
|
+
const entries = allEntries.slice(offset, offset + limit).map(e => ({
|
|
226
|
+
key: e.key,
|
|
227
|
+
storedAt: e.storedAt,
|
|
228
|
+
accessCount: e.accessCount,
|
|
229
|
+
preview: typeof e.value === 'string'
|
|
230
|
+
? e.value.substring(0, 50) + (e.value.length > 50 ? '...' : '')
|
|
231
|
+
: JSON.stringify(e.value).substring(0, 50),
|
|
232
|
+
}));
|
|
233
|
+
|
|
234
|
+
return {
|
|
235
|
+
entries,
|
|
236
|
+
total: allEntries.length,
|
|
237
|
+
limit,
|
|
238
|
+
offset,
|
|
239
|
+
};
|
|
240
|
+
},
|
|
241
|
+
},
|
|
242
|
+
{
|
|
243
|
+
name: 'memory/stats',
|
|
244
|
+
description: 'Get memory storage statistics',
|
|
245
|
+
category: 'memory',
|
|
246
|
+
inputSchema: {
|
|
247
|
+
type: 'object',
|
|
248
|
+
properties: {},
|
|
249
|
+
},
|
|
250
|
+
handler: async () => {
|
|
251
|
+
const store = loadMemoryStore();
|
|
252
|
+
const entries = Object.values(store.entries);
|
|
253
|
+
const totalSize = JSON.stringify(store).length;
|
|
254
|
+
|
|
255
|
+
return {
|
|
256
|
+
totalEntries: entries.length,
|
|
257
|
+
totalSize: `${(totalSize / 1024).toFixed(2)} KB`,
|
|
258
|
+
version: store.version,
|
|
259
|
+
backend: 'file',
|
|
260
|
+
location: getMemoryPath(),
|
|
261
|
+
oldestEntry: entries.length > 0
|
|
262
|
+
? entries.reduce((a, b) => a.storedAt < b.storedAt ? a : b).storedAt
|
|
263
|
+
: null,
|
|
264
|
+
newestEntry: entries.length > 0
|
|
265
|
+
? entries.reduce((a, b) => a.storedAt > b.storedAt ? a : b).storedAt
|
|
266
|
+
: null,
|
|
86
267
|
};
|
|
87
268
|
},
|
|
88
269
|
},
|