UNPKG

@measey/mycoder-agent

Version:

Agent module for mycoder - an AI-powered software development assistant

151 lines 6.3 kB
import { z } from 'zod'; import { zodToJsonSchema } from 'zod-to-json-schema'; const parameterSchema = z.object({ agentId: z.string().describe('The ID returned by agentStart'), guidance: z .string() .optional() .describe('Optional guidance or instructions to send to the sub-agent'), terminate: z .boolean() .optional() .describe('Whether to terminate the sub-agent (default: false)'), description: z .string() .describe('The reason for this agent interaction (max 80 chars)'), }); const returnSchema = z.object({ output: z.string().describe('The current output from the sub-agent'), completed: z .boolean() .describe('Whether the sub-agent has completed its task'), error: z .string() .optional() .describe('Error message if the sub-agent encountered an error'), terminated: z .boolean() .optional() .describe('Whether the sub-agent was terminated by this message'), messageSent: z .boolean() .optional() .describe('Whether a message was sent to the sub-agent'), messageCount: z .number() .optional() .describe("The number of messages in the sub-agent's queue"), }); export const agentMessageTool = { name: 'agentMessage', description: 'Interacts with a running sub-agent, getting its current state and optionally providing guidance', logPrefix: '🤖', parameters: parameterSchema, parametersJsonSchema: zodToJsonSchema(parameterSchema), returns: returnSchema, returnsJsonSchema: zodToJsonSchema(returnSchema), execute: async ({ agentId, guidance, terminate, description: _ }, { logger, agentTracker, ...__ }) => { logger.debug(`Interacting with sub-agent ${agentId}${guidance ? ' with guidance' : ''}${terminate ? ' with termination request' : ''}`); try { // Get the agent from the tracker const agent = agentTracker.getAgent(agentId); if (!agent) { throw new Error(`No sub-agent found with ID ${agentId}`); } // Check if the agent was already terminated if (agent.aborted) { return { output: agent.output || 'Sub-agent was previously terminated', completed: true, terminated: true, messageSent: false, messageCount: 0, }; } // Terminate the agent if requested if (terminate) { agent.aborted = true; agent.completed = true; return { output: agent.output || 'Sub-agent terminated before completion', completed: true, terminated: true, messageSent: false, messageCount: 0, }; } // Add guidance to the agent state's parentMessages array // The sub-agent will check for these messages on each iteration if (guidance) { logger.log(`Guidance provided to sub-agent ${agentId}: ${guidance}`); // Add the guidance to the parentMessages array agent.parentMessages.push(guidance); logger.debug(`Added message to sub-agent ${agentId}'s parentMessages queue. Total messages: ${agent.parentMessages.length}`); } // Get the current output and captured logs const resultOutput = agent.result_detailed?.result || ''; let output = resultOutput || agent.output || 'No output yet'; // Append captured logs if there are any if (agent.capturedLogs && agent.capturedLogs.length > 0) { // Always append logs if there are any const logContent = agent.capturedLogs.join('\n'); output = `${output}\n\n--- Agent Log Messages ---\n${logContent}`; // Log that we're returning captured logs logger.debug(`Returning ${agent.capturedLogs.length} captured log messages for agent ${agentId}`); // Clear the captured logs after retrieving them agent.capturedLogs = []; } // Reset the output to an empty string agent.output = ''; return { output, completed: agent.completed, ...(agent.error && { error: agent.error }), messageSent: guidance ? true : false, messageCount: agent.parentMessages.length, }; } catch (error) { if (error instanceof Error) { logger.debug(`Sub-agent interaction failed: ${error.message}`); return { output: '', completed: false, error: error.message, messageSent: false, messageCount: 0, }; } const errorMessage = String(error); logger.error(`Unknown error during sub-agent interaction: ${errorMessage}`); return { output: '', completed: false, error: `Unknown error occurred: ${errorMessage}`, messageSent: false, messageCount: 0, }; } }, logParameters: (input, { logger }) => { logger.log(`Interacting with sub-agent ${input.agentId}, ${input.description}${input.terminate ? ' (terminating)' : ''}`); }, logReturns: (output, { logger }) => { if (output.error) { logger.error(`Sub-agent interaction error: ${output.error}`); } else if (output.terminated) { logger.log('Sub-agent was terminated'); } else if (output.completed) { logger.log('Sub-agent has completed its task'); } else { logger.log('Sub-agent is still running'); } if (output.messageSent) { logger.log(`Message sent to sub-agent. Queue now has ${output.messageCount || 0} message(s).`); } }, }; //# sourceMappingURL=agentMessage.js.map