#!/usr/bin/env python3
"""
Marketing Content Swarm Generator
Fires 200 agents via OpenRouter to generate marketing content for Sunaiva products.

Usage:
    python marketing_swarm.py

Outputs to: /mnt/e/genesis-system/swarm-output/session24/
"""

import os
import sys
import json
import asyncio
import time
from datetime import datetime
from typing import List, Dict, Any
from dataclasses import dataclass, asdict

try:
    import aiohttp
except ImportError:
    print("ERROR: aiohttp not installed. Install with: pip install aiohttp")
    sys.exit(1)


# Configuration
OPENROUTER_BASE_URL = "https://openrouter.ai/api/v1/chat/completions"
MODEL_ID = "gpt-3.5-turbo"  # Reliable, fast, cheap
BATCH_SIZE = 20  # Parallel requests per batch
REQUEST_TIMEOUT_SECONDS = 120
OUTPUT_DIR = "/mnt/e/genesis-system/swarm-output/session24"

# Marketing content categories (200 total pieces)
CONTENT_TASKS = [
    # 50 LinkedIn posts about AI voice agents for Australian businesses
    *[{
        "category": "linkedin_post",
        "prompt": f"""Write a LinkedIn post (150-200 words) about AI voice agents for Australian businesses.

Focus area: {topic}

Requirements:
- Professional but conversational tone
- Include 1-2 relevant stats or insights
- End with a question or call-to-action
- Use 2-3 relevant hashtags
- Target: Australian business owners, GMs, operations managers
- Brand: Sunaiva (AI voice agents, automation, digital employees)

Write ONLY the post content, ready to copy-paste.""",
        "index": i
    } for i, topic in enumerate([
        "24/7 customer service without hiring",
        "Reducing missed calls and lost revenue",
        "AI receptionists vs human hiring costs",
        "Voice AI for Australian tradie businesses",
        "Appointment booking automation",
        "After-hours call handling",
        "Customer experience with AI voice",
        "Scaling customer support without headcount",
        "AI voice agents for dental practices",
        "Legal practice receptionist automation",
        "Real estate inquiry handling with AI",
        "HVAC service call automation",
        "Plumbing emergency call routing",
        "Electrical business lead qualification",
        "Beauty salon booking automation",
        "Gym membership inquiry handling",
        "Restaurant reservation AI",
        "Medical practice phone triage",
        "Automotive service scheduling",
        "Home services lead capture",
        "Multi-location business phone management",
        "Franchise call center replacement",
        "Small business growth with AI",
        "Voice AI ROI for Australian SMBs",
        "Customer data capture from phone calls",
        "CRM integration with voice AI",
        "Bilingual AI receptionists (English/Mandarin)",
        "Voice AI for multicultural businesses",
        "Reducing receptionist burnout",
        "Call analytics for business insights",
        "Voice AI vs offshore call centers",
        "Australian accent voice AI",
        "Local business automation trends",
        "Digital transformation for tradies",
        "AI voice agent success stories",
        "Customer testimonials from voice AI",
        "Voice AI implementation speed",
        "No-code AI voice setup",
        "Voice AI for busy business owners",
        "Missed call revenue recovery",
        "Lead response time with AI",
        "Customer retention with better service",
        "Voice AI competitive advantage",
        "Future of business phone systems",
        "AI voice agent pricing transparency",
        "White-label voice AI opportunities",
        "Agency partner revenue with voice AI",
        "Building passive income with AI referrals",
        "Voice AI market opportunity Australia",
        "Why Australian businesses need AI now"
    ], start=1)],

    # 50 cold email follow-up sequences (3-email drips) for agency partners
    *[{
        "category": "email_sequence",
        "prompt": f"""Write a 3-email cold outreach sequence for website/marketing agency owners to partner with Sunaiva.

Agency type: {agency_type}

Sequence structure:
EMAIL 1 (Initial): Value prop, credibility, soft CTA
EMAIL 2 (Follow-up day 3): Case study or stat, address objection, CTA
EMAIL 3 (Breakup day 7): Final value reminder, scarcity/urgency, strong CTA

Partnership offer:
- 30% recurring commission on every client
- White-label voice AI widgets for their clients' websites
- $197-$497/month per widget price point
- One agency = 50-200 potential clients = $3K-$15K/month passive income
- Zero technical work required (we handle everything)

Target: {agency_type} owners with 20-100 clients

Write all 3 emails with subject lines. Keep each under 150 words.""",
        "index": i
    } for i, agency_type in enumerate([
        "Web design agencies",
        "Digital marketing agencies",
        "SEO agencies",
        "Social media agencies",
        "WordPress developers",
        "Shopify agencies",
        "E-commerce agencies",
        "Real estate marketing agencies",
        "Healthcare marketing agencies",
        "Legal marketing agencies",
        "Tradie marketing specialists",
        "Local business marketing agencies",
        "Lead generation agencies",
        "Conversion rate optimization agencies",
        "Growth marketing agencies",
        "Content marketing agencies",
        "Video marketing agencies",
        "PPC/Google Ads agencies",
        "Facebook Ads agencies",
        "LinkedIn marketing agencies",
        "Email marketing agencies",
        "Marketing automation agencies",
        "CRM implementation agencies",
        "Sales funnel builders",
        "Landing page agencies",
        "Branding agencies",
        "Creative agencies",
        "Full-service agencies",
        "Boutique marketing firms",
        "Franchise marketing agencies",
        "Multi-location business specialists",
        "White-label marketing providers",
        "Marketing resellers",
        "Agency networks",
        "Marketing consultants",
        "Business coaches",
        "Startup accelerators",
        "Innovation labs",
        "Tech integrators",
        "Software resellers",
        "SaaS agencies",
        "No-code/low-code agencies",
        "Webflow agencies",
        "Wix partners",
        "Squarespace designers",
        "GHL (GoHighLevel) agencies",
        "HubSpot partners",
        "Salesforce consultants",
        "Zoho partners",
        "Australian agency networks"
    ], start=51)],

    # 50 Google Ads copy variations for tradiechatbots.com.au and related domains
    *[{
        "category": "google_ads",
        "prompt": f"""Write Google Ads copy for tradiechatbots.com.au targeting {keyword_theme}.

Ad structure:
HEADLINE 1 (30 chars max): Main hook
HEADLINE 2 (30 chars max): Benefit/feature
HEADLINE 3 (30 chars max): CTA/urgency
DESCRIPTION 1 (90 chars max): Value prop + credibility
DESCRIPTION 2 (90 chars max): Differentiator + CTA

Target audience: {audience}
Pain point: {pain}
Solution: AI voice chatbot/receptionist for tradie websites

Include:
- Australian spelling/terms
- Tradie-specific language
- Price indicator if relevant ($197-$497/month)
- Trust signals (24/7, no missed calls, instant quotes)

Write 3 variations of each component (3 headlines, 3 descriptions).""",
        "index": i
    } for i, (keyword_theme, audience, pain) in enumerate([
        ("24/7 receptionist", "Plumbers", "Missed calls after hours"),
        ("AI chatbot tradies", "Electricians", "Can't answer phone on job sites"),
        ("Automated quotes", "HVAC technicians", "Quote requests outside business hours"),
        ("Lead capture tradies", "Builders", "Losing leads to faster competitors"),
        ("Voice AI plumbers", "Plumbing businesses", "Need receptionist but can't afford one"),
        ("Tradie phone system", "Multi-van operations", "Juggling multiple calls"),
        ("AI receptionist", "Renovation contractors", "Spending too much time on phone"),
        ("Never miss a call", "Roof plumbers", "Emergency calls missed = lost revenue"),
        ("Instant quotes AI", "Kitchen renovators", "Quote requests slow to respond"),
        ("Booking automation", "Air conditioning installers", "Manual booking = admin burden"),
        ("Lead qualification", "Commercial electricians", "Waste time on unqualified leads"),
        ("After hours calls", "Emergency plumbers", "24/7 availability without 24/7 staff"),
        ("Virtual receptionist", "Electrical contractors", "Professional image on a budget"),
        ("Smart phone system", "Solar installers", "Complex quoting process"),
        ("AI voice assistant", "Pool builders", "Seasonal call volume spikes"),
        ("Automated scheduling", "Appliance repair", "Double-bookings and no-shows"),
        ("Customer service AI", "Handyman services", "Can't scale without more staff"),
        ("Voice chatbot", "Bathroom renovators", "Need to capture more details upfront"),
        ("AI call handling", "Gutter cleaners", "Weather-dependent call surges"),
        ("Smart receptionist", "Pest control", "Emergency calls need instant response"),
        ("Lead management AI", "Landscapers", "Seasonal business = inconsistent staffing"),
        ("Quote automation", "Concrete contractors", "Complex pricing = slow quotes"),
        ("Customer engagement", "Painting contractors", "Follow-up calls never happen"),
        ("AI phone assistant", "Tilers", "Phone tag with customers"),
        ("Tradie automation", "Carpenters", "Too busy to answer calls"),
        ("Voice AI website", "Shop fitters", "Website visitors leave without calling"),
        ("Website chatbot", "Locksmith", "Emergency calls = instant booking needed"),
        ("Talking website", "Glass repair", "Mobile site visitors won't call"),
        ("AI voice widget", "Signage companies", "Complex products = lots of questions"),
        ("Smart booking", "Fencing contractors", "Measurement bookings = admin hell"),
        ("Automated inquiry", "Blind installers", "Showroom hours = missed calls"),
        ("AI call center", "Security installers", "Technical questions = need experts"),
        ("Virtual assistant", "Fire protection", "Compliance questions = gatekeeping"),
        ("Phone automation", "Garage door repair", "Emergency calls = immediate dispatch"),
        ("AI customer service", "Gate automation", "Custom projects = qualification needed"),
        ("Smart call routing", "Intercom installers", "Need to route commercial vs residential"),
        ("Voice AI tools", "Cable installers", "Appointment confirmation = manual burden"),
        ("Chatbot for tradies", "Antenna installers", "Weather delays = rebooking nightmare"),
        ("AI receptionist cost", "Solar cleaners", "Receptionist = overhead we can't afford"),
        ("Tradie lead gen", "Window cleaners", "Need more commercial clients"),
        ("Voice AI pricing", "Pressure washing", "Transparent pricing = more bookings"),
        ("AI phone calls", "Rendering contractors", "Quote requests = hours of back-and-forth"),
        ("Automated follow-up", "Waterproofing", "Follow-up = where revenue leaks"),
        ("Smart lead capture", "Underpinning", "Specialized service = education needed"),
        ("AI voice tech", "Scaffolding", "Commercial clients = compliance questions"),
        ("Tradie phone AI", "Demolition", "Safety questions = must answer correctly"),
        ("Voice assistant", "Asbestos removal", "Regulatory info = gatekeeping"),
        ("AI booking system", "Arborists", "Council permits = customer questions"),
        ("Smart call handling", "Stump grinding", "Same-day service = instant booking"),
        ("Tradie growth AI", "Tree removal", "Storm season = call volume 10x")
    ], start=101)],

    # 50 case study outlines for different industries
    *[{
        "category": "case_study",
        "prompt": f"""Write a case study outline for a {industry} business using Sunaiva AI voice agents.

Industry: {industry}
Business type: {business_type}

Structure:
1. CLIENT PROFILE (50 words)
   - Business name (fictional but realistic)
   - Location (Australian city/region)
   - Team size
   - Annual revenue range

2. CHALLENGE (75 words)
   - {challenge_1}
   - {challenge_2}
   - Impact on revenue/operations

3. SOLUTION (100 words)
   - Sunaiva AI voice agent implementation
   - Key features used
   - Integration points (CRM, booking, etc.)
   - Setup time

4. RESULTS (100 words)
   - Quantified outcomes (calls handled, revenue captured, time saved)
   - ROI calculation
   - Qualitative improvements
   - Customer feedback

5. QUOTE (25 words)
   - Testimonial from owner/GM

Make numbers realistic and conservative (real ROI for case study credibility).""",
        "index": i
    } for i, (industry, business_type, challenge_1, challenge_2) in enumerate([
        ("Dental", "2-dentist suburban practice", "90+ calls/day overwhelming reception", "After-hours calls going to voicemail"),
        ("Legal", "3-lawyer family law firm", "New inquiry response time 4-6 hours", "Receptionist overwhelmed during court days"),
        ("Real Estate", "12-agent residential sales team", "Open home inquiries missed on weekends", "Lead response time = competitive disadvantage"),
        ("Beauty", "5-chair salon + 2 beauty therapists", "Booking calls interrupting treatments", "Double-bookings from manual diary"),
        ("HVAC", "6-van air conditioning service", "Emergency calls after 5pm going to voicemail", "Lost $40K+ in after-hours work annually"),
        ("Plumbing", "4-plumber residential business", "On-site techs can't answer calls", "Quote requests taking 24-48hrs"),
        ("Electrical", "Commercial electrical contractor", "Quoting process taking 3-4 days", "Missing out on urgent jobs"),
        ("Accounting", "8-accountant suburban firm", "Tax season call volume unmanageable", "Clients frustrated with hold times"),
        ("Physiotherapy", "3-physio sports injury clinic", "Cancellations not captured = empty slots", "ACC vs private = wrong info given"),
        ("Chiropractic", "2-chiropractor wellness center", "New patient screening taking 15min per call", "Receptionist spending 3hrs/day on calls"),
        ("Veterinary", "3-vet mixed animal practice", "Emergency triage overwhelming reception", "After-hours emergencies = ref to 24hr (lost revenue)"),
        ("Optometry", "2-optometrist independent practice", "Frame selection questions = long calls", "Bulk-billing vs private confusion"),
        ("Gym", "24/7 gym + PT studio", "Membership inquiries outside staffed hours", "Trial bookings = admin burden"),
        ("Cafe", "High-traffic breakfast/lunch spot", "Catering inquiries = phone tag", "Function bookings = complexity"),
        ("Restaurant", "Fine dining 80-seat restaurant", "Reservation management = 2hrs/day", "Special dietary requirements = miscommunication"),
        ("Auto Repair", "4-bay mechanical workshop", "Service bookings vs walk-ins = chaos", "Parts availability questions = time sink"),
        ("Car Detailing", "Mobile + fixed site detailer", "Quote requests = 30min back-and-forth", "Booking confirmations = no-show rate"),
        ("Pet Grooming", "3-groomer salon + hydrobath", "Breed-specific pricing questions", "Appointment reminders = manual texting"),
        ("Florist", "Wedding/events specialist", "Consultation bookings = phone tag", "Seasonal peak (Valentine's, Mother's Day) = overwhelm"),
        ("Photography", "Wedding + portrait photographer", "Package inquiries = 45min calls", "Booking deposits = follow-up burden"),
        ("Cleaning", "12-staff commercial cleaners", "Quote requests = site visit scheduling", "Client complaints = after-hours calls"),
        ("Landscaping", "8-staff design + construct", "Design consults = long qualification", "Seasonal peaks = can't answer calls"),
        ("Pool Maintenance", "6-van weekly service routes", "On-route techs = can't take calls", "Chemical delivery questions = safety critical"),
        ("Pest Control", "4-van residential + commercial", "Emergency calls (spiders, wasps) = instant booking", "Pre-treatment info = compliance requirement"),
        ("Security Systems", "Installation + monitoring", "Technical support calls = expert needed", "Quote complexity = gatekeeper role"),
        ("Interior Design", "2-designer studio", "Initial consult bookings = extensive screening", "Trade client vs retail = different workflows"),
        ("Mortgage Broker", "3-broker firm", "Application inquiries = complex screening", "Document collection = follow-up intensive"),
        ("Financial Planning", "5-advisor practice", "Compliance = careful info gatekeeping", "Appointment booking = AVS integration"),
        ("Insurance Broker", "Commercial + personal lines", "Quote requests = multi-step process", "Claims support = urgent routing"),
        ("Recruitment", "IT + engineering specialist", "Candidate screening = time intensive", "Client job briefs = detailed capture"),
        ("HR Consulting", "5-consultant firm", "Inquiry qualification = expertise matching", "Workshop bookings = complex logistics"),
        ("IT Support", "MSP 200+ SMB clients", "Ticket creation = detail capture critical", "After-hours emergencies = triage needed"),
        ("Web Design", "4-developer + 2-designer agency", "Project inquiries = scoping call needed", "Support requests = client vs prospect routing"),
        ("Marketing Agency", "8-staff full service", "Lead gen inquiries = qualification needed", "Existing client requests = account manager routing"),
        ("Copywriting", "Freelancer + 2 junior writers", "Project briefs = extensive detail", "Overflow inquiries = capacity management"),
        ("Graphic Design", "Print + digital 3-designer studio", "Revision requests = version tracking", "Rush jobs = price negotiation"),
        ("Video Production", "2-videographer + editor", "Wedding inquiries = package complexity", "Corporate clients = multi-stakeholder"),
        ("Event Planning", "Wedding + corporate events", "Venue availability questions", "Vendor coordination = complexity"),
        ("Catering", "Corporate + events 15-staff kitchen", "Dietary requirements = detail critical", "Quote variations = menu complexity"),
        ("Bakery", "Wholesale + retail storefront", "Custom cake inquiries = design consult", "Wholesale orders = account management"),
        ("Butcher", "Traditional + online store", "Custom cuts = specification needed", "Delivery logistics = postcode routing"),
        ("Hardware Store", "Independent 2-location", "Stock availability questions", "Trade account inquiries = credit checks"),
        ("Garden Center", "Plants + landscaping supplies", "Plant care advice = expertise needed", "Delivery = complex logistics"),
        ("Furniture Store", "Custom + retail 2-showrooms", "Custom orders = measurement bookings", "Delivery scheduling = multi-step"),
        ("Mattress Store", "3-location franchise", "Sleep consultation = qualification", "Delivery + old mattress removal = logistics"),
        ("Blinds/Curtains", "Measure + install service", "Measurement bookings = calendar tetris", "Quote follow-ups = conversion critical"),
        ("Tile Showroom", "Commercial + retail", "Sample requests = account setup", "Installation referrals = partner coordination"),
        ("Kitchen Showroom", "Design + supply + install", "Design consult bookings = long qualification", "Quote complexity = multi-stage"),
        ("Bathroom Renovations", "Design + construct", "Project inquiries = budget screening", "Showroom appointments = preparation needed"),
        ("Roofing", "4-crew residential + commercial", "Insurance claims = documentation heavy", "Emergency repairs = instant dispatch")
    ], start=151)]
]


