<?php

namespace App\Http\Controllers;

use App\Models\Payment;
use App\Models\Booking;
use App\Models\Rooms;
use App\Models\User;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Storage;
use Illuminate\Support\Facades\Validator;
use Illuminate\Support\Facades\DB;
use Illuminate\Support\Facades\Notification;
use App\Notifications\NewPaymentNotification;
use App\Notifications\PaymentSubmittedNotification;
use App\Notifications\PaymentApprovedNotification;
use App\Notifications\PaymentVerificationNotice;
use PDF;
use Symfony\Component\HttpFoundation\StreamedResponse;

class PaymentController extends Controller
{
    /**
     * Upload file bukti pembayaran.
     */
    private function uploadFile($file, $type = 'bukti')
    {
        $fileName = time() . '_' . $type . '.' . $file->getClientOriginalExtension();
        $file->move(public_path('storage/images/payment/'), $fileName);
        return Storage::url('images/payment/' . $fileName);
    }

    /**
     * Tampilkan semua data pembayaran, bisa difilter by user (optional).
     */
    public function index(Request $request)
    {
        try {
            $query = Payment::with('booking', 'rekening','user')->latest();

            if ($request->has('user_id')) {
                $query->where('user_id', $request->user_id);
            }

            $payments = $query->paginate(10);

            return response()->json(['success' => true, 'data' => $payments], 200);
        } catch (\Exception $e) {
            return response()->json(['success' => false, 'message' => $e->getMessage()], 500);
        }
    }
    public function index2(Request $request)
    {
        try {
           
            $payments = Payment::with('booking', 'rekening')
                ->where('user_id', auth()->id())
                ->latest()
                ->paginate(5);

            return response()->json([
                'success' => true,
                'data' => $payments
            ], 200);

        } catch (\Exception $e) {
       
            return response()->json([
                'success' => false,
                'message' => 'Gagal mengambil data: ' . $e->getMessage()
            ], 500);
        }
    }

    /**
     * Simpan data pembayaran baru.
     */
    public function store(Request $request)
    {
        $validator = Validator::make($request->all(), [
            'invoice_id' => 'required|exists:bookings,invoice_id',
            'id_rek' => 'required|exists:rekenings,id',
            'nama_bank'  => 'required|string|max:100',
            'norek'      => 'required|string|max:50',
            'atas_nama'  => 'required|string|max:100',
            'bukti'      => 'required|file|mimes:jpg,jpeg,png,pdf,webp|max:2048',
        ]);

        if ($validator->fails()) {
            return response()->json(['success' => false, 'errors' => $validator->errors()], 422);
        }
        // Cek apakah booking sudah dibayar
        $booking = Booking::where('invoice_id', $request->invoice_id)->first();
        if (!$booking) {
            return response()->json(['success' => false, 'message' => 'Booking not found'], 404);
        }

        // Cek apakah sudah ada payment untuk invoice ini
        $existingPayment = Payment::where('invoice_id', $request->invoice_id)->first();
        if ($existingPayment) {
            return response()->json(['success' => false, 'message' => 'Payment already exists for this invoice'], 422);
        }

        try {
            $path = $this->uploadFile($request->file('bukti'), 'bukti');

            $payment = Payment::create([
                'invoice_id' => $request->invoice_id,
                'id_rek' => $request->id_rek,
                'nama_bank'  => $request->nama_bank,
                'norek'      => $request->norek,
                'atas_nama'  => $request->atas_nama,
                'bukti'      => $path,
                'user_id'    => auth()->id() ?? null,
            ]);
            // Jika berhasil, ubah status pada model booking menjadi 'review'
            $booking->status = 'review';
            $booking->save();
            
            // ✅ Kirim email ke admin yang terverifikasi
            $admins = User::whereIn('id_role', [1, 2])
            ->whereNotNull('email_verified_at')
            ->get();

            Notification::send($admins, new \App\Notifications\NewPaymentNotification($payment));

            // ✅ Kirim email ke penyewa jika email verified
            if ($payment->user && $payment->user->email_verified_at) {
            $payment->user->notify(new \App\Notifications\PaymentSubmittedNotification($payment));
            }

            return response()->json([
                'success' => true, 
                'message' => 'Payment submitted successfully. Please wait for admin verification.',
                'data' => $payment->load(['booking', 'rekening', 'user'])
            ], 201);

        } catch (\Exception $e) {
            return response()->json(['success' => false, 'message' => $e->getMessage()], 500);
        }
    }

    /**
     * Update data pembayaran.
     */
    public function update(Request $request, $id)
    {
        $payment = Payment::find($id);

        if (!$payment) {
            return response()->json(['success' => false, 'message' => 'Payment not found'], 404);
        }

        $validator = Validator::make($request->all(), [
            'invoice_id' => 'sometimes|exists:bookings,invoice_id',
            'id_rek' => 'sometimes|exists:rekenings,id',
            'nama_bank'  => 'sometimes|string|max:100',
            'norek'      => 'sometimes|string|max:50',
            'atas_nama'  => 'sometimes|string|max:100',
            'bukti'      => 'sometimes|file|mimes:jpg,jpeg,png,pdf|max:2048',
        ]);

        if ($validator->fails()) {
            return response()->json(['success' => false, 'errors' => $validator->errors()], 422);
        }

        try {
            if ($request->hasFile('bukti')) {
                $path = $this->uploadFile($request->file('bukti'), 'bukti');
                $payment->bukti = $path;
            }

            $payment->update($request->except('bukti'));

            return response()->json(['success' => true, 'data' => $payment], 200);
        } catch (\Exception $e) {
            return response()->json(['success' => false, 'message' => $e->getMessage()], 500);
        }
    }

