#!/usr/bin/env python3
"""
Luzia Status System - Integration Example

This example demonstrates how to integrate the status publishing system
into your orchestrator code. Each section shows the 7 key integration points.

Copy these patterns into your existing code wherever you dispatch tasks,
monitor progress, or handle completion/failures.
"""

import time
import uuid
import asyncio
import logging
from pathlib import Path
from typing import Optional

# Setup logging
logging.basicConfig(level=logging.INFO)
logger = logging.getLogger(__name__)

# Import the sync wrapper (works in both async and sync contexts)
from luzia_status_sync_wrapper import get_sync_publisher


class TaskDispatcherWithStatus:
    """Example task dispatcher with integrated status publishing"""

    def __init__(self):
        self.publisher = get_sync_publisher()

    def dispatch_task(self, project: str, description: str, estimated_duration: int = 600):
        """
        Example 1: Publish task started
        Location: In your task dispatcher when you create a new task
        """
        task_id = f"{project}-{uuid.uuid4().hex[:8]}"

        logger.info(f"Dispatching task: {task_id}")

        # PUBLISHING POINT #1: Task Started
        self.publisher.publish_task_started(
            task_id=task_id,
            project=project,
            description=description,
            estimated_duration_seconds=estimated_duration
        )

        return task_id

    def monitor_task_progress(self, task_id: str, project: str, total_steps: int = 4):
        """
        Example 2 & 5: Publish progress updates and warnings
        Location: In your main task execution loop
        """
        start_time = time.time()
        step_names = ["Analyzing", "Processing", "Validating", "Finalizing"]

        for step_num, step_name in enumerate(step_names, 1):
            logger.info(f"  Step {step_num}/{total_steps}: {step_name}")

            # Simulate work
            time.sleep(2)

            elapsed = int(time.time() - start_time)
            progress = int((step_num / total_steps) * 100)

            # PUBLISHING POINT #2: Progress Update
            # Do this every 30 seconds or at significant milestones
            self.publisher.publish_progress(
                task_id=task_id,
                progress_percent=progress,
                current_step=step_num,
                total_steps=total_steps,
                current_step_name=step_name,
                elapsed_seconds=elapsed,
                estimated_remaining_seconds=int((600 - elapsed) * (100 - progress) / 100)
            )

            # PUBLISHING POINT #5: Warning (if approaching time limit)
            if elapsed > 480:  # 80% of 600 second budget
                remaining = int(600 - elapsed)
                if remaining < 120:  # Less than 2 minutes left
                    self.publisher.publish_warning(
                        task_id=task_id,
                        warning_type="DURATION_EXCEEDED",
                        message=f"Task approaching time limit: {remaining}s remaining",
                        current_step=step_num,
                        total_steps=total_steps,
                        current_step_name=step_name,
                        elapsed_seconds=elapsed,
                        progress_percent=progress,
                        recommendation="May need optimization or extension"
                    )

    def complete_task(self, task_id: str, project: str, elapsed_secs: int, findings: list):
        """
        Example 3: Publish task completed
        Location: When task finishes successfully
        """
        logger.info(f"Task completed: {task_id}")

        # PUBLISHING POINT #3: Task Completed
        self.publisher.publish_task_completed(
            task_id=task_id,
            elapsed_seconds=elapsed_secs,
            findings_count=len(findings),
            recommendations_count=1,  # Number of recommendations
            status="APPROVED"  # or NEEDS_WORK, REJECTED
        )

    def fail_task(self, task_id: str, error: str, elapsed_secs: int, retry_count: int):
        """
        Example 6: Publish task failed
        Location: In your error handler
        """
        logger.error(f"Task failed: {task_id}")

        # PUBLISHING POINT #6: Task Failed
        self.publisher.publish_task_failed(
            task_id=task_id,
            error=error,
            elapsed_seconds=elapsed_secs,
            retry_count=retry_count,
            retriable=retry_count < 5  # Can be retried?
        )


class QueueManagerWithStatus:
    """Example queue manager with integrated status publishing"""

    def __init__(self):
        self.publisher = get_sync_publisher()
        self.queue = []

    def queue_task(self, task_id: str, project: str, description: str, reason: str, wait_estimate: int):
        """
        Example 4: Publish task queued
        Location: In your queue manager when adding to queue
        """
        queue_position = len(self.queue) + 1

        logger.info(f"Queuing task: {task_id} (position {queue_position})")

        # PUBLISHING POINT #4: Task Queued
        self.publisher.publish_task_queued(
            task_id=task_id,
            project=project,
            description=description,
            reason=reason,  # Why it was queued
            queue_position=queue_position,
            queue_ahead=[t['id'] for t in self.queue],  # Tasks ahead in queue
            estimated_wait_seconds=wait_estimate
        )

        self.queue.append({
            'id': task_id,
            'project': project,
            'description': description
        })


