<?php

declare(strict_types=1);

namespace App\Console\Commands;

use App\Enums\SupportCenter\SupportCenterCheckSeverity;
use App\Services\SupportCenter\SupportCenterCheckOutputSanitizer;
use App\Services\SupportCenter\SupportCenterCheckReport;
use App\Services\SupportCenter\SupportCenterCheckRow;
use App\Services\SupportCenter\SupportCenterPostInstallCheckService;
use App\Services\SupportCenter\SupportCenterReleasePackageCheckService;
use Illuminate\Console\Command;

final class DberpSupportCenterCheckCommand extends Command
{
    protected $signature = 'dberp:support-center:check
                            {--release : 执行官方发布包交付自检}
                            {--post-install : 执行安装后就绪自检}
                            {--remote : 追加远程连通性探测（默认仅本地检查）}';

    protected $description = 'DBErp 官方支撑中心发布包/安装后自检（默认不访问远程 Support Center）';

    public function handle(
        SupportCenterReleasePackageCheckService $releasePackageCheckService,
        SupportCenterPostInstallCheckService $postInstallCheckService,
        SupportCenterCheckOutputSanitizer $outputSanitizer,
    ): int {
        $includeRemote = (bool) $this->option('remote');
        $runRelease = (bool) $this->option('release');
        $runPostInstall = (bool) $this->option('post-install');

        if (! $runRelease && ! $runPostInstall) {
            $runRelease = true;
            $runPostInstall = true;
        }

        $exitCode = self::SUCCESS;

        if ($runRelease) {
            $report = $releasePackageCheckService->run($includeRemote);
            $this->renderReport('【发布包自检】', $report, $outputSanitizer);

            if ($report->hasErrors()) {
                $exitCode = self::FAILURE;
            }
        }

        if ($runPostInstall) {
            if ($runRelease) {
                $this->newLine();
            }

            $report = $postInstallCheckService->run($includeRemote);
            $this->renderReport('【安装后就绪自检】', $report, $outputSanitizer);

            if ($report->hasErrors()) {
                $exitCode = self::FAILURE;
            }
        }

        $this->newLine();
        $this->line($exitCode === self::SUCCESS
            ? '自检完成：未发现阻塞项。'
            : '自检完成：存在 ERROR 级别问题，请根据原因码处理。');

        return $exitCode;
    }

    private function renderReport(
        string $title,
        SupportCenterCheckReport $report,
        SupportCenterCheckOutputSanitizer $outputSanitizer,
    ): void {
        $this->line($title);

        foreach ($report->rows() as $row) {
            $this->renderRow($row, $outputSanitizer);
        }

        $reasonCodes = $report->reasonCodes();

        if ($reasonCodes !== []) {
            $this->line('原因码：'.implode(', ', $reasonCodes));
        }

        $this->line('安装包就绪：'.($report->isPackageReady() ? '是' : '否'));
    }

    private function renderRow(
        SupportCenterCheckRow $row,
        SupportCenterCheckOutputSanitizer $outputSanitizer,
    ): void {
        $prefix = match ($row->severity) {
            SupportCenterCheckSeverity::Ok => '[OK]   ',
            SupportCenterCheckSeverity::Warn => '[WARN] ',
            SupportCenterCheckSeverity::Error => '[ERROR]',
        };

        $line = $prefix.' '.$row->label;

        if ($row->reasonCode !== null && $row->reasonCode !== '') {
            $line .= ' ['.$row->reasonCode.']';
        }

        $this->line($line);

        $detail = $outputSanitizer->sanitize($row->detail);

        if ($detail !== null && $detail !== '') {
            $this->line('       详情：'.$detail);
        }
    }
}
