<?php

namespace Daylight\Core\Modules\MediaLibrary\Livewire;

use Daylight\Core\Modules\MediaLibrary\Services\MediaUploadService;
use Illuminate\Support\Facades\Log;
use Illuminate\View\View;
use Livewire\Attributes\On;
use Livewire\Component;
use Livewire\WithFileUploads;

class MediaUploader extends Component
{
    use WithFileUploads;

    public ?int $directoryId = null;

    public array $uploads = [];

    public bool $showModal = false;

    public array $uploadingFiles = [];

    public int $maxFileUploads = 20;

    public function mount(?int $directoryId = null): void
    {
        $this->directoryId = $directoryId;

        // Get PHP's max_file_uploads setting
        $maxUploads = ini_get('max_file_uploads');
        $this->maxFileUploads = $maxUploads !== false ? (int) $maxUploads : 20;
    }

    #[On('open-upload-modal')]
    public function openModal(?int $directoryId = null): void
    {
        if ($directoryId !== null) {
            $this->directoryId = $directoryId;
        }
        $this->showModal = true;
        $this->uploadingFiles = [];
    }

    public function updatedUploads(): void
    {
        // This is called after Livewire finishes uploading files to temp storage
        // Process immediately as files come in
        if (empty($this->uploads)) {
            return;
        }

        // Check if we exceeded PHP's limits
        $maxFileUploads = ini_get('max_file_uploads') ?: 20;
        if (count($this->uploads) > $maxFileUploads) {
            Log::warning('Too many files uploaded at once', [
                'count' => count($this->uploads),
                'max' => $maxFileUploads,
            ]);
        }

        try {
            // Process all uploads sequentially
            $this->processUploadsSequentially();
        } catch (\Exception $e) {
            Log::error('Upload processing failed', [
                'error' => $e->getMessage(),
                'trace' => $e->getTraceAsString(),
            ]);

            // Show error to user
            $this->uploadingFiles = [[
                'name' => 'Error',
                'size' => 0,
                'status' => 'error',
                'progress' => 0,
                'error' => 'Upload failed: ' . $e->getMessage(),
            ]];
            $this->dispatch('$refresh');
        }
    }

    protected function processUploadsSequentially(): void
    {
        $uploadService = app(MediaUploadService::class);

        // Initialize all files as pending first
        $filesToProcess = [];
        foreach ($this->uploads as $file) {
            $filesToProcess[] = $file;
            $this->uploadingFiles[] = [
                'name' => $file->getClientOriginalName(),
                'size' => $file->getSize(),
                'status' => 'pending',
                'progress' => 0,
                'error' => null,
            ];
        }
        $this->dispatch('$refresh');

        // Process files one by one
        foreach ($filesToProcess as $index => $file) {
            // Update status to uploading
            $this->uploadingFiles[$index]['status'] = 'uploading';
            $this->uploadingFiles[$index]['progress'] = 25;
            $this->dispatch('$refresh');

            try {
                // Upload the file
                $media = $uploadService->upload($file, $this->directoryId);

                // Upload processing (conversions, etc)
                $this->uploadingFiles[$index]['progress'] = 75;
                $this->dispatch('$refresh');

                // Complete
                $this->uploadingFiles[$index]['progress'] = 100;
                $this->uploadingFiles[$index]['status'] = 'success';
                $this->dispatch('$refresh');

                $this->dispatch('file-uploaded', id: $media->id);
            } catch (\Exception $e) {
                Log::error('File upload failed: ' . $e->getMessage(), [
                    'file' => $file->getClientOriginalName(),
                    'directory_id' => $this->directoryId,
                    'error' => $e->getMessage(),
                ]);

                // Update status to error
                $this->uploadingFiles[$index]['status'] = 'error';
                $this->uploadingFiles[$index]['progress'] = 0;
                $this->uploadingFiles[$index]['error'] = $e->getMessage();
                $this->dispatch('$refresh');
            }
        }

        // Clear uploads array
        $this->uploads = [];

        // All files processed, clean up
        $this->uploadingFiles = [];
        $this->dispatch('$refresh');
        $this->dispatch('uploads-complete');
        $this->dispatch('refresh-media-grid')->to('daylight::media-file-grid');
    }

    public function closeModalAfterUpload(): void
    {
        $this->showModal = false;
        $this->uploadingFiles = [];
    }

    public function closeModal(): void
    {
        $this->showModal = false;
        $this->uploads = [];
        $this->uploadingFiles = [];
    }

    public function render(): View
    {
        return view('daylight::livewire.media.media-uploader');
    }
}