class SystemMonitorWithStatus:
    """Example system monitor with integrated status publishing"""

    def __init__(self):
        self.publisher = get_sync_publisher()

    def check_system_health(self):
        """
        Example 7: Publish system alert
        Location: In your system health monitor
        """
        import psutil

        # Check memory
        memory_percent = psutil.virtual_memory().percent
        if memory_percent > 80:
            # PUBLISHING POINT #7: System Alert
            self.publisher.publish_system_alert(
                alert_type="RESOURCE_WARNING",
                message=f"Memory usage at {memory_percent}%",
                recommendation="New tasks will be queued until memory is freed",
                severity="warning"
            )

        # Check disk
        disk_percent = psutil.disk_usage('/').percent
        if disk_percent > 90:
            self.publisher.publish_system_alert(
                alert_type="DISK_CRITICAL",
                message=f"Disk usage at {disk_percent}%",
                recommendation="Immediate cleanup required",
                severity="critical"
            )


# Example usage
def example_task_lifecycle():
    """
    Demonstrate the complete task lifecycle with status publishing

    This shows all 7 integration points in action
    """
    dispatcher = TaskDispatcherWithStatus()
    queue_manager = QueueManagerWithStatus()
    monitor = SystemMonitorWithStatus()

    # Example 1: Dispatch a task
    task_id = dispatcher.dispatch_task(
        project="musica",
        description="Fix audio synthesis engine",
        estimated_duration=600
    )

    try:
        # Example 2 & 5: Monitor progress (with warnings)
        dispatcher.monitor_task_progress(task_id, "musica")

        # Example 3: Complete the task
        dispatcher.complete_task(
            task_id=task_id,
            project="musica",
            elapsed_secs=615,
            findings=["Issue A", "Issue B"]
        )

    except Exception as e:
        # Example 6: Handle failures
        dispatcher.fail_task(
            task_id=task_id,
            error=str(e),
            elapsed_secs=300,
            retry_count=1
        )


def example_queue_management():
    """Demonstrate queuing with status publishing"""
    queue_manager = QueueManagerWithStatus()

    # Example 4: Queue a task (when system is busy)
    queue_manager.queue_task(
        task_id="admin-code-001",
        project="admin",
        description="Code review and cleanup",
        reason="System resource limit reached",
        wait_estimate=300
    )


def example_system_monitoring():
    """Demonstrate system monitoring with alerts"""
    monitor = SystemMonitorWithStatus()

    # Example 7: Check system health
    try:
        monitor.check_system_health()
    except ImportError:
        logger.warning("psutil not available, skipping system check")


# Integration Points Summary
"""
To integrate into your orchestrator, add the following 7 calls:

1. Task Dispatcher (when creating task):
   publisher.publish_task_started(task_id, project, description, estimated_duration)

2. Progress Loop (every 30 seconds):
   publisher.publish_progress(task_id, progress_percent, current_step, total_steps,
                            current_step_name, elapsed_seconds, estimated_remaining)

3. Task Completion (when task succeeds):
   publisher.publish_task_completed(task_id, elapsed_seconds, findings_count, status)

4. Queue Manager (when queueing task):
   publisher.publish_task_queued(task_id, project, description, reason,
                                 queue_position, queue_ahead, wait_estimate)

5. Resource Monitor (when warning threshold exceeded):
   publisher.publish_warning(task_id, warning_type, message, current_step,
                            total_steps, current_step_name, elapsed_seconds,
                            progress_percent, recommendation)

6. Error Handler (when task fails):
   publisher.publish_task_failed(task_id, error, elapsed_seconds,
                                retry_count, retriable)

7. System Monitor (on health issues):
   publisher.publish_system_alert(alert_type, message, recommendation, severity)

Each call is idempotent and safe to use in production.
"""

if __name__ == "__main__":
    print("\n" + "=" * 60)
    print("LUZIA STATUS INTEGRATION EXAMPLES")
    print("=" * 60)

    print("\n1. Task Lifecycle Example:")
    print("-" * 60)
    example_task_lifecycle()

    print("\n2. Queue Management Example:")
    print("-" * 60)
    example_queue_management()

    print("\n3. System Monitoring Example:")
    print("-" * 60)
    example_system_monitoring()

    print("\n" + "=" * 60)
    print("Integration complete - status events published")
    print("=" * 60)
