<?php

declare(strict_types=1);

require_once __DIR__ . '/../../vendor/autoload.php';

use App\Framework\Core\AppBootstrapper;
use App\Framework\Core\ValueObjects\Duration;
use App\Framework\DateTime\SystemClock;
use App\Framework\DateTime\SystemHighResolutionClock;
use App\Framework\Performance\EnhancedPerformanceCollector;
use App\Framework\Performance\MemoryMonitor;
use App\Framework\Queue\Queue;
use App\Framework\Queue\ValueObjects\JobPayload;
use App\Framework\Scheduler\Schedules\IntervalSchedule;
use App\Framework\Scheduler\Services\SchedulerService;

echo "🔄 Testing Scheduler + Queue Integration\n";
echo "=======================================\n\n";

try {
    // Bootstrap framework
    $clock = new SystemClock();
    $highResClock = new SystemHighResolutionClock();
    $memoryMonitor = new MemoryMonitor();
    $collector = new EnhancedPerformanceCollector($clock, $highResClock, $memoryMonitor, enabled: false);

    $bootstrapper = new AppBootstrapper(__DIR__ . '/../..', $collector, $memoryMonitor);
    $container = $bootstrapper->bootstrapWorker();

    $scheduler = $container->get(SchedulerService::class);
    $queue = $container->get(Queue::class);

    echo "✅ Framework bootstrapped successfully\n";
    echo "✅ SchedulerService retrieved\n";
    echo "✅ Queue service retrieved\n\n";

    // Test 1: Create a test job object
    $testJob = new class () {
        public function handle(): void
        {
            echo "🔥 Queue Job executed at " . date('Y-m-d H:i:s') . "\n";
            file_put_contents('/tmp/queue-job-executed.txt', date('Y-m-d H:i:s') . "\n", FILE_APPEND);
        }

        public function getType(): string
        {
            return 'test-queue-job';
        }

        public function toArray(): array
        {
            return ['type' => $this->getType(), 'created_at' => date('c')];
        }
    };

    // Test 2: Schedule a task that queues a job
    echo "📋 Test 1: Scheduling task that queues background jobs\n";
    echo "----------------------------------------------------\n";

    $intervalSchedule = IntervalSchedule::every(Duration::fromSeconds(15));
    $scheduler->schedule('queue-dispatcher', $intervalSchedule, function () use ($queue, $testJob) {
        echo "📤 Scheduler dispatching job to queue at " . date('Y-m-d H:i:s') . "\n";
        $jobPayload = JobPayload::immediate($testJob);
        $queue->push($jobPayload);

        return ['status' => 'job_queued', 'timestamp' => time()];
    });

    echo "✅ Scheduled task that dispatches to queue\n\n";

    // Test 3: Check if there are due scheduler tasks
    echo "📋 Test 2: Checking due scheduler tasks\n";
    echo "--------------------------------------\n";

    $dueTasks = $scheduler->getDueTasks();
    echo "📊 Due scheduler tasks: " . count($dueTasks) . "\n";

    if (count($dueTasks) > 0) {
        echo "✅ Found due tasks, executing...\n";
        $results = $scheduler->executeDueTasks();

        foreach ($results as $result) {
            echo "  • Task: {$result->taskId}\n";
            echo "    Success: " . ($result->success ? 'Yes' : 'No') . "\n";
            if ($result->result) {
                echo "    Result: " . json_encode($result->result) . "\n";
            }
        }
    } else {
        echo "ℹ️  No scheduler tasks due right now\n";
    }
    echo "\n";

    // Test 4: Check queue status
    echo "📋 Test 3: Checking queue status\n";
    echo "-------------------------------\n";

    // Try to get queue statistics (if available)
    echo "📊 Queue Status:\n";

    // Check if there are any jobs in queue
    try {
        // This might not exist, but let's see what queue methods are available
        $reflection = new ReflectionClass($queue);
        $methods = $reflection->getMethods(ReflectionMethod::IS_PUBLIC);

        echo "📋 Available Queue Methods:\n";
        foreach ($methods as $method) {
            if (! $method->isConstructor() && ! $method->isDestructor()) {
                echo "  • {$method->getName()}\n";
            }
        }
    } catch (Exception $e) {
        echo "⚠️  Could not inspect queue methods: " . $e->getMessage() . "\n";
    }
    echo "\n";

    // Test 5: Try to process queue (if method exists)
    echo "📋 Test 4: Attempting to process queue\n";
    echo "-------------------------------------\n";

    try {
        // Check if queue has a process method
        if (method_exists($queue, 'process')) {
            echo "✅ Queue has process method, attempting to process jobs...\n";
            $queue->process();
        } elseif (method_exists($queue, 'work')) {
            echo "✅ Queue has work method, attempting to work queue...\n";
            $queue->work();
        } elseif (method_exists($queue, 'pop')) {
            echo "✅ Queue has pop method, attempting to pop job...\n";
            $jobPayload = $queue->pop();
            if ($jobPayload) {
                echo "✅ Found job payload, executing job...\n";
                $job = $jobPayload->job;
                if (method_exists($job, 'handle')) {
                    $job->handle();
                } else {
                    echo "⚠️  Job object doesn't have handle method\n";
                }
            } else {
                echo "ℹ️  No jobs in queue\n";
            }
        } else {
            echo "⚠️  Queue doesn't have standard processing methods\n";
        }
    } catch (Exception $e) {
        echo "❌ Queue processing failed: " . $e->getMessage() . "\n";
    }
    echo "\n";

    // Test 6: Integration results
    echo "📊 Integration Test Results:\n";
    echo "===========================\n";
    echo "✅ Scheduler can schedule tasks\n";
    echo "✅ Scheduler can execute due tasks\n";
    echo "✅ Queue service is accessible\n";

    // Check if integration file was created
    if (file_exists('/tmp/queue-job-executed.txt')) {
        echo "✅ Queue job execution verified (log file created)\n";
        $content = file_get_contents('/tmp/queue-job-executed.txt');
        echo "📄 Job execution log:\n";
        echo $content;
    } else {
        echo "⚠️  No queue job execution detected\n";
    }

} catch (Exception $e) {
    echo "❌ Integration test failed: " . $e->getMessage() . "\n";
    echo "Stack trace:\n" . $e->getTraceAsString() . "\n";
    exit(1);
}

echo "\n🎯 Scheduler + Queue integration test completed!\n";
