Files
ajarbot/SUB_AGENTS.md
Jordan Ramos 50cf7165cb Add sub-agent orchestration, MCP tools, and critical bug fixes
Major Features:
- Sub-agent orchestration system with dynamic specialist spawning
  * spawn_sub_agent(): Create specialists with custom prompts
  * delegate(): Convenience method for task delegation
  * Cached specialists for reuse
  * Separate conversation histories and focused context

- MCP (Model Context Protocol) tool integration
  * Zettelkasten: fleeting_note, daily_note, permanent_note, literature_note
  * Search: search_vault (hybrid search), search_by_tags
  * Web: web_fetch for real-time data
  * Zero-cost file/system operations on Pro subscription

Critical Bug Fixes:
- Fixed max tool iterations (15 → 30, configurable)
- Fixed max_tokens error in Agent SDK query() call
- Fixed MCP tool routing in execute_tool()
  * Routes zettelkasten + web tools to async handlers
  * Prevents "Unknown tool" errors

Documentation:
- SUB_AGENTS.md: Complete guide to sub-agent system
- MCP_MIGRATION.md: Agent SDK migration details
- SOUL.example.md: Sanitized bot identity template
- scheduled_tasks.example.yaml: Sanitized task config template

Security:
- Added obsidian vault to .gitignore
- Protected SOUL.md and MEMORY.md (personal configs)
- Sanitized example configs with placeholders

Dependencies:
- Added beautifulsoup4, httpx, lxml for web scraping
- Updated requirements.txt

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
2026-02-16 07:43:31 -07:00

7.0 KiB

Sub-Agent Orchestration System

Overview

Ajarbot now supports dynamic sub-agent spawning - the ability to create specialized agents on-demand for complex tasks. The main agent can delegate work to specialists with focused system prompts, reducing context window bloat and improving task efficiency.

Architecture

Main Agent (Garvis)
├─> Handles general chat, memory, scheduling
├─> Can spawn sub-agents dynamically
└─> Sub-agents share tools and (optionally) memory

Sub-Agent (Specialist)
├─> Focused system prompt (no SOUL, user profile overhead)
├─> Own conversation history (isolated context)
├─> Can use all 24 tools
└─> Returns result to main agent

Key Features

  • Dynamic spawning: Create specialists at runtime, no hardcoded definitions
  • Caching: Reuse specialists across multiple calls (agent_id parameter)
  • Memory sharing: Sub-agents can share memory workspace with main agent
  • Tool access: All tools available to sub-agents (file, web, zettelkasten, Google)
  • Isolation: Each sub-agent has separate conversation history

Usage

Method 1: Manual Spawning

# Spawn a specialist
specialist = agent.spawn_sub_agent(
    specialist_prompt="You are a zettelkasten expert. Focus ONLY on note organization.",
    agent_id="zettelkasten_processor"  # Optional: cache for reuse
)

# Use the specialist
result = specialist.chat("Process my fleeting notes", username="jordan")
# One-off delegation (specialist not cached)
result = agent.delegate(
    task="Analyze my emails and extract action items",
    specialist_prompt="You are an email analyst. Extract action items and deadlines.",
    username="jordan"
)

# Cached delegation (specialist reused)
result = agent.delegate(
    task="Create permanent notes from my fleeting notes",
    specialist_prompt="You are a zettelkasten specialist. Focus on note linking.",
    username="jordan",
    agent_id="zettelkasten_processor"  # Cached for future use
)

Method 3: LLM-Driven Orchestration (Future)

The main agent can analyze requests and decide when to delegate:

def _should_delegate(self, user_message: str) -> Optional[str]:
    """Let LLM decide if delegation is needed."""
    # Ask LLM: "Should this be delegated? If yes, generate specialist prompt"
    # Return specialist_prompt if delegation needed, None otherwise
    pass

Use Cases

Complex Zettelkasten Operations

# Main agent detects: "This requires deep note processing"
specialist = agent.spawn_sub_agent(
    specialist_prompt="""You are a zettelkasten expert. Your ONLY job is:
    - Process fleeting notes into permanent notes
    - Find semantic connections using hybrid search
    - Create wiki-style links between related concepts
    Stay focused on knowledge management.""",
    agent_id="zettelkasten_processor"
)

