UNPKG

@stackmemoryai/stackmemory

Version:

Project-scoped memory for AI coding tools. Durable context across sessions with MCP integration, frames, smart retrieval, Claude Code skills, and automatic hooks.

389 lines (373 loc) 11.7 kB
import { fileURLToPath as __fileURLToPath } from 'url'; import { dirname as __pathDirname } from 'path'; const __filename = __fileURLToPath(import.meta.url); const __dirname = __pathDirname(__filename); import { v4 as uuidv4 } from "uuid"; import { logger } from "../../../core/monitoring/logger.js"; import { SwarmCoordinator } from "../swarm/swarm-coordinator.js"; import { RalphStackMemoryBridge } from "../bridge/ralph-stackmemory-bridge.js"; class OracleWorkerCoordinator extends SwarmCoordinator { oracle; workerPool; reviewerPool; costTracker; constructor(config) { super({ maxAgents: config.maxWorkers + 2, // Workers + Oracle + Reviewer coordinationInterval: config.coordinationInterval, enableDynamicPlanning: true, pathologicalBehaviorDetection: true }); this.oracle = config.oracle; this.workerPool = config.workers; this.reviewerPool = config.reviewers; this.costTracker = { oracleSpent: 0, workerSpent: 0, reviewerSpent: 0, totalBudget: config.costBudget || 10 // $10 default }; logger.info("Oracle/Worker coordinator initialized", { oracle: this.oracle.model, workers: this.workerPool.length, budget: this.costTracker.totalBudget }); } /** * Launch swarm with Oracle/Worker pattern */ async launchOracleWorkerSwarm(projectDescription, taskHints) { logger.info("Launching Oracle/Worker swarm", { project: projectDescription.substring(0, 100) }); const oracleTaskId = await this.createOracleTask( "project_planning", projectDescription, taskHints ); const decomposition = await this.executeOracleTask(oracleTaskId); const workerTasks = this.allocateTasksToWorkers(decomposition); const workerPromises = workerTasks.map( (task) => this.executeWorkerTask(task) ); const reviewTaskId = await this.scheduleOracleReview(decomposition); const [workerResults, reviewResult] = await Promise.all([ Promise.allSettled(workerPromises), this.executeOracleTask(reviewTaskId) ]); const swarmId = await this.integrateResults(workerResults, reviewResult); this.logCostAnalysis(); return swarmId; } /** * Create planning task for Oracle */ async createOracleTask(type, description, hints) { const taskId = uuidv4(); const oraclePrompt = this.buildOraclePrompt(type, description, hints); const estimatedTokens = this.estimateTokens(oraclePrompt); logger.info("Oracle task created", { taskId, type, estimatedTokens, estimatedCost: estimatedTokens * this.oracle.costPerToken }); return taskId; } /** * Build specialized prompt for Oracle model */ buildOraclePrompt(type, description, hints) { const basePrompt = ` # ORACLE ROLE: Strategic Planning & Coordination You are the Oracle in an Oracle/Worker pattern. Your role: - HIGH-LEVEL STRATEGIC thinking - TASK DECOMPOSITION for worker agents - QUALITY CONTROL and review - COORDINATION between workers - ERROR CORRECTION and replanning ## Project Context ${description} ${hints ? `## Hints & Context ${hints.map((h) => `- ${h}`).join("\n")}` : ""} ## Your Oracle Responsibilities 1. **Decompose** this project into discrete, parallelizable tasks 2. **Assign complexity levels** (low/medium/high) to guide worker selection 3. **Define acceptance criteria** for each task 4. **Identify dependencies** between tasks 5. **Plan coordination touchpoints** for integration ## Worker Constraints - Workers are smaller models optimized for focused execution - Workers excel at: implementation, testing, documentation, simple analysis - Workers struggle with: complex architecture, strategic decisions, cross-cutting concerns ## Output Required Provide a detailed task decomposition in JSON format: \`\`\`json { "project_summary": "Brief overview", "task_decomposition": [ { "id": "unique-id", "title": "Task name", "description": "Detailed description", "complexity": "low|medium|high", "type": "implementation|testing|documentation|analysis", "estimated_effort": "1-5 scale", "worker_requirements": ["specific capabilities needed"], "acceptance_criteria": ["criterion 1", "criterion 2"], "dependencies": ["task-id-1", "task-id-2"] } ], "coordination_plan": { "integration_points": ["When to sync between workers"], "review_checkpoints": ["When Oracle should review progress"], "risk_mitigation": ["Potential issues and solutions"] } } \`\`\` Remember: Your intelligence is expensive. Focus on high-value strategic thinking that workers cannot do effectively. `; return basePrompt; } /** * Execute Oracle task with high-end model */ async executeOracleTask(taskId) { logger.info("Executing Oracle task", { taskId }); const ralph = new RalphStackMemoryBridge({ baseDir: `.oracle/${taskId}`, maxIterations: 3, // Oracle should be efficient useStackMemory: true }); const result = await ralph.run(); const tokens = this.estimateTokens(result); const cost = tokens * this.oracle.costPerToken; this.costTracker.oracleSpent += cost; logger.info("Oracle task completed", { taskId, tokensUsed: tokens, cost: cost.toFixed(4) }); return this.parseTaskDecomposition(result); } /** * Allocate decomposed tasks to worker models */ allocateTasksToWorkers(decomposition) { const allocatedTasks = []; for (const task of decomposition) { const workerModel = this.selectWorkerForTask(task); const workerPrompt = this.buildWorkerPrompt(task, workerModel); allocatedTasks.push({ ...task, assignedModel: "worker" }); logger.debug("Task allocated to worker", { taskId: task.id, complexity: task.complexity, worker: workerModel.model }); } return allocatedTasks; } /** * Select optimal worker model for task complexity */ selectWorkerForTask(task) { if (task.complexity === "high") { return this.workerPool[0]; } else { return this.workerPool.reduce( (cheapest, current) => current.costPerToken < cheapest.costPerToken ? current : cheapest ); } } /** * Build focused prompt for worker models */ buildWorkerPrompt(task, worker) { return ` # WORKER ROLE: Focused Task Execution You are a specialized worker in an Oracle/Worker pattern. ## Your Task ${task.type}: ${task.title} ${task.description} ## Success Criteria ${task.acceptanceCriteria.map((c) => `- ${c}`).join("\n")} ## Worker Guidelines - FOCUS on this specific task only - IMPLEMENT according to the specifications provided - ASK for clarification if requirements are unclear - COMMUNICATE progress through shared context - COMPLETE the task efficiently without over-engineering ## Constraints - You are optimized for execution, not planning - Stay within your assigned scope - Collaborate with other workers through shared context - The Oracle will handle integration and review Execute your task now. `; } /** * Execute worker task with cost tracking */ async executeWorkerTask(task) { logger.info("Executing worker task", { taskId: task.id, complexity: task.complexity }); const ralph = new RalphStackMemoryBridge({ baseDir: `.workers/${task.id}`, maxIterations: task.complexity === "low" ? 3 : 7, useStackMemory: true }); const result = await ralph.run(); const workerModel = this.selectWorkerForTask(task); const tokens = this.estimateTokens(result); const cost = tokens * workerModel.costPerToken; this.costTracker.workerSpent += cost; logger.info("Worker task completed", { taskId: task.id, tokensUsed: tokens, cost: cost.toFixed(4) }); return result; } /** * Schedule Oracle review of worker progress */ async scheduleOracleReview(decomposition) { const reviewTaskId = uuidv4(); logger.info("Oracle review scheduled", { reviewTaskId, tasksToReview: decomposition.length }); return reviewTaskId; } /** * Integrate worker results under Oracle coordination */ async integrateResults(workerResults, reviewResult) { const swarmId = uuidv4(); const successfulTasks = workerResults.filter( (result) => result.status === "fulfilled" ).length; logger.info("Integration completed", { swarmId, totalTasks: workerResults.length, successfulTasks, successRate: (successfulTasks / workerResults.length * 100).toFixed(1) }); return swarmId; } /** * Parse task decomposition from Oracle output */ parseTaskDecomposition(output) { return []; } /** * Estimate token usage for cost calculation */ estimateTokens(text) { return Math.ceil(text.length / 4); } /** * Log cost analysis and efficiency metrics */ logCostAnalysis() { const total = this.costTracker.oracleSpent + this.costTracker.workerSpent + this.costTracker.reviewerSpent; const savings = this.calculateTraditionalCost() - total; logger.info("Oracle/Worker Cost Analysis", { oracleSpent: `$${this.costTracker.oracleSpent.toFixed(4)}`, workerSpent: `$${this.costTracker.workerSpent.toFixed(4)}`, totalSpent: `$${total.toFixed(4)}`, budgetUsed: `${(total / this.costTracker.totalBudget * 100).toFixed(1)}%`, estimatedSavings: `$${savings.toFixed(4)}`, efficiency: `${(this.costTracker.workerSpent / total * 100).toFixed(1)}% worker tasks` }); } /** * Calculate what this would cost with all-Oracle approach */ calculateTraditionalCost() { const totalSpent = this.costTracker.oracleSpent + this.costTracker.workerSpent + this.costTracker.reviewerSpent; const avgWorkerCost = this.workerPool[0]?.costPerToken || 1e-3; const workerTokensAsOracle = this.costTracker.workerSpent / avgWorkerCost; return this.costTracker.oracleSpent + workerTokensAsOracle * this.oracle.costPerToken; } } const defaultModelConfigs = { oracle: [ { tier: "oracle", provider: "claude", model: "claude-3-opus-20240229", costPerToken: 0.015, // $15/1M input tokens capabilities: [ "strategic_planning", "complex_reasoning", "task_decomposition", "quality_review", "error_correction" ] } ], worker: [ { tier: "worker", provider: "claude", model: "claude-3-5-haiku-20241022", costPerToken: 25e-5, // $0.25/1M input tokens capabilities: [ "code_implementation", "unit_testing", "documentation", "simple_analysis", "data_processing" ] }, { tier: "worker", provider: "openai", model: "gpt-4o-mini", costPerToken: 15e-5, // $0.15/1M input tokens capabilities: [ "rapid_prototyping", "script_writing", "basic_testing", "formatting", "simple_refactoring" ] } ], reviewer: [ { tier: "reviewer", provider: "claude", model: "claude-3-sonnet-20240229", costPerToken: 3e-3, // $3/1M input tokens capabilities: [ "code_review", "quality_assessment", "integration_testing", "performance_analysis", "security_review" ] } ] }; var oracle_worker_pattern_default = OracleWorkerCoordinator; export { OracleWorkerCoordinator, oracle_worker_pattern_default as default, defaultModelConfigs }; //# sourceMappingURL=oracle-worker-pattern.js.map