<?php

declare(strict_types=1);

namespace PpPhp\Core\Diagnostics\Formatters;

use PpPhp\Core\Diagnostics\Contracts\DiagnosticFormatterInterface;
use PpPhp\Core\Diagnostics\Results\DiagnosticReport;
use PpPhp\Core\Diagnostics\Severity;

final class CliDiagnosticFormatter implements DiagnosticFormatterInterface
{
    public function format(DiagnosticReport $report): string
    {
        $lines = [];

        $lines[] = '';
        $lines[] = 'PPphp Diagnostics';
        $lines[] = '=================';
        $lines[] = 'Health Score: ' . $report->healthScore() . '%';
        $lines[] = 'Critical: ' . $report->criticalCount()
            . ' | Errors: ' . $report->errorCount()
            . ' | Warnings: ' . $report->warningCount()
            . ' | Info: ' . $report->infoCount();
        $lines[] = '';

        foreach ($report->categorySummary() as $category => $summary) {
            $lines[] = ucfirst((string) $category) . ': ' . $summary['score'] . '%'
                . ' (C:' . $summary['critical']
                . ' E:' . $summary['error']
                . ' W:' . $summary['warning']
                . ' I:' . $summary['info'] . ')';
        }

        $lines[] = '';

        foreach ($report->results() as $result) {
            $lines[] = $result->providerLabel();
            $lines[] = str_repeat('-', strlen($result->providerLabel()));

            if ($result->issues() === []) {
                $lines[] = '  ✔ No issues found.';
                $lines[] = '';
                continue;
            }

            foreach ($result->issues() as $issue) {
                $symbol = match ($issue->severity) {
                    Severity::CRITICAL => '‼',
                    Severity::ERROR => '✖',
                    Severity::WARNING => '⚠',
                    default => 'ℹ',
                };

                $lines[] = '  ' . $symbol . ' ' . $issue->message;

                if ($issue->source !== '') {
                    $lines[] = '    Source: ' . $issue->source;
                }

                if ($issue->suggestion !== '') {
                    $lines[] = '    Suggestion: ' . $issue->suggestion;
                }
            }

            $lines[] = '';
        }

        return implode(PHP_EOL, $lines);
    }
}