Email Intelligence

specialist = agent.spawn_sub_agent(
    specialist_prompt="""You are an email analyst. Your ONLY job is:
    - Summarize email threads
    - Extract action items and deadlines
    - Identify patterns in communication
    Stay focused on email analysis.""",
    agent_id="email_analyst"
)

Calendar Optimization

specialist = agent.spawn_sub_agent(
    specialist_prompt="""You are a calendar optimization expert. Your ONLY job is:
    - Find scheduling conflicts
    - Suggest optimal meeting times
    - Identify time-blocking opportunities
    Stay focused on schedule management.""",
    agent_id="calendar_optimizer"
)

Benefits

  1. Reduced Context Window: Specialists don't load SOUL.md, user profiles, or irrelevant memory
  2. Focused Performance: Specialists stay on-task without distractions
  3. Token Efficiency: Smaller system prompts = lower token usage
  4. Parallel Execution: Can spawn multiple specialists simultaneously (future)
  5. Learning Over Time: Main agent learns when to delegate based on patterns

Configuration

No configuration needed! The infrastructure is ready to use. You can:

  1. Add specialists later: Define common specialists in a config file
  2. LLM-driven delegation: Let the main agent decide when to delegate
  3. Parallel execution: Spawn multiple specialists for complex workflows
  4. Custom workspaces: Give specialists isolated memory (set share_memory=False)

Implementation Details

Code Location

  • agent.py: Lines 25-90 (sub-agent infrastructure)
    • spawn_sub_agent(): Create specialist with custom prompt
    • delegate(): Convenience method for one-off delegation
    • is_sub_agent, specialist_prompt: Instance variables
    • sub_agents: Cache dictionary

Thread Safety

  • Sub-agents have their own _chat_lock
  • Safe to spawn from multiple threads
  • Cached specialists are reused (no duplicate spawning)

Memory Sharing

  • Default: Sub-agents share main memory workspace
  • Optional: Isolated workspace at memory_workspace/sub_agents/{agent_id}/
  • Shared memory = specialists can access/update zettelkasten vault

Future Enhancements

  1. Specialist Registry: Define common specialists in config/specialists.yaml
  2. Auto-Delegation: Main agent auto-detects when to delegate
  3. Parallel Execution: Run multiple specialists concurrently
  4. Result Synthesis: Main agent combines outputs from multiple specialists
  5. Learning System: Track which specialists work best for which tasks

Example Workflows

Workflow 1: Zettelkasten Processing with Delegation

# User: "Process my fleeting notes about AI and machine learning"
# Main agent detects: complex zettelkasten task

result = agent.delegate(
    task="Find all fleeting notes tagged 'AI' or 'machine-learning', process into permanent notes, and discover connections",
    specialist_prompt="You are a zettelkasten expert. Use hybrid search to find semantic connections. Create permanent notes with smart links.",
    username="jordan",
    agent_id="zettelkasten_processor"
)

# Specialist:
# 1. search_by_tags(tags=["AI", "machine-learning", "fleeting"])
# 2. For each note: permanent_note() with auto-linking
# 3. Returns: "Created 5 permanent notes with 18 discovered connections"

# Main agent synthesizes:
# "Sir, I've processed your AI and ML notes. Five concepts emerged with particularly
#  interesting connections to your existing work on neural architecture..."

Workflow 2: Email + Calendar Coordination

# User: "Find meetings next week and check if I have email threads about them"

# Spawn two specialists in parallel (future feature)
email_result = agent.delegate(
    task="Search emails for threads about meetings",
    specialist_prompt="Email analyst. Extract meeting context.",
    agent_id="email_analyst"
)

calendar_result = agent.delegate(
    task="List all meetings next week",
    specialist_prompt="Calendar expert. Get meeting details.",
    agent_id="calendar_optimizer"
)

# Main agent synthesizes both results

Status: Infrastructure complete, ready to use. Add specialists as patterns emerge!