<?php
namespace EasyChat\Library\Email;

final class EmailHealthService {
    private $registry;
    public function __construct($registry = null) { $this->registry = $registry; }

    public function check(array $config): array {
        $inbound = $this->checkInbound($config);
        $outbound = $this->checkOutbound($config);
        $deliverability = (new EmailDeliverabilityAdvisor())->advise($config, $outbound);
        $senderRecommendation = (new EmailSenderAddressAdvisor())->advise($config, $outbound);
        return array(
            'success'=>!empty($inbound['success']) && !empty($outbound['success']),
            'activation_ready'=>!empty($inbound['success']) && !empty($outbound['success']),
            'inbound'=>$inbound,
            'outbound'=>$outbound,
            'deliverability'=>$deliverability,
            'sender_recommendation'=>$senderRecommendation,
        );
    }

    private function checkInbound(array $config): array {
        try {
            (new ImapConnector())->testConnection($config);
            return array('success'=>true,'status'=>'ready','code'=>'imap_ready','message'=>'Получение писем работает.');
        } catch (\Throwable $e) {
            $code = preg_replace('/[^a-z0-9_\-]/i', '', $e->getMessage());
            if ($code === 'imap_command_failed') {
                $message = ($config['provider_id'] ?? '') === 'yandex'
                    ? 'Яндекс отклонил вход. Включите IMAP и проверьте пароль приложения.'
                    : 'Почтовый сервис отклонил вход. Проверьте логин, пароль приложения и доступ для почтовых клиентов.';
                $code = 'imap_auth_failed';
            } else {
                $message = 'Не удалось подключиться к IMAP по защищённому соединению. Проверьте сервер и порт 993.';
            }
            return array('success'=>false,'status'=>'error','code'=>$code ?: 'imap_failed','message'=>$message);
        }
    }

    private function checkOutbound(array $config): array {
        $selected = (string)($config['outbound_transport'] ?? 'auto');
        if ($selected === 'cms_mail' && $this->hasFreshCmsBridge()) {
            $snapshot=$this->cmsBridgeSnapshot();$capabilities=(array)($snapshot['capabilities']??array());
            return array('success'=>true,'status'=>'ready','code'=>'cms_mail_ready','transport'=>'cms_mail','sender_email'=>(string)($capabilities['sender_email']??''),'selection_mode'=>'manual','requested_transport'=>'cms_mail','rejected_transports'=>array(),'verified_alternatives'=>array(),'message'=>'Почтовая система сайта поддерживает ответы и цепочки писем.');
        }
        try {
            $result = (new OutboundMailTransportResolver($this->registry))->probe($config);
        } catch (\Throwable $e) {
            $result = array('success'=>false,'status'=>'error','code'=>preg_replace('/[^a-z0-9_\-]/i','',$e->getMessage()));
        }
        $code = (string)($result['code'] ?? 'outbound_failed');
        if (empty($result['success']) && $selected === 'auto' && $this->hasFreshCmsBridge()) {
            $snapshot=$this->cmsBridgeSnapshot();$capabilities=(array)($snapshot['capabilities']??array());
            return array('success'=>true,'status'=>'ready','code'=>'cms_mail_available','transport'=>'cms_mail','sender_email'=>(string)($capabilities['sender_email']??''),'selection_mode'=>'auto','requested_transport'=>'auto','rejected_transports'=>array('direct_smtp'=>$code),'verified_alternatives'=>array(),'message'=>'Ответы будут передаваться проверенной почтовой системе сайта.');
        }
        $messages = array(
            'smtp_ready'=>'SMTP принимает учётные данные по TLS.',
            'smtp_bz_ready'=>'SMTP.BZ подтвердил API-ключ и домен отправителя.',
            'local_relay_ready'=>'Локальная почтовая система хостинга доступна.',
            'cms_mail_ready'=>'Почтовая система сайта готова принимать ответы.',
            'external_smtp_intercepted'=>'Хостинг перенаправляет внешний SMTP. Выберите почту сайта или локальную почту хостинга.',
            'smtp_tls_identity_mismatch'=>'Сертификат SMTP не принадлежит указанному серверу. Безопасное соединение отклонено.',
            'smtp_connect_failed'=>'Хостинг не разрешает соединение с внешним SMTP.',
            'smtp_rejected'=>'SMTP отклонил логин или пароль приложения.',
            'smtp_bz_auth_failed'=>'SMTP.BZ отклонил API-ключ.',
            'smtp_bz_domain_unverified'=>'Домен отправителя ещё не подтверждён в SMTP.BZ.',
            'local_relay_unavailable'=>'Локальная почтовая система хостинга недоступна.',
            'cms_mail_bridge_unavailable'=>'Почтовая система CMS недоступна в текущем планировщике.',
        );
        $result['message'] = $messages[$code] ?? (!empty($result['success']) ? 'Отправка ответов готова.' : 'Не удалось подготовить отправку ответов. Проверьте способ отправки.');
        return $result;
    }

    private function hasFreshCmsBridge(): bool {
        $snapshot=$this->cmsBridgeSnapshot();
        return CmsMailBridgeHealth::supportsRequiredHeaders((array)($snapshot['capabilities'] ?? array()));
    }
    private function cmsBridgeSnapshot(): array {return $this->registry?(new CmsMailBridgeHealth($this->registry))->latest():array();}
}
