<?php

namespace App\Http\Controllers\Admin;

use App\Http\Controllers\Controller;
use App\Models\DocumentoCollegato;
use App\Models\Stabile;
use App\Models\RubricaUniversale;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Storage;
use Illuminate\Support\Str;
use Carbon\Carbon;

class DocumentoCollegatoController extends Controller
{
    /**
     * Display a listing of the resource.
     */
    public function index(Request $request)
    {
        $query = DocumentoCollegato::with(['stabile', 'contatto']);

        // Filtri
        if ($request->filled('categoria')) {
            $query->where('tipo_documento', $request->categoria);
        }

        if ($request->filled('anno')) {
            $query->whereYear('data_sottoscrizione', $request->anno);
        }

        if ($request->filled('search')) {
            $search = $request->search;
            $query->where(function ($q) use ($search) {
                $q->where('titolo', 'like', "%{$search}%")
                    ->orWhere('numero_protocollo', 'like', "%{$search}%")
                    ->orWhere('descrizione', 'like', "%{$search}%");
            });
        }

        $documenti = $query->orderBy('created_at', 'desc')->paginate(15);

        return view('admin.documenti-collegati.index', compact('documenti'));
    }

    /**
     * Display a listing of the resource for a specific stabile.
     */
    public function indexByStabile(Stabile $stabile)
    {
        $documenti = $stabile->documentiCollegati()
            ->with('contatto')
            ->orderBy('created_at', 'desc')
            ->get();

        $statistiche = $this->calcolaStatistiche($stabile);

        return response()->json([
            'success' => true,
            'data' => $documenti,
            'statistiche' => $statistiche
        ]);
    }

    /**
     * Show the form for creating a new resource.
     */
    public function create()
    {
        $stabili = Stabile::orderBy('denominazione')->get();
        $contatti = RubricaUniversale::attivi()->orderBy('nome_completo')->get();

        return view('admin.documenti-collegati.create', compact('stabili', 'contatti'));
    }

    /**
     * Store a newly created resource in storage.
     */
    public function store(Request $request)
    {
        $validated = $request->validate([
            'stabile_id' => 'required|exists:stabili,id',
            'contatto_id' => 'nullable|exists:rubrica_universale,id',
            'tipo_documento' => 'required|in:contratto,assicurazione,certificato,preventivo,fattura,verbale,altro',
            'titolo' => 'required|string|max:255',
            'descrizione' => 'nullable|string',
            'data_sottoscrizione' => 'required|date',
            'data_scadenza' => 'nullable|date|after:data_sottoscrizione',
            'data_disdetta_limite' => 'nullable|date',
            'giorni_preavviso_disdetta' => 'nullable|integer|min:1|max:365',
            'tipo_contratto' => 'nullable|in:mensile,bimestrale,trimestrale,semestrale,annuale',
            'importo_contratto' => 'nullable|numeric|min:0',
            'valuta' => 'string|max:3|default:EUR',
            'stato_documento' => 'required|in:attivo,scaduto,disdetto,rinnovato',
            'numero_pagine_totali' => 'nullable|integer|min:1',
            'note' => 'nullable|string',
            'file_documento' => 'nullable|file|mimes:pdf,doc,docx,jpg,jpeg,png|max:10240' // 10MB max
        ]);

        // Genera numero di protocollo automatico
        $validated['numero_protocollo'] = $this->generaNumeroProtocollo($validated['tipo_documento']);
        $validated['creato_da'] = Auth::id();

        // Gestione upload file
        if ($request->hasFile('file_documento')) {
            $file = $request->file('file_documento');
            $fileName = $validated['numero_protocollo'] . '_' . Str::slug($validated['titolo']) . '.' . $file->getClientOriginalExtension();
            $filePath = $file->storeAs('documenti-collegati', $fileName, 'public');
            $validated['path_file_originale'] = $filePath;
        }

        $documento = DocumentoCollegato::create($validated);

        return redirect()
            ->route('admin.documenti-collegati.show', $documento)
            ->with('success', 'Documento creato con successo. Protocollo: ' . $validated['numero_protocollo']);
    }

