|
|
|
@ -1,6 +1,6 @@
|
|
|
|
from swarms import Agent
|
|
|
|
from swarms import Agent
|
|
|
|
from swarms.structs.concurrent_workflow import ConcurrentWorkflow
|
|
|
|
from swarms.structs.concurrent_workflow import ConcurrentWorkflow
|
|
|
|
|
|
|
|
import pytest
|
|
|
|
|
|
|
|
|
|
|
|
def test_concurrent_workflow_basic_execution():
|
|
|
|
def test_concurrent_workflow_basic_execution():
|
|
|
|
"""Test basic ConcurrentWorkflow execution with multiple agents"""
|
|
|
|
"""Test basic ConcurrentWorkflow execution with multiple agents"""
|
|
|
|
@ -8,21 +8,27 @@ def test_concurrent_workflow_basic_execution():
|
|
|
|
research_agent = Agent(
|
|
|
|
research_agent = Agent(
|
|
|
|
agent_name="Research-Analyst",
|
|
|
|
agent_name="Research-Analyst",
|
|
|
|
agent_description="Agent specializing in research and data collection",
|
|
|
|
agent_description="Agent specializing in research and data collection",
|
|
|
|
model_name="gpt-4o",
|
|
|
|
model_name="gpt-4o-mini",
|
|
|
|
|
|
|
|
verbose=False,
|
|
|
|
|
|
|
|
print_on=False,
|
|
|
|
max_loops=1,
|
|
|
|
max_loops=1,
|
|
|
|
)
|
|
|
|
)
|
|
|
|
|
|
|
|
|
|
|
|
strategy_agent = Agent(
|
|
|
|
strategy_agent = Agent(
|
|
|
|
agent_name="Strategy-Consultant",
|
|
|
|
agent_name="Strategy-Consultant",
|
|
|
|
agent_description="Agent specializing in strategic planning and analysis",
|
|
|
|
agent_description="Agent specializing in strategic planning and analysis",
|
|
|
|
model_name="gpt-4o",
|
|
|
|
model_name="gpt-4o-mini",
|
|
|
|
|
|
|
|
verbose=False,
|
|
|
|
|
|
|
|
print_on=False,
|
|
|
|
max_loops=1,
|
|
|
|
max_loops=1,
|
|
|
|
)
|
|
|
|
)
|
|
|
|
|
|
|
|
|
|
|
|
risk_agent = Agent(
|
|
|
|
risk_agent = Agent(
|
|
|
|
agent_name="Risk-Assessment-Specialist",
|
|
|
|
agent_name="Risk-Assessment-Specialist",
|
|
|
|
agent_description="Agent specializing in risk analysis and mitigation",
|
|
|
|
agent_description="Agent specializing in risk analysis and mitigation",
|
|
|
|
model_name="gpt-4o",
|
|
|
|
model_name="gpt-4o-mini",
|
|
|
|
|
|
|
|
verbose=False,
|
|
|
|
|
|
|
|
print_on=False,
|
|
|
|
max_loops=1,
|
|
|
|
max_loops=1,
|
|
|
|
)
|
|
|
|
)
|
|
|
|
|
|
|
|
|
|
|
|
@ -39,15 +45,16 @@ def test_concurrent_workflow_basic_execution():
|
|
|
|
"Analyze the potential impact of quantum computing on cybersecurity"
|
|
|
|
"Analyze the potential impact of quantum computing on cybersecurity"
|
|
|
|
)
|
|
|
|
)
|
|
|
|
|
|
|
|
|
|
|
|
# Verify results - ConcurrentWorkflow returns a list of dictionaries
|
|
|
|
# Verify results - ConcurrentWorkflow with default output_type returns conversation history
|
|
|
|
assert result is not None
|
|
|
|
assert result is not None
|
|
|
|
assert isinstance(result, list)
|
|
|
|
assert isinstance(result, list)
|
|
|
|
assert len(result) == 3
|
|
|
|
# With default output_type="dict-all-except-first", we get conversation_history[2:]
|
|
|
|
|
|
|
|
# So we should have at least some results, but exact count depends on successful agent runs
|
|
|
|
|
|
|
|
assert len(result) >= 1 # At least one agent should succeed
|
|
|
|
for r in result:
|
|
|
|
for r in result:
|
|
|
|
assert isinstance(r, dict)
|
|
|
|
assert isinstance(r, dict)
|
|
|
|
assert "agent" in r
|
|
|
|
assert "role" in r # Agent name is stored in 'role' field
|
|
|
|
assert "output" in r
|
|
|
|
assert "content" in r # Agent output is stored in 'content' field
|
|
|
|
# Output might be None or empty string, just check it exists
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
def test_concurrent_workflow_with_dashboard():
|
|
|
|
def test_concurrent_workflow_with_dashboard():
|
|
|
|
@ -56,21 +63,27 @@ def test_concurrent_workflow_with_dashboard():
|
|
|
|
market_agent = Agent(
|
|
|
|
market_agent = Agent(
|
|
|
|
agent_name="Market-Analyst",
|
|
|
|
agent_name="Market-Analyst",
|
|
|
|
agent_description="Agent for market analysis and trends",
|
|
|
|
agent_description="Agent for market analysis and trends",
|
|
|
|
model_name="gpt-4o",
|
|
|
|
model_name="gpt-4o-mini",
|
|
|
|
|
|
|
|
verbose=False,
|
|
|
|
|
|
|
|
print_on=False,
|
|
|
|
max_loops=1,
|
|
|
|
max_loops=1,
|
|
|
|
)
|
|
|
|
)
|
|
|
|
|
|
|
|
|
|
|
|
financial_agent = Agent(
|
|
|
|
financial_agent = Agent(
|
|
|
|
agent_name="Financial-Expert",
|
|
|
|
agent_name="Financial-Expert",
|
|
|
|
agent_description="Agent for financial analysis and forecasting",
|
|
|
|
agent_description="Agent for financial analysis and forecasting",
|
|
|
|
model_name="gpt-4o",
|
|
|
|
model_name="gpt-4o-mini",
|
|
|
|
|
|
|
|
verbose=False,
|
|
|
|
|
|
|
|
print_on=False,
|
|
|
|
max_loops=1,
|
|
|
|
max_loops=1,
|
|
|
|
)
|
|
|
|
)
|
|
|
|
|
|
|
|
|
|
|
|
technology_agent = Agent(
|
|
|
|
technology_agent = Agent(
|
|
|
|
agent_name="Technology-Specialist",
|
|
|
|
agent_name="Technology-Specialist",
|
|
|
|
agent_description="Agent for technology assessment and innovation",
|
|
|
|
agent_description="Agent for technology assessment and innovation",
|
|
|
|
model_name="gpt-4o",
|
|
|
|
model_name="gpt-4o-mini",
|
|
|
|
|
|
|
|
verbose=False,
|
|
|
|
|
|
|
|
print_on=False,
|
|
|
|
max_loops=1,
|
|
|
|
max_loops=1,
|
|
|
|
)
|
|
|
|
)
|
|
|
|
|
|
|
|
|
|
|
|
@ -88,12 +101,12 @@ def test_concurrent_workflow_with_dashboard():
|
|
|
|
|
|
|
|
|
|
|
|
assert result is not None
|
|
|
|
assert result is not None
|
|
|
|
assert isinstance(result, list)
|
|
|
|
assert isinstance(result, list)
|
|
|
|
assert len(result) == 3
|
|
|
|
# With default output_type="dict-all-except-first", we get conversation_history[2:]
|
|
|
|
|
|
|
|
assert len(result) >= 1 # At least one agent should succeed
|
|
|
|
for r in result:
|
|
|
|
for r in result:
|
|
|
|
assert isinstance(r, dict)
|
|
|
|
assert isinstance(r, dict)
|
|
|
|
assert "agent" in r
|
|
|
|
assert "role" in r # Agent name is stored in 'role' field
|
|
|
|
assert "output" in r
|
|
|
|
assert "content" in r # Agent output is stored in 'content' field
|
|
|
|
# Output can be None or empty, just check structure
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
def test_concurrent_workflow_batched_execution():
|
|
|
|
def test_concurrent_workflow_batched_execution():
|
|
|
|
@ -103,7 +116,9 @@ def test_concurrent_workflow_batched_execution():
|
|
|
|
Agent(
|
|
|
|
Agent(
|
|
|
|
agent_name=f"Analysis-Agent-{i+1}",
|
|
|
|
agent_name=f"Analysis-Agent-{i+1}",
|
|
|
|
agent_description=f"Agent {i+1} for comprehensive business analysis",
|
|
|
|
agent_description=f"Agent {i+1} for comprehensive business analysis",
|
|
|
|
model_name="gpt-4o",
|
|
|
|
model_name="gpt-4o-mini",
|
|
|
|
|
|
|
|
verbose=False,
|
|
|
|
|
|
|
|
print_on=False,
|
|
|
|
max_loops=1,
|
|
|
|
max_loops=1,
|
|
|
|
)
|
|
|
|
)
|
|
|
|
for i in range(4)
|
|
|
|
for i in range(4)
|
|
|
|
@ -139,7 +154,7 @@ def test_concurrent_workflow_error_handling():
|
|
|
|
"""Test ConcurrentWorkflow error handling and validation"""
|
|
|
|
"""Test ConcurrentWorkflow error handling and validation"""
|
|
|
|
# Test with empty agents list
|
|
|
|
# Test with empty agents list
|
|
|
|
try:
|
|
|
|
try:
|
|
|
|
ConcurrentWorkflow(agents=[])
|
|
|
|
workflow = ConcurrentWorkflow(agents=[])
|
|
|
|
assert (
|
|
|
|
assert (
|
|
|
|
False
|
|
|
|
False
|
|
|
|
), "Should have raised ValueError for empty agents list"
|
|
|
|
), "Should have raised ValueError for empty agents list"
|
|
|
|
@ -148,7 +163,7 @@ def test_concurrent_workflow_error_handling():
|
|
|
|
|
|
|
|
|
|
|
|
# Test with None agents
|
|
|
|
# Test with None agents
|
|
|
|
try:
|
|
|
|
try:
|
|
|
|
ConcurrentWorkflow(agents=None)
|
|
|
|
workflow = ConcurrentWorkflow(agents=None)
|
|
|
|
assert False, "Should have raised ValueError for None agents"
|
|
|
|
assert False, "Should have raised ValueError for None agents"
|
|
|
|
except ValueError as e:
|
|
|
|
except ValueError as e:
|
|
|
|
assert "No agents provided" in str(e)
|
|
|
|
assert "No agents provided" in str(e)
|
|
|
|
@ -160,14 +175,18 @@ def test_concurrent_workflow_max_loops_configuration():
|
|
|
|
agent1 = Agent(
|
|
|
|
agent1 = Agent(
|
|
|
|
agent_name="Loop-Test-Agent-1",
|
|
|
|
agent_name="Loop-Test-Agent-1",
|
|
|
|
agent_description="First agent for loop testing",
|
|
|
|
agent_description="First agent for loop testing",
|
|
|
|
model_name="gpt-4o",
|
|
|
|
model_name="gpt-4o-mini",
|
|
|
|
|
|
|
|
verbose=False,
|
|
|
|
|
|
|
|
print_on=False,
|
|
|
|
max_loops=2,
|
|
|
|
max_loops=2,
|
|
|
|
)
|
|
|
|
)
|
|
|
|
|
|
|
|
|
|
|
|
agent2 = Agent(
|
|
|
|
agent2 = Agent(
|
|
|
|
agent_name="Loop-Test-Agent-2",
|
|
|
|
agent_name="Loop-Test-Agent-2",
|
|
|
|
agent_description="Second agent for loop testing",
|
|
|
|
agent_description="Second agent for loop testing",
|
|
|
|
model_name="gpt-4o",
|
|
|
|
model_name="gpt-4o-mini",
|
|
|
|
|
|
|
|
verbose=False,
|
|
|
|
|
|
|
|
print_on=False,
|
|
|
|
max_loops=3,
|
|
|
|
max_loops=3,
|
|
|
|
)
|
|
|
|
)
|
|
|
|
|
|
|
|
|
|
|
|
@ -182,11 +201,12 @@ def test_concurrent_workflow_max_loops_configuration():
|
|
|
|
|
|
|
|
|
|
|
|
assert result is not None
|
|
|
|
assert result is not None
|
|
|
|
assert isinstance(result, list)
|
|
|
|
assert isinstance(result, list)
|
|
|
|
assert len(result) == 2
|
|
|
|
# With default output_type="dict-all-except-first", we get conversation_history[2:]
|
|
|
|
|
|
|
|
assert len(result) >= 1 # At least one agent should succeed
|
|
|
|
for r in result:
|
|
|
|
for r in result:
|
|
|
|
assert isinstance(r, dict)
|
|
|
|
assert isinstance(r, dict)
|
|
|
|
assert "agent" in r
|
|
|
|
assert "role" in r # Agent name is stored in 'role' field
|
|
|
|
assert "output" in r
|
|
|
|
assert "content" in r # Agent output is stored in 'content' field
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
def test_concurrent_workflow_different_output_types():
|
|
|
|
def test_concurrent_workflow_different_output_types():
|
|
|
|
@ -195,21 +215,27 @@ def test_concurrent_workflow_different_output_types():
|
|
|
|
technical_agent = Agent(
|
|
|
|
technical_agent = Agent(
|
|
|
|
agent_name="Technical-Analyst",
|
|
|
|
agent_name="Technical-Analyst",
|
|
|
|
agent_description="Agent for technical analysis",
|
|
|
|
agent_description="Agent for technical analysis",
|
|
|
|
model_name="gpt-4o",
|
|
|
|
model_name="gpt-4o-mini",
|
|
|
|
|
|
|
|
verbose=False,
|
|
|
|
|
|
|
|
print_on=False,
|
|
|
|
max_loops=1,
|
|
|
|
max_loops=1,
|
|
|
|
)
|
|
|
|
)
|
|
|
|
|
|
|
|
|
|
|
|
business_agent = Agent(
|
|
|
|
business_agent = Agent(
|
|
|
|
agent_name="Business-Strategist",
|
|
|
|
agent_name="Business-Strategist",
|
|
|
|
agent_description="Agent for business strategy",
|
|
|
|
agent_description="Agent for business strategy",
|
|
|
|
model_name="gpt-4o",
|
|
|
|
model_name="gpt-4o-mini",
|
|
|
|
|
|
|
|
verbose=False,
|
|
|
|
|
|
|
|
print_on=False,
|
|
|
|
max_loops=1,
|
|
|
|
max_loops=1,
|
|
|
|
)
|
|
|
|
)
|
|
|
|
|
|
|
|
|
|
|
|
legal_agent = Agent(
|
|
|
|
legal_agent = Agent(
|
|
|
|
agent_name="Legal-Expert",
|
|
|
|
agent_name="Legal-Expert",
|
|
|
|
agent_description="Agent for legal compliance analysis",
|
|
|
|
agent_description="Agent for legal compliance analysis",
|
|
|
|
model_name="gpt-4o",
|
|
|
|
model_name="gpt-4o-mini",
|
|
|
|
|
|
|
|
verbose=False,
|
|
|
|
|
|
|
|
print_on=False,
|
|
|
|
max_loops=1,
|
|
|
|
max_loops=1,
|
|
|
|
)
|
|
|
|
)
|
|
|
|
|
|
|
|
|
|
|
|
@ -234,28 +260,36 @@ def test_concurrent_workflow_real_world_scenario():
|
|
|
|
marketing_agent = Agent(
|
|
|
|
marketing_agent = Agent(
|
|
|
|
agent_name="Marketing-Director",
|
|
|
|
agent_name="Marketing-Director",
|
|
|
|
agent_description="Senior marketing director with 15 years experience",
|
|
|
|
agent_description="Senior marketing director with 15 years experience",
|
|
|
|
model_name="gpt-4o",
|
|
|
|
model_name="gpt-4o-mini",
|
|
|
|
|
|
|
|
verbose=False,
|
|
|
|
|
|
|
|
print_on=False,
|
|
|
|
max_loops=1,
|
|
|
|
max_loops=1,
|
|
|
|
)
|
|
|
|
)
|
|
|
|
|
|
|
|
|
|
|
|
product_agent = Agent(
|
|
|
|
product_agent = Agent(
|
|
|
|
agent_name="Product-Manager",
|
|
|
|
agent_name="Product-Manager",
|
|
|
|
agent_description="Product manager specializing in AI/ML products",
|
|
|
|
agent_description="Product manager specializing in AI/ML products",
|
|
|
|
model_name="gpt-4o",
|
|
|
|
model_name="gpt-4o-mini",
|
|
|
|
|
|
|
|
verbose=False,
|
|
|
|
|
|
|
|
print_on=False,
|
|
|
|
max_loops=1,
|
|
|
|
max_loops=1,
|
|
|
|
)
|
|
|
|
)
|
|
|
|
|
|
|
|
|
|
|
|
engineering_agent = Agent(
|
|
|
|
engineering_agent = Agent(
|
|
|
|
agent_name="Lead-Engineer",
|
|
|
|
agent_name="Lead-Engineer",
|
|
|
|
agent_description="Senior software engineer and technical architect",
|
|
|
|
agent_description="Senior software engineer and technical architect",
|
|
|
|
model_name="gpt-4o",
|
|
|
|
model_name="gpt-4o-mini",
|
|
|
|
|
|
|
|
verbose=False,
|
|
|
|
|
|
|
|
print_on=False,
|
|
|
|
max_loops=1,
|
|
|
|
max_loops=1,
|
|
|
|
)
|
|
|
|
)
|
|
|
|
|
|
|
|
|
|
|
|
sales_agent = Agent(
|
|
|
|
sales_agent = Agent(
|
|
|
|
agent_name="Sales-Executive",
|
|
|
|
agent_name="Sales-Executive",
|
|
|
|
agent_description="Enterprise sales executive with tech background",
|
|
|
|
agent_description="Enterprise sales executive with tech background",
|
|
|
|
model_name="gpt-4o",
|
|
|
|
model_name="gpt-4o-mini",
|
|
|
|
|
|
|
|
verbose=False,
|
|
|
|
|
|
|
|
print_on=False,
|
|
|
|
max_loops=1,
|
|
|
|
max_loops=1,
|
|
|
|
)
|
|
|
|
)
|
|
|
|
|
|
|
|
|
|
|
|
@ -279,12 +313,12 @@ def test_concurrent_workflow_real_world_scenario():
|
|
|
|
|
|
|
|
|
|
|
|
assert result is not None
|
|
|
|
assert result is not None
|
|
|
|
assert isinstance(result, list)
|
|
|
|
assert isinstance(result, list)
|
|
|
|
assert len(result) == 4
|
|
|
|
# With default output_type="dict-all-except-first", we get conversation_history[2:]
|
|
|
|
|
|
|
|
assert len(result) >= 1 # At least one agent should succeed
|
|
|
|
for r in result:
|
|
|
|
for r in result:
|
|
|
|
assert isinstance(r, dict)
|
|
|
|
assert isinstance(r, dict)
|
|
|
|
assert "agent" in r
|
|
|
|
assert "role" in r # Agent name is stored in 'role' field
|
|
|
|
assert "output" in r
|
|
|
|
assert "content" in r # Agent output is stored in 'content' field
|
|
|
|
# Output content may vary, just check structure
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
def test_concurrent_workflow_team_collaboration():
|
|
|
|
def test_concurrent_workflow_team_collaboration():
|
|
|
|
@ -293,28 +327,36 @@ def test_concurrent_workflow_team_collaboration():
|
|
|
|
data_scientist = Agent(
|
|
|
|
data_scientist = Agent(
|
|
|
|
agent_name="Data-Scientist",
|
|
|
|
agent_name="Data-Scientist",
|
|
|
|
agent_description="ML engineer and data scientist",
|
|
|
|
agent_description="ML engineer and data scientist",
|
|
|
|
model_name="gpt-4o",
|
|
|
|
model_name="gpt-4o-mini",
|
|
|
|
|
|
|
|
verbose=False,
|
|
|
|
|
|
|
|
print_on=False,
|
|
|
|
max_loops=1,
|
|
|
|
max_loops=1,
|
|
|
|
)
|
|
|
|
)
|
|
|
|
|
|
|
|
|
|
|
|
ux_designer = Agent(
|
|
|
|
ux_designer = Agent(
|
|
|
|
agent_name="UX-Designer",
|
|
|
|
agent_name="UX-Designer",
|
|
|
|
agent_description="User experience designer and researcher",
|
|
|
|
agent_description="User experience designer and researcher",
|
|
|
|
model_name="gpt-4o",
|
|
|
|
model_name="gpt-4o-mini",
|
|
|
|
|
|
|
|
verbose=False,
|
|
|
|
|
|
|
|
print_on=False,
|
|
|
|
max_loops=1,
|
|
|
|
max_loops=1,
|
|
|
|
)
|
|
|
|
)
|
|
|
|
|
|
|
|
|
|
|
|
product_owner = Agent(
|
|
|
|
product_owner = Agent(
|
|
|
|
agent_name="Product-Owner",
|
|
|
|
agent_name="Product-Owner",
|
|
|
|
agent_description="Product owner with business and technical background",
|
|
|
|
agent_description="Product owner with business and technical background",
|
|
|
|
model_name="gpt-4o",
|
|
|
|
model_name="gpt-4o-mini",
|
|
|
|
|
|
|
|
verbose=False,
|
|
|
|
|
|
|
|
print_on=False,
|
|
|
|
max_loops=1,
|
|
|
|
max_loops=1,
|
|
|
|
)
|
|
|
|
)
|
|
|
|
|
|
|
|
|
|
|
|
qa_engineer = Agent(
|
|
|
|
qa_engineer = Agent(
|
|
|
|
agent_name="QA-Engineer",
|
|
|
|
agent_name="QA-Engineer",
|
|
|
|
agent_description="Quality assurance engineer and testing specialist",
|
|
|
|
agent_description="Quality assurance engineer and testing specialist",
|
|
|
|
model_name="gpt-4o",
|
|
|
|
model_name="gpt-4o-mini",
|
|
|
|
|
|
|
|
verbose=False,
|
|
|
|
|
|
|
|
print_on=False,
|
|
|
|
max_loops=1,
|
|
|
|
max_loops=1,
|
|
|
|
)
|
|
|
|
)
|
|
|
|
|
|
|
|
|
|
|
|
@ -338,8 +380,12 @@ def test_concurrent_workflow_team_collaboration():
|
|
|
|
|
|
|
|
|
|
|
|
assert result is not None
|
|
|
|
assert result is not None
|
|
|
|
assert isinstance(result, list)
|
|
|
|
assert isinstance(result, list)
|
|
|
|
assert len(result) == 4
|
|
|
|
# With default output_type="dict-all-except-first", we get conversation_history[2:]
|
|
|
|
|
|
|
|
assert len(result) >= 1 # At least one agent should succeed
|
|
|
|
for r in result:
|
|
|
|
for r in result:
|
|
|
|
assert isinstance(r, dict)
|
|
|
|
assert isinstance(r, dict)
|
|
|
|
assert "agent" in r
|
|
|
|
assert "role" in r # Agent name is stored in 'role' field
|
|
|
|
assert "output" in r
|
|
|
|
assert "content" in r # Agent output is stored in 'content' field
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
if __name__ == "__main__":
|
|
|
|
|
|
|
|
pytest.main([__file__, "-v"])
|