@dataclass
class MarketingResult:
    """Result from a single marketing content generation."""
    agent_id: int
    category: str
    index: int
    status: str
    content: str = None
    error: str = None
    prompt_tokens: int = 0
    completion_tokens: int = 0
    total_tokens: int = 0
    cost_usd: float = 0.0
    response_time_ms: int = 0
    timestamp: str = None

    def __post_init__(self):
        if self.timestamp is None:
            self.timestamp = datetime.now().isoformat()


def load_api_key() -> str:
    """Load OpenRouter API key."""
    api_key = os.getenv('OPENROUTER_API_KEY')
    if api_key:
        return api_key

    credentials_file = "/mnt/e/genesis-system/Credentials/Genesis Credentials additions.txt"
    try:
        with open(credentials_file, 'r') as f:
            for line in f:
                if 'OpenRouter-Genesis-OpenClaw-API-KEY=' in line:
                    return line.split('=')[1].strip()
    except Exception as e:
        print(f"ERROR: Could not read credentials file: {e}")

    print("ERROR: OPENROUTER_API_KEY not found")
    sys.exit(1)


async def generate_content(
    session: aiohttp.ClientSession,
    task: Dict[str, Any],
    agent_id: int,
    api_key: str
) -> MarketingResult:
    """Generate a single piece of marketing content."""
    start_time = time.time()

    headers = {
        "Authorization": f"Bearer {api_key}",
        "Content-Type": "application/json",
        "HTTP-Referer": "https://github.com/genesis-system",
        "X-Title": "Genesis Marketing Swarm"
    }

    payload = {
        "model": MODEL_ID,
        "messages": [
            {"role": "system", "content": "You are an expert marketing copywriter and content strategist. Write compelling, conversion-focused content that drives action. Be authentic, specific, and results-oriented."},
            {"role": "user", "content": task["prompt"]}
        ],
        "temperature": 0.8,
        "max_tokens": 2000
    }

    try:
        timeout = aiohttp.ClientTimeout(total=REQUEST_TIMEOUT_SECONDS)
        async with session.post(OPENROUTER_BASE_URL, json=payload, headers=headers, timeout=timeout) as response:
            response_time_ms = int((time.time() - start_time) * 1000)

            if response.status != 200:
                error_text = await response.text()
                return MarketingResult(
                    agent_id=agent_id,
                    category=task["category"],
                    index=task["index"],
                    status="fail",
                    error=f"HTTP {response.status}: {error_text[:200]}",
                    response_time_ms=response_time_ms
                )

            data = await response.json()
            usage = data.get('usage', {})
            prompt_tokens = usage.get('prompt_tokens', 0)
            completion_tokens = usage.get('completion_tokens', 0)
            total_tokens = usage.get('total_tokens', 0)

            # GPT-3.5-turbo pricing via OpenRouter: ~$0.50/MTok input, ~$1.50/MTok output
            cost_usd = (prompt_tokens / 1_000_000 * 0.5) + (completion_tokens / 1_000_000 * 1.5)

            content = data['choices'][0]['message']['content']

            return MarketingResult(
                agent_id=agent_id,
                category=task["category"],
                index=task["index"],
                status="success",
                content=content,
                prompt_tokens=prompt_tokens,
                completion_tokens=completion_tokens,
                total_tokens=total_tokens,
                cost_usd=cost_usd,
                response_time_ms=response_time_ms
            )

    except asyncio.TimeoutError:
        response_time_ms = int((time.time() - start_time) * 1000)
        return MarketingResult(
            agent_id=agent_id,
            category=task["category"],
            index=task["index"],
            status="fail",
            error=f"Timeout after {REQUEST_TIMEOUT_SECONDS}s",
            response_time_ms=response_time_ms
        )
    except Exception as e:
        response_time_ms = int((time.time() - start_time) * 1000)
        return MarketingResult(
            agent_id=agent_id,
            category=task["category"],
            index=task["index"],
            status="fail",
            error=str(e)[:200],
            response_time_ms=response_time_ms
        )


