Skip to Content

Calling Agents

Code workflows handle deterministic logic well, but sometimes you need AI intelligence — for summarizing, writing, or making decisions. The invokeWorkflow function lets you embed AI capabilities within code workflows.

When to use invokeWorkflow

Use invokeWorkflow for tasks that need intelligence:

  • Writing — Composing emails, summaries, reports
  • Summarizing — Condensing information
  • Deciding — Making judgments about content
  • Analyzing — Understanding context or sentiment

Use regular code for deterministic work:

  • Filtering — Removing items by criteria
  • Formatting — Structuring output
  • Aggregating — Grouping or counting
  • Iterating — Processing lists

Defining agents

Agents are defined in the workflow’s configuration:

{ "agents": { "summary_writer": { "description": "Writes friendly email summaries", "prompt": "Given a list of emails, write a 2-3 sentence intro summarizing the day's activity and a brief outro.", "outputSchema": { "intro": "string", "outro": "string" } } } }

Each agent has:

  • description — What the agent does (for documentation)
  • prompt — Instructions for the AI
  • outputSchema — Structure of the expected output

Using invokeWorkflow

const result = await invokeWorkflow({ agent: { type: "name", name: "summary_writer" }, context: { emails, count: emails.length }, sync: true }); if (!result.success) { throw new Error(result.error || "Agent failed"); } // result.result.intro and result.result.outro are now available

The context object is passed to the agent and available in its prompt. The agent returns a result object with success, result, and optionally error. The result field contains structured output matching the agent’s outputSchema.

Example: Smart summary

import { step, tool, invokeWorkflow, complete } from './workflow-runtime'; // Gather data const emails = await step('gather', async () => { return await tool('search_emails', { query: 'newer_than:1d is:unread' }); }); // Deterministic formatting const formatted = await step('format', async () => { return emails.map(e => `- ${e.subject} (from ${e.from})`).join('\n'); }); // AI-driven writing const summary = await step('summarize', async () => { const result = await invokeWorkflow({ agent: { type: "name", name: "writer" }, context: { emailCount: emails.length, emailList: formatted }, sync: true }); if (!result.success) throw new Error(result.error || "Writer agent failed"); return result.result; }); // Send the result await step('send', async () => { await tool('send_email_to_user', { subject: 'Daily Summary', body: `${summary.intro}\n\n${formatted}\n\n${summary.outro}` }); }); complete();

Agent configuration examples

Summarizer

{ "summary_writer": { "description": "Writes concise summaries", "prompt": "Summarize the provided content in 2-3 sentences. Be concise and highlight the most important points.", "outputSchema": { "summary": "string" } } }

Categorizer

{ "email_categorizer": { "description": "Categorizes emails by type", "prompt": "Analyze the email and categorize it. Return one of: important, newsletter, notification, spam, other.", "outputSchema": { "category": "string", "confidence": "number" } } }

Writer

{ "reply_writer": { "description": "Drafts email replies", "prompt": "Draft a professional reply to this email. Be helpful and concise. Match the tone of the original.", "outputSchema": { "subject": "string", "body": "string" } } }

Best practices

Keep agent prompts focused. Each agent should do one thing well. Use multiple agents for different tasks.

Use outputSchema. Structured output is easier to work with in code than free-form text.

Provide rich context. The more relevant information you pass in context, the better the agent’s output.

Separate AI from logic

Keep AI work in invokeWorkflow, logic in code:

// Good: AI does writing, code does structure const result = await invokeWorkflow({ agent: { type: "name", name: "analyzer" }, context: { email }, sync: true }); const analysis = result.result; const formatted = `Priority: ${analysis.priority}\nSummary: ${analysis.summary}`; // Avoid: Mixing concerns const result = await invokeWorkflow({ agent: { type: "name", name: "do_everything" }, context: { email }, sync: true }); // The agent is trying to format AND analyze AND decide
Last updated on