<?php

namespace App\Livewire\Backup;

use App\Models\Backup;
use App\Services\BackupService;
use Illuminate\Foundation\Auth\Access\AuthorizesRequests;
use Livewire\Component;
use Livewire\WithFileUploads;

class BackupRestoreIndex extends Component
{
    use WithFileUploads, AuthorizesRequests;

    public bool $showRestoreModal = false;
    public $uploadedZip;

    public function createBackup(string $type, BackupService $backupService): void
    {
        $this->authorize('create', Backup::class);

        try {
            $backup = $backupService->createBackup($type);
            session()->flash('toast', ['type' => 'success', 'message' => "File backup ({$type}) berhasil dibuat: {$backup->file_name}"]);
        } catch (\Throwable $e) {
            session()->flash('toast', ['type' => 'error', 'message' => "Gagal membuat backup: " . $e->getMessage()]);
        }
    }

    public function downloadBackup(int $id)
    {
        $this->authorize('viewAny', Backup::class);
        $backup = Backup::findOrFail($id);

        $filePath = storage_path('app/' . $backup->file_path);
        if (!file_exists($filePath)) {
            session()->flash('toast', ['type' => 'error', 'message' => 'File backup tidak ditemukan di server.']);
            return;
        }

        return response()->download($filePath, $backup->file_name);
    }

    public function restoreBackup(int $id, BackupService $backupService): void
    {
        $this->authorize('restore', Backup::class);

        try {
            $backup = Backup::findOrFail($id);
            $backupService->restoreBackup($backup);
            session()->flash('toast', ['type' => 'success', 'message' => "Database berhasil dipulihkan dari {$backup->file_name}."]);
        } catch (\Throwable $e) {
            session()->flash('toast', ['type' => 'error', 'message' => "Gagal memulihkan database: " . $e->getMessage()]);
        }
    }

    public function openRestoreModal(): void
    {
        $this->authorize('restore', Backup::class);
        $this->uploadedZip = null;
        $this->showRestoreModal = true;
    }

    public function processRestoreUploadedZip(BackupService $backupService): void
    {
        $this->authorize('restore', Backup::class);

        $this->validate([
            'uploadedZip' => ['required', 'file', 'mimes:zip', 'max:51200'], // max 50MB
        ], [
            'uploadedZip.required' => 'File ZIP backup wajib diunggah.',
            'uploadedZip.mimes' => 'Format file harus berupa archive .ZIP.',
        ]);

        try {
            $backupService->restoreFromUploadedZip($this->uploadedZip);
            session()->flash('toast', ['type' => 'success', 'message' => 'Database berhasil dipulihkan dari file ZIP yang diunggah.']);
            $this->showRestoreModal = false;
        } catch (\Throwable $e) {
            session()->flash('toast', ['type' => 'error', 'message' => "Gagal memulihkan dari ZIP: " . $e->getMessage()]);
        }
    }

    public function deleteBackup(int $id, BackupService $backupService): void
    {
        $this->authorize('delete', Backup::class);

        $backup = Backup::findOrFail($id);
        $backupService->deleteBackup($backup);
        session()->flash('toast', ['type' => 'info', 'message' => 'File backup berhasil dihapus.']);
    }

    public function render(BackupService $backupService)
    {
        $this->authorize('viewAny', Backup::class);

        $backups = $backupService->getAllBackups();

        return view('livewire.backup.backup-restore-index', [
            'backups' => $backups,
        ])->layout('components.layouts.app');
    }
}
