<?php
declare(strict_types=1);

namespace PpPhp\Core\Platform\Event\Retry\Validation;

use RuntimeException;
use PpPhp\Core\Platform\Event\Queue\DeferredEvent;
use PpPhp\Core\Platform\Event\Retry\Policy\ExponentialBackoffPolicy;
use PpPhp\Core\Platform\Event\Retry\RetryContext;
use PpPhp\Core\Platform\Event\Retry\RetryRuntime;

final class RetryVerifier
{
    public function verify(): array
    {
        $runtime = new RetryRuntime();

        $success = $runtime->execute(DeferredEvent::fromEvent('retry.success'), static function (): void {});
        $retry = $runtime->execute(DeferredEvent::fromEvent('retry.retry'), static function (): void { throw new RuntimeException('transient'); }, 'immediate', 3);
        $dead = $runtime->execute(DeferredEvent::fromArray(['eventName' => 'retry.dead', 'attempts' => 2]), static function (): void { throw new RuntimeException('final'); }, 'immediate', 3);

        $policy = new ExponentialBackoffPolicy(2, 30);
        $delay = $policy->nextDelaySeconds(new RetryContext(DeferredEvent::fromEvent('retry.delay'), 2, 3));

        $checks = [
            'success' => $success->ok(),
            'retryScheduled' => $retry->retryScheduled(),
            'deadLetter' => $dead->deadLettered() && $runtime->deadLetters()->count() === 1,
            'policies' => count($runtime->policies()->names()) >= 4,
            'backoff' => $delay === 4,
        ];

        $issues = [];
        foreach ($checks as $check => $ok) {
            if (!$ok) { $issues[] = ['check' => $check, 'message' => 'Retry verification failed: ' . $check]; }
        }

        return [
            'ok' => !in_array(false, $checks, true),
            'checks' => $checks,
            'issues' => $issues,
            'summary' => [
                'policies' => count($runtime->policies()->names()),
                'deadLetters' => $runtime->deadLetters()->count(),
                'score' => in_array(false, $checks, true) ? 80 : 100,
            ],
        ];
    }
}