    /**
     * Store a newly created resource for a specific stabile.
     */
    public function storeForStabile(Request $request, Stabile $stabile)
    {
        $validated = $request->validate([
            'contatto_id' => 'nullable|exists:rubrica_universale,id',
            'tipo_documento' => 'required|in:contratto,assicurazione,certificato,preventivo,fattura,verbale,altro',
            'titolo' => 'required|string|max:255',
            'descrizione' => 'nullable|string',
            'data_sottoscrizione' => 'required|date',
            'data_scadenza' => 'nullable|date|after:data_sottoscrizione',
            'data_disdetta_limite' => 'nullable|date',
            'giorni_preavviso_disdetta' => 'nullable|integer|min:1|max:365',
            'tipo_contratto' => 'nullable|in:mensile,bimestrale,trimestrale,semestrale,annuale',
            'importo_contratto' => 'nullable|numeric|min:0',
            'valuta' => 'string|max:3|default:EUR',
            'stato_documento' => 'required|in:attivo,scaduto,disdetto,rinnovato',
            'numero_pagine_totali' => 'nullable|integer|min:1',
            'note' => 'nullable|string'
        ]);

        $validated['stabile_id'] = $stabile->id;
        $validated['numero_protocollo'] = $this->generaNumeroProtocollo($validated['tipo_documento']);
        $validated['creato_da'] = Auth::id();

        $documento = DocumentoCollegato::create($validated);

        return response()->json([
            'success' => true,
            'message' => 'Documento creato con successo.',
            'data' => $documento->load('contatto'),
            'protocollo' => $validated['numero_protocollo']
        ]);
    }

    /**
     * Display the specified resource.
     */
    public function show(DocumentoCollegato $documentoCollegato)
    {
        $documentoCollegato->load(['stabile', 'contatto', 'createdBy', 'updatedBy']);

        return view('admin.documenti-collegati.show', compact('documentoCollegato'));
    }

    /**
     * Show the form for editing the specified resource.
     */
    public function edit(DocumentoCollegato $documentoCollegato)
    {
        $stabili = Stabile::orderBy('denominazione')->get();
        $contatti = RubricaUniversale::attivi()->orderBy('nome_completo')->get();

        return view('admin.documenti-collegati.edit', compact('documentoCollegato', 'stabili', 'contatti'));
    }

    /**
     * Update the specified resource in storage.
     */
    public function update(Request $request, DocumentoCollegato $documentoCollegato)
    {
        $validated = $request->validate([
            'contatto_id' => 'nullable|exists:rubrica_universale,id',
            'tipo_documento' => 'required|in:contratto,assicurazione,certificato,preventivo,fattura,verbale,altro',
            'titolo' => 'required|string|max:255',
            'descrizione' => 'nullable|string',
            'data_sottoscrizione' => 'required|date',
            'data_scadenza' => 'nullable|date|after:data_sottoscrizione',
            'data_disdetta_limite' => 'nullable|date',
            'giorni_preavviso_disdetta' => 'nullable|integer|min:1|max:365',
            'tipo_contratto' => 'nullable|in:mensile,bimestrale,trimestrale,semestrale,annuale',
            'importo_contratto' => 'nullable|numeric|min:0',
            'valuta' => 'string|max:3',
            'stato_documento' => 'required|in:attivo,scaduto,disdetto,rinnovato',
            'numero_pagine_totali' => 'nullable|integer|min:1',
            'note' => 'nullable|string',
            'file_documento' => 'nullable|file|mimes:pdf,doc,docx,jpg,jpeg,png|max:10240'
        ]);

        $validated['modificato_da'] = Auth::id();

        // Gestione upload file sostitutivo
        if ($request->hasFile('file_documento')) {
            // Elimina il file precedente se esiste
            if ($documentoCollegato->path_file_originale) {
                Storage::disk('public')->delete($documentoCollegato->path_file_originale);
            }

            $file = $request->file('file_documento');
            $fileName = $documentoCollegato->numero_protocollo . '_' . Str::slug($validated['titolo']) . '.' . $file->getClientOriginalExtension();
            $filePath = $file->storeAs('documenti-collegati', $fileName, 'public');
            $validated['path_file_originale'] = $filePath;
        }

        $documentoCollegato->update($validated);

        return redirect()
            ->route('admin.documenti-collegati.show', $documentoCollegato)
            ->with('success', 'Documento aggiornato con successo.');
    }

    /**
     * Remove the specified resource from storage.
     */
    public function destroy(DocumentoCollegato $documentoCollegato)
    {
        $stabileId = $documentoCollegato->stabile_id;

        // Elimina il file associato
        if ($documentoCollegato->path_file_originale) {
            Storage::disk('public')->delete($documentoCollegato->path_file_originale);
        }

        $documentoCollegato->delete();

        return redirect()
            ->route('admin.stabili.show', $stabileId)
            ->with('success', 'Documento eliminato con successo.');
    }

    /**
     * Download document file.
     */
    public function download(DocumentoCollegato $documento)
    {
        if (!$documento->path_file_originale || !Storage::disk('public')->exists($documento->path_file_originale)) {
            return redirect()->back()->with('error', 'File non trovato.');
        }

        return Storage::disk('public')->download(
            $documento->path_file_originale,
            $documento->numero_protocollo . '_' . Str::slug($documento->titolo) . '.pdf'
        );
    }