    /**
     * Verifikasi pembayaran secara manual (opsional).
     */
    public function verify($id)
    {
        $payment = Payment::find($id);

        if (!$payment) {
            return response()->json(['success' => false, 'message' => 'Payment not found'], 404);
        }

        try {
            $payment->verified_at = now();
            $payment->status = 'success';
            $payment->save();

             // Update booking terkait
            $booking = Booking::where('invoice_id', $payment->invoice_id)->first();
            if ($booking) {
                $booking->start_date = $booking->checkin ?? now()->toDateString();
                $quantity = $booking->quantity ?? 1;
                $booking->end_date = now()->addDays($quantity * 31)->toDateString();
                $booking->status = 'success';
                $booking->save();

                // Update id_user pada tabel Room
                $room = Rooms::where('id', $booking->id_room)->first();
                if ($room) {
                    $room->id_user = $booking->id_user;
                    $room->status = 'occupied';
                    $room->save();
                }
            }

             // 1.  Penyewa (jika email verified)
            if ($payment->user && $payment->user->email_verified_at) {
                $payment->user->notify(new PaymentApprovedNotification($payment));
            }

            // 2.  Admin lain (role 1 & 2) yang email‑nya verified
            $admins = User::whereIn('id_role', [1, 2])
                ->whereNotNull('email_verified_at')
                ->get();

            foreach ($admins as $admin) {
                $admin->notify(new PaymentVerificationNotice($payment));
            }

            return response()->json(['success' => true, 'message' => 'Payment verified'], 200);
        } catch (\Exception $e) {
            return response()->json(['success' => false, 'message' => $e->getMessage()], 500);
        }
    }

    /**
     * Hapus data pembayaran.
     */
    public function destroy($id)
    {
        try {
            $payment = Payment::findOrFail($id);
            $payment->delete();

            return response()->json(['success' => true, 'message' => 'Payment deleted'], 200);
        } catch (\Exception $e) {
            return response()->json(['success' => false, 'message' => $e->getMessage()], 500);
        }
    }

    /**
     * Menampilkan daftar pembayaran yang sudah dihapus (soft deleted).
     */
    public function trashed()
    {
        try {
            $payments = Payment::onlyTrashed()->get();
            return response()->json(['success' => true, 'data' => $payments], 200);
        } catch (\Exception $e) {
            return response()->json(['success' => false, 'message' => $e->getMessage()], 500);
        }
    }

    /**
     * Mengembalikan data pembayaran yang sudah dihapus (restore).
     */
    public function restore($id)
    {
        try {
            $payment = Payment::onlyTrashed()->findOrFail($id);
            $payment->restore();
            return response()->json(['success' => true, 'message' => 'Payment restored'], 200);
        } catch (\Exception $e) {
            return response()->json(['success' => false, 'message' => $e->getMessage()], 500);
        }
    }

    /**
     * Menghapus permanen data pembayaran (force delete).
     */
    public function forceDelete($id)
    {
        try {
            $payment = Payment::onlyTrashed()->findOrFail($id);
            $payment->forceDelete();
            return response()->json(['success' => true, 'message' => 'Payment permanently deleted'], 200);
        } catch (\Exception $e) {
            return response()->json(['success' => false, 'message' => $e->getMessage()], 500);
        }
    }

    /**
     * Export individual payment to PDF
     */
    public function exportPdf($id)
    {
        try {
            $payment = Payment::with(['user', 'booking', 'rekening'])->findOrFail($id);
            
            $data = [
                'payment' => $payment,
                'title' => 'Detail Payment - ' . $payment->invoice_id
            ];

            $pdf = PDF::loadView('exports.payment_detail', $data);
            
            return $pdf->download('payment-' . $payment->invoice_id . '.pdf');
        } catch (\Exception $e) {
            return response()->json([
                'success' => false,
                'message' => 'Failed to generate PDF: ' . $e->getMessage()
            ], 500);
        }
    }

    /**
     * Export all payments to Excel/CSV
     */
    public function exportExcel()
    {
        $fileName = 'payments_' . date('Y-m-d_H-i-s') . '.csv';

        $response = new StreamedResponse(function () use ($fileName) {
            $handle = fopen('php://output', 'w');

            // Header CSV
            fputcsv($handle, [
                'No', 'Invoice ID', 'User', 'Bank Name', 'Account Number', 'Account Holder', 
                'Payment Proof', 'Status', 'Verified At', 'Created At'
            ]);

            try {
                Payment::with(['user', 'booking', 'rekening'])->chunk(500, function ($payments) use ($handle) {
                    $counter = 1;
                    foreach ($payments as $payment) {
                        fputcsv($handle, [
                            $counter++,
                            $payment->invoice_id,
                            $payment->user ? $payment->user->name : 'Unknown',
                            $payment->nama_bank,
                            $payment->norek,
                            $payment->atas_nama,
                            $payment->bukti,
                            $payment->status,
                            $payment->verified_at,
                            $payment->created_at
                        ]);
                    }
                });
            } catch (\Exception $e) {
                fclose($handle);
                return response()->json(['error' => 'Failed to generate CSV: ' . $e->getMessage()], 500);
            }

            fclose($handle);
        });

        $response->headers->set('Content-Type', 'text/csv');
        $response->headers->set('Content-Disposition', 'attachment; filename="' . $fileName . '"');

        return $response;
    }
}