async def execute_swarm(tasks: List[Dict[str, Any]], api_key: str) -> List[MarketingResult]:
    """Execute all content generation tasks in batches."""
    results = []
    total_tasks = len(tasks)

    async with aiohttp.ClientSession() as session:
        for i in range(0, total_tasks, BATCH_SIZE):
            batch = tasks[i:i + BATCH_SIZE]
            batch_num = (i // BATCH_SIZE) + 1
            total_batches = (total_tasks + BATCH_SIZE - 1) // BATCH_SIZE

            print(f"Batch {batch_num}/{total_batches}: Processing {len(batch)} pieces...")

            batch_results = await asyncio.gather(
                *[generate_content(session, task, i + j + 1, api_key) for j, task in enumerate(batch)]
            )

            results.extend(batch_results)

            successes = len([r for r in batch_results if r.status == "success"])
            failures = len([r for r in batch_results if r.status == "fail"])
            print(f"  ✅ {successes} success, ❌ {failures} failed")

            # Small delay between batches
            if i + BATCH_SIZE < total_tasks:
                await asyncio.sleep(2)

    return results


def save_results(results: List[MarketingResult]):
    """Save results by category to separate files."""
    os.makedirs(OUTPUT_DIR, exist_ok=True)

    # Group by category
    by_category = {}
    for r in results:
        if r.category not in by_category:
            by_category[r.category] = []
        by_category[r.category].append(r)

    # Save each category
    for category, items in by_category.items():
        output_file = f"{OUTPUT_DIR}/{category}.jsonl"
        with open(output_file, 'w') as f:
            for item in items:
                f.write(json.dumps(asdict(item)) + '\n')
        print(f"  Saved {len(items)} {category} items to {output_file}")

    # Save summary report
    total_agents = len(results)
    successes = len([r for r in results if r.status == "success"])
    failures = len([r for r in results if r.status == "fail"])
    total_tokens = sum(r.total_tokens for r in results)
    total_cost = sum(r.cost_usd for r in results)
    avg_time = sum(r.response_time_ms for r in results) / total_agents if total_agents > 0 else 0

    report = f"""# Marketing Swarm Execution Report

**Generated:** {datetime.now().isoformat()}
**Model:** {MODEL_ID}

## Summary

| Metric | Value |
|--------|-------|
| Total Pieces Generated | {total_agents} |
| Successful | {successes} ({successes/total_agents*100:.1f}%) |
| Failed | {failures} |
| Total Tokens | {total_tokens:,} |
| Total Cost | ${total_cost:.4f} |
| Average Response Time | {avg_time:.0f}ms |

## Category Breakdown

| Category | Count | Successes | Failures |
|----------|-------|-----------|----------|
"""

    for category, items in sorted(by_category.items()):
        cat_success = len([i for i in items if i.status == "success"])
        cat_fail = len([i for i in items if i.status == "fail"])
        report += f"| {category} | {len(items)} | {cat_success} | {cat_fail} |\n"

    report += f"""

## Output Files

"""
    for category in sorted(by_category.keys()):
        report += f"- `{OUTPUT_DIR}/{category}.jsonl`\n"

    report += f"""

## Failed Items

"""
    failed = [r for r in results if r.status == "fail"]
    if failed:
        for r in failed:
            report += f"- {r.category} #{r.index}: {r.error}\n"
    else:
        report += "None! All content generated successfully.\n"

    report_file = f"{OUTPUT_DIR}/EXECUTION_REPORT.md"
    with open(report_file, 'w') as f:
        f.write(report)

    print(f"\n{'='*80}")
    print("MARKETING SWARM COMPLETE")
    print(f"{'='*80}")
    print(f"Total Pieces: {total_agents}")
    print(f"Successes: {successes} ({successes/total_agents*100:.1f}%)")
    print(f"Failures: {failures}")
    print(f"Total Cost: ${total_cost:.4f}")
    print(f"Average Time: {avg_time:.0f}ms")
    print(f"\nReport: {report_file}")
    print(f"{'='*80}\n")


async def main():
    """Main orchestrator."""
    print(f"\n{'='*80}")
    print("GENESIS MARKETING SWARM - 200 AGENT DEPLOYMENT")
    print(f"{'='*80}")
    print(f"Timestamp: {datetime.now().isoformat()}")
    print(f"Model: {MODEL_ID}")
    print(f"Batch Size: {BATCH_SIZE}")
    print(f"Total Tasks: {len(CONTENT_TASKS)}")
    print(f"Output: {OUTPUT_DIR}")
    print(f"{'='*80}\n")

    api_key = load_api_key()
    print(f"✅ OpenRouter API key loaded\n")

    print(f"📝 Executing {len(CONTENT_TASKS)} content generation tasks...\n")
    results = await execute_swarm(CONTENT_TASKS, api_key)

    print(f"\n💾 Saving results...\n")
    save_results(results)


if __name__ == "__main__":
    asyncio.run(main())