    /**
     * Print archive label for document.
     */
    public function stampaEtichetta(DocumentoCollegato $documento)
    {
        return view('admin.documenti-collegati.etichetta', compact('documento'));
    }

    /**
     * Renew a document.
     */
    public function rinnova(DocumentoCollegato $documento)
    {
        // Crea una copia del documento con nuove date
        $nuovoDocumento = $documento->replicate();
        $nuovoDocumento->numero_protocollo = $this->generaNumeroProtocollo($documento->tipo_documento);
        $nuovoDocumento->data_sottoscrizione = Carbon::now();
        $nuovoDocumento->data_scadenza = $documento->data_scadenza ?
            Carbon::parse($documento->data_scadenza)->addYear() : null;
        $nuovoDocumento->stato_documento = 'attivo';
        $nuovoDocumento->creato_da = Auth::id();
        $nuovoDocumento->save();

        // Aggiorna il documento originale
        $documento->update(['stato_documento' => 'rinnovato']);

        return response()->json([
            'success' => true,
            'message' => 'Documento rinnovato con successo.',
            'nuovo_protocollo' => $nuovoDocumento->numero_protocollo
        ]);
    }

    /**
     * Get statistics for documents (API).
     */
    public function getStatistiche($stabileId = null)
    {
        $query = DocumentoCollegato::query();

        if ($stabileId) {
            $query->where('stabile_id', $stabileId);
        }

        $statistiche = [
            'contratti' => $query->clone()->where('tipo_documento', 'contratto')->where('stato_documento', 'attivo')->count(),
            'assicurazioni' => $query->clone()->where('tipo_documento', 'assicurazione')->where('stato_documento', 'attivo')->count(),
            'scadenze' => $query->clone()->where('data_scadenza', '<=', Carbon::now()->addDays(30))->where('stato_documento', 'attivo')->count(),
            'totale' => $query->clone()->count(),
            'scaduti' => $query->clone()->where('data_scadenza', '<', Carbon::now())->where('stato_documento', 'attivo')->count()
        ];

        return response()->json([
            'success' => true,
            'statistiche' => $statistiche
        ]);
    }

    /**
     * Get documents expiring soon (API).
     */
    public function getScadenzeImminenti($giorni = 30)
    {
        $scadenze = DocumentoCollegato::with(['stabile', 'contatto'])
            ->where('data_scadenza', '<=', Carbon::now()->addDays($giorni))
            ->where('data_scadenza', '>=', Carbon::now())
            ->where('stato_documento', 'attivo')
            ->orderBy('data_scadenza')
            ->get();

        return response()->json([
            'success' => true,
            'scadenze' => $scadenze
        ]);
    }

    /**
     * Generate automatic protocol number.
     */
    private function generaNumeroProtocollo($tipoDocumento)
    {
        $anno = date('Y');
        $prefissi = [
            'contratto' => 'CONTR',
            'assicurazione' => 'ASSIC',
            'certificato' => 'CERT',
            'preventivo' => 'PREV',
            'fattura' => 'FATT',
            'verbale' => 'VERB',
            'altro' => 'DOC'
        ];

        $prefisso = $prefissi[$tipoDocumento] ?? 'DOC';

        // Trova il prossimo numero progressivo per l'anno corrente
        $ultimoNumero = DocumentoCollegato::where('numero_protocollo', 'like', "{$prefisso}-{$anno}-%")
            ->orderBy('numero_protocollo', 'desc')
            ->first();

        $progressivo = 1;
        if ($ultimoNumero) {
            $parts = explode('-', $ultimoNumero->numero_protocollo);
            $progressivo = (int)end($parts) + 1;
        }

        return sprintf('%s-%s-%03d', $prefisso, $anno, $progressivo);
    }

    /**
     * Calculate statistics for a stabile.
     */
    private function calcolaStatistiche(Stabile $stabile)
    {
        $documenti = $stabile->documentiCollegati();

        return [
            'contratti' => $documenti->clone()->where('tipo_documento', 'contratto')->where('stato_documento', 'attivo')->count(),
            'assicurazioni' => $documenti->clone()->where('tipo_documento', 'assicurazione')->where('stato_documento', 'attivo')->count(),
            'scadenze' => $documenti->clone()->where('data_scadenza', '<=', Carbon::now()->addDays(30))->where('stato_documento', 'attivo')->count(),
            'totale' => $documenti->clone()->count(),
            'scaduti' => $documenti->clone()->where('data_scadenza', '<', Carbon::now())->where('stato_documento', 'attivo')->count()
        ];
    }
}
