Skip to content

Bug: --external-agent proxies the CLI instead of delegating via the PraisonAI manager Agent #1417

@MervinPraison

Description

@MervinPraison

Bug: --external-agent proxies the CLI instead of delegating via the PraisonAI manager Agent

@claude please implement the minimal fix below.

Problem

praisonai "prompt" --external-agent claude currently bypasses the PraisonAI manager Agent and directly executes the external CLI as a pass-through proxy. This defeats the "manager → subagent" value proposition.

Evidence

@src/praisonai/praisonai/cli/main.py:4367-4401:

if getattr(self.args, 'external_agent', None):
    ...
    integration = handler.get_integration(external_agent_name, workspace=workspace)
    if integration.is_available:
        # Run the external agent directly instead of PraisonAI agent  ← PROXY, not delegation
        result = asyncio.run(integration.execute(prompt))
        ext_console.print(result)
        return ""

The ExternalAgentsHandler already has apply_to_agent_config(config, flag_value) at cli/features/external_agents.py:134-179 that injects integration.as_tool() into an agent's tools list — this is the correct delegation path. It is never called from main.py for the --external-agent flag.

Desired Behavior

--external-agent X should make the PraisonAI manager Agent use X as a subagent tool, so:

  1. Manager receives the user prompt
  2. Manager reasons / plans
  3. Manager decides when to call the external CLI tool
  4. Manager aggregates the result into a final response

With an escape hatch --direct for today's proxy behavior.

Working proof this is easy

from praisonaiagents import Agent
from praisonai.integrations import ClaudeCodeIntegration

claude = ClaudeCodeIntegration(workspace=".")
manager = Agent(
    name="Manager",
    instructions="Delegate coding tasks to claude_tool.",
    tools=[claude.as_tool()],
    llm="gpt-4o-mini",
)
print(manager.start("Use claude_tool to say hello in exactly 5 words"))

Tested locally → returns: "I used the tool to generate a five-word greeting: 'Hello there, how are you?'". Manager correctly delegates.

Fix (minimal)

@src/praisonai/praisonai/cli/main.py:4367-4401:

if getattr(self.args, 'external_agent', None):
    external_agent_name = self.args.external_agent
    direct = getattr(self.args, 'external_agent_direct', False)

    from .features.external_agents import ExternalAgentsHandler
    handler = ExternalAgentsHandler(verbose=getattr(self.args, 'verbose', False))
    integration = handler.get_integration(external_agent_name, workspace=os.getcwd())

    if not integration.is_available:
        # existing error path
        ...
        return None

    if direct:
        # Pass-through proxy (today's behavior, preserved as escape hatch)
        result = asyncio.run(integration.execute(prompt))
        ext_console.print(result)
        return ""

    # NEW default: manager Agent uses external CLI as subagent tool
    from praisonaiagents import Agent
    manager = Agent(
        name="Manager",
        instructions=(
            f"You are a manager that delegates tasks to the {external_agent_name} subagent "
            f"via the {integration.cli_command}_tool. Call the tool for coding/analysis tasks."
        ),
        tools=[integration.as_tool()],
        llm=os.environ.get("MODEL_NAME", "gpt-4o-mini"),
    )
    result = manager.start(prompt)
    ext_console.print(result)
    return ""

And register the new flag next to the existing one at @src/praisonai/praisonai/cli/main.py:1067:

parser.add_argument("--external-agent-direct", action="store_true",
                    help="Use external agent as direct proxy (skip manager Agent delegation)")

Acceptance Criteria

  • praisonai "Say hi in 5 words" --external-agent claude → manager delegates, returns response (may include manager's framing text)
  • praisonai "Say hi in 5 words" --external-agent claude --external-agent-direct → pass-through proxy (today's behavior)
  • All 4 CLIs (claude/gemini/codex/cursor) work through both paths (once companion bug-fix issue #A is merged)
  • Existing cli/features/external_agents.py apply_to_agent_config is used (DRY)
  • No new dependencies; no new module-level imports

Files to Modify

File Change
src/praisonai/praisonai/cli/main.py:1067 Add --external-agent-direct flag
src/praisonai/praisonai/cli/main.py:4367-4401 Replace direct execute with manager Agent delegation; keep direct path behind --external-agent-direct

Verification

# Manager delegation (new default)
praisonai "Say hi in 5 words" --external-agent claude
# → Manager reasons, calls claude_tool, aggregates

# Proxy (escape hatch)
praisonai "Say hi in 5 words" --external-agent claude --external-agent-direct
# → Today's pass-through behavior

# Multi-subagent (future — just add list support to the flag)
# praisonai "Refactor auth then analyze" --external-agent claude,gemini

Principles

  • Agent-centric: manager → subagent is the primary model
  • DRY: reuse ExternalAgentsHandler.apply_to_agent_config where possible
  • Backward compat: --external-agent-direct preserves current behavior
  • Minimal code change: ~30 lines in one file

Metadata

Metadata

Assignees

No one assigned

    Labels

    bugSomething isn't workingclaudeAuto-trigger Claude analysis

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions