<?php

namespace App\Notifications;

use App\Services\HubSpot\HubSpotSyncMetrics;
use Illuminate\Bus\Queueable;
use Illuminate\Notifications\Messages\MailMessage;
use Illuminate\Notifications\Notification;

class HubSpotSyncReport extends Notification
{
    use Queueable;

    /**
     * @var HubSpotSyncMetrics
     */
    protected $metrics;

    /**
     * Create a new notification instance.
     *
     * @param HubSpotSyncMetrics $metrics
     */
    public function __construct(HubSpotSyncMetrics $metrics)
    {
        $this->metrics = $metrics;
    }

    /**
     * Get the notification's delivery channels.
     *
     * @param object $notifiable
     * @return array
     */
    public function via(object $notifiable): array
    {
        return ['mail'];
    }

    /**
     * Get the mail representation of the notification.
     *
     * @param object $notifiable
     * @return MailMessage
     */
    public function toMail(object $notifiable): MailMessage
    {
        $isDryRun = $this->metrics->isDryRun();
        $hasErrors = $this->metrics->hasErrors();

        $modePrefix = $isDryRun ? '[DRY-RUN] ' : '';
        $statusEmoji = $hasErrors ? '❌' : '✅';
        $statusText = $hasErrors ? 'With Errors' : 'Success';

        $subject = "{$statusEmoji} {$modePrefix}HubSpot Sync Report - {$statusText}";

        $greeting = $isDryRun
            ? "HubSpot Sync Dry-Run Completed"
            : ($hasErrors ? "HubSpot Sync Completed with Errors" : "HubSpot Sync Completed Successfully");

        $mail = (new MailMessage)
            ->subject($subject)
            ->greeting($greeting);

        // Duration and timestamp
        $mail->line("**Duration:** {$this->metrics->getDurationHuman()}")
             ->line("**Date:** " . ($this->metrics->getStartTime()?->format('Y-m-d H:i:s T') ?? 'N/A'));

        if ($isDryRun) {
            $mail->line("")
                 ->line("⚠️ **This was a dry-run. No actual changes were made.**");
        }

        // Database summary
        $data = $this->metrics->toArray();
        $mail->line("")
             ->line("---")
             ->line("### 📊 Database Summary")
             ->line("- **Committees:** {$data['database']['totalCommittees']}")
             ->line("- **WorkGroups:** {$data['database']['totalWorkGroups']}")
             ->line("- **Active Users:** {$data['database']['totalUsers']}");

        // Lists summary
        $mail->line("")
             ->line("---")
             ->line("### 📋 Lists Summary")
             ->line("- **Created:** {$data['lists']['createdCount']}")
             ->line("- **Deleted:** {$data['lists']['deletedCount']}")
             ->line("- **Processed:** {$data['lists']['processedCount']}");

        // Lists created details
        if (!empty($data['lists']['created'])) {
            $mail->line("")
                 ->line("**Lists Created:**");
            foreach ($data['lists']['created'] as $title) {
                $mail->line("- {$title}");
            }
        }

        // Lists deleted details
        if (!empty($data['lists']['deleted'])) {
            $mail->line("")
                 ->line("**Lists Deleted:**");
            foreach ($data['lists']['deleted'] as $title) {
                $mail->line("- {$title}");
            }
        }

        // Contacts summary
        $mail->line("")
             ->line("---")
             ->line("### 👥 Contacts Summary")
             ->line("- **Added:** {$data['contacts']['totalAdded']}")
             ->line("- **Removed:** {$data['contacts']['totalRemoved']}")
             ->line("- **Kept:** {$data['contacts']['totalKept']}");

        // Contacts added per list
        if (!empty($data['contacts']['added'])) {
            $mail->line("")
                 ->line("**Contacts Added:**");
            foreach ($data['contacts']['added'] as $listTitle => $emails) {
                $count = count($emails);
                if ($count > 0) {
                    $mail->line("- **{$listTitle}:** {$count} contacts");
                    // Show first 5 emails
                    $shown = array_slice($emails, 0, 5);
                    foreach ($shown as $email) {
                        $mail->line("  - {$email}");
                    }
                    if (count($emails) > 5) {
                        $remaining = count($emails) - 5;
                        $mail->line("  - ... and {$remaining} more");
                    }
                }
            }
        }

        // Contacts removed per list
        if (!empty($data['contacts']['removed'])) {
            $mail->line("")
                 ->line("**Contacts Removed:**");
            foreach ($data['contacts']['removed'] as $listTitle => $emails) {
                $count = count($emails);
                if ($count > 0) {
                    $mail->line("- **{$listTitle}:** {$count} contacts");
                    // Show first 5 emails
                    $shown = array_slice($emails, 0, 5);
                    foreach ($shown as $email) {
                        $mail->line("  - {$email}");
                    }
                    if (count($emails) > 5) {
                        $remaining = count($emails) - 5;
                        $mail->line("  - ... and {$remaining} more");
                    }
                }
            }
        }

        // Errors
        if ($hasErrors) {
            $mail->line("")
                 ->line("---")
                 ->line("### ❌ Errors");
            foreach ($data['errors'] as $error) {
                $context = !empty($error['context']) ? " ({$error['context']})" : "";
                $mail->line("- {$error['message']}{$context}");
            }
        }

        // Warnings
        if (!empty($data['warnings'])) {
            $mail->line("")
                 ->line("---")
                 ->line("### ⚠️ Warnings");
            foreach ($data['warnings'] as $warning) {
                $mail->line("- {$warning}");
            }
        }

        $mail->line("")
             ->line("---")
             ->line("This is an automated notification from the HubSpot synchronization system.");

        return $mail;
    }

    /**
     * Get the array representation of the notification.
     *
     * @param object $notifiable
     * @return array
     */
    public function toArray(object $notifiable): array
    {
        return $this->metrics->toArray();
    }
}
