<?php

declare(strict_types=1);

namespace App\Domain\MailServer\Adapters;

use App\Domain\MailServer\Contracts\MailServerAdapter;
use App\Domain\Sysapi\Contracts\SysapiBridge;
use Illuminate\Support\Facades\Mail;

/**
 * Mail server adapter base — ortak lifecycle implementasyonu.
 *
 * Concrete adapter sadece meta + binary paths verir, geri kalan
 * sysapi script'leri üzerinden gelir.
 */
abstract class AbstractMailServerAdapter implements MailServerAdapter
{
    public function __construct(protected readonly SysapiBridge $sysapi) {}

    abstract public function name(): string;

    abstract public function key(): string;

    abstract public function description(): string;

    abstract public function packageName(): string;

    abstract public function serviceName(): string;

    abstract public function strengths(): array;

    abstract public function performanceScore(): int;

    /**
     * Adapter binary paths (servis-bazlı adapter'lar için).
     * Override edilmezse boş array → isInstalled() false döner.
     * @return array<int, string>
     */
    protected function binaryPaths(): array
    {
        return [];
    }

    public function isInstalled(): bool
    {
        foreach ($this->binaryPaths() as $path) {
            if (is_executable($path)) {
                return true;
            }
        }

        return false;
    }

    public function isRunning(): bool
    {
        if (! $this->serviceName()) {
            return false;
        }
        $result = $this->sysapi->run('service-status', ['service' => $this->serviceName()]);

        return $result->ok() && ($result->data['active'] ?? false);
    }

    public function isEnabled(): bool
    {
        if (! $this->serviceName()) {
            return false;
        }
        $result = $this->sysapi->run('service-status', ['service' => $this->serviceName()]);

        return $result->ok() && ($result->data['enabled'] ?? false);
    }

    public function version(): string
    {
        $result = $this->sysapi->run('service-status', ['service' => $this->serviceName()]);

        return (string) ($result->data['version'] ?? $this->name() . '/?');
    }

    public function install(): array
    {
        $result = $this->sysapi->run('mailserver-install', [
            'driver' => $this->key(),
            'package' => $this->packageName(),
            'service' => $this->serviceName(),
        ]);

        return [
            'ok' => $result->ok(),
            'output' => $result->stdout ?: ($result->data['message'] ?? ''),
            'error' => $result->ok() ? null : ($result->stderr ?: 'Kurulum başarısız'),
        ];
    }

    public function uninstall(): array
    {
        $result = $this->sysapi->run('mailserver-uninstall', [
            'driver' => $this->key(),
            'package' => $this->packageName(),
            'service' => $this->serviceName(),
        ]);

        return [
            'ok' => $result->ok(),
            'output' => $result->stdout ?: ($result->data['message'] ?? ''),
        ];
    }

    public function start(): void
    {
        $this->sysapi->run('service-restart', ['service' => $this->serviceName(), 'mode' => 'start']);
    }

    public function stop(): void
    {
        $this->sysapi->run('service-restart', ['service' => $this->serviceName(), 'mode' => 'stop']);
    }

    public function reload(): void
    {
        $this->sysapi->run('service-restart', ['service' => $this->serviceName(), 'mode' => 'reload']);
    }

    public function restart(): void
    {
        $this->sysapi->run('service-restart', ['service' => $this->serviceName(), 'mode' => 'restart']);
    }

    public function enable(): void
    {
        $this->sysapi->run('service-restart', ['service' => $this->serviceName(), 'mode' => 'enable']);
    }

    public function disable(): void
    {
        $this->sysapi->run('service-restart', ['service' => $this->serviceName(), 'mode' => 'disable']);
    }

    public function sendTestMail(string $to, string $from): void
    {
        Mail::raw('Onoxsoft Panel mail server test — ' . $this->name() . ' — ' . now()->toIso8601String(),
            function ($msg) use ($to, $from) {
                $msg->to($to)->from($from)->subject('Onoxsoft ' . $this->name() . ' Test');
            });
    }

    public function queueStatus(): array
    {
        return ['count' => 0, 'oldest_seconds' => null, 'frozen' => 0];
    }

    public function flushQueue(): void
    {
        // Override in concrete adapter
    }

    public function laravelConfig(): array
    {
        return [];
    }
}
