<?php

namespace App\Http\Controllers;

use App\Models\Order;
use App\Models\OrderItem;
use App\Models\Product;
use App\Models\Province;
use App\Models\Regency;
use App\Models\UserAddress;
use Illuminate\Http\Request;
use Illuminate\Routing\Controllers\HasMiddleware;
use Illuminate\Routing\Controllers\Middleware;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Log;
use Midtrans\Config;
use Midtrans\Snap;

class CheckoutController extends Controller implements HasMiddleware
{
    public static function middleware(): array
    {
        return [
            (new Middleware(function ($request, $next) {
                if (auth()->check() && auth()->user()->is_admin) {
                    return redirect()->route('front.index')
                        ->with('error', 'Akses ditolak! Admin tidak bisa melakukan proses checkout.');
                }

                return $next($request);
            }))->except(['showPayment', 'success']),
        ];
    }

    public function index()
    {
        if (session()->has('buy_now_data')) {
            $cart = session('buy_now_data');
        } elseif (session()->has('checkout_items')) {
            $cart = session('checkout_items');
        } else {
            $cart = session('cart');
        }

        if (! $cart || count($cart) == 0) {
            return redirect()->route('front.index')->with('error', 'Tidak ada barang untuk dibayar.');
        }

        $totalPrice = 0;
        $totalWeight = 0;

        foreach ($cart as $id => $item) {
            $product = Product::find($id);
            $weight = $product->weight ?? 1000;

            $totalPrice += $item['price'] * $item['quantity'];
            $totalWeight += $weight * $item['quantity'];
        }

        $user = Auth::user();
        $provinces = Province::all();

        // AMBIL BUKU ALAMAT MILIK USER
        $addresses = UserAddress::where('user_id', Auth::id())->latest()->get();

        return view('front.checkout', compact('cart', 'totalPrice', 'totalWeight', 'provinces', 'user', 'addresses'));
    }

    public function getCities(Request $request)
    {
        $cities = Regency::where('province_id', $request->province_id)->get();

        return response()->json($cities);
    }

    public function checkOngkir(Request $request)
    {
        $courier = strtoupper($request->courier ?? 'JNE');

        return response()->json([
            [
                'code' => strtolower($courier),
                'name' => $courier.' (TEST MODE)',
                'costs' => [
                    [
                        'service' => 'REG',
                        'description' => 'Layanan Reguler (Dummy)',
                        'cost' => [
                            [
                                'value' => 20000,
                                'etd' => '2-3 Hari',
                                'note' => 'Harga Dummy',
                            ],
                        ],
                    ],
                    [
                        'service' => 'YES',
                        'description' => 'Yakin Esok Sampai (Dummy)',
                        'cost' => [
                            [
                                'value' => 35000,
                                'etd' => '1 Hari',
                                'note' => 'Harga Dummy',
                            ],
                        ],
                    ],
                ],
            ],
        ]);
    }

    public function process(Request $request)
    {
        $request->validate([
            'customer_name' => 'required|string|max:255',
            'customer_email' => 'required|email',
            'customer_phone' => 'required',
            'customer_address' => 'required',
            'province_id' => 'required',
            'city_id' => 'required',
            'district_id' => 'required',
            'courier_code' => 'required',
            'courier_service' => 'required',
            'shipping_cost' => 'required|numeric',
            'payment_method' => 'required|in:online,cod',
        ]);

        // CEK APAKAH USER CENTANG "SIMPAN SEBAGAI ALAMAT BARU"
        if ($request->has('save_new_address') && $request->save_new_address == '1') {
            UserAddress::create([
                'user_id' => Auth::id(),
                'label' => $request->address_label ?? 'Alamat Baru',
                'recipient_name' => $request->customer_name,
                'phone' => $request->customer_phone,
                'province_id' => $request->province_id,
                'city_id' => $request->city_id,
                'district_id' => $request->district_id,
                'village_id' => $request->village_id,
                'detail_address' => $request->customer_address,
            ]);
        }

        if (session()->has('buy_now_data')) {
            $cart = session('buy_now_data');
        } elseif (session()->has('checkout_items')) {
            $cart = session('checkout_items');
        } else {
            $cart = session('cart');
        }

        if (! $cart || empty($cart)) {
            return redirect()->route('front.index')->with('error', 'Keranjang belanja kosong.');
        }

        $subtotal = 0;
        foreach ($cart as $id => $details) {
            $product = Product::find($id);
            if (! $product) {
                continue;
            }
            $subtotal += $product->price * $details['quantity'];
        }

        $shippingCost = $request->shipping_cost;
        $grandTotal = $subtotal + $shippingCost;
        $orderNumber = 'TRF-'.strtoupper(bin2hex(random_bytes(3)));

        foreach ($cart as $id => $details) {
            $product = Product::find($id);
            if (! $product || $product->status == 'sold' || $product->status == 'booked' || ($product->stock !== null && $product->stock <= 0)) {
                return redirect()->route('cart.index')->with('error', 'Waduh, keduluan! Item "'.($product->name ?? 'Produk').'" baru aja di-checkout orang lain.');
            }
        }

        $order = Order::create([
            'user_id' => Auth::id(),
            'order_number' => $orderNumber,
            'customer_name' => $request->customer_name,
            'customer_email' => $request->customer_email,
            'customer_phone' => $request->customer_phone,
            'customer_address' => $request->customer_address,
            'province_id' => $request->province_id,
            'regency_id' => $request->city_id,
            'district_id' => $request->district_id,
            'village_id' => $request->village_id,
            'total_price' => $grandTotal,
            'shipping_cost' => $shippingCost,
            'courier_name' => strtoupper($request->courier_code),
            'courier_service' => $request->courier_service,
            'payment_method' => $request->payment_method,
            'status' => $request->payment_method === 'cod' ? 'pending_cod' : 'pending',
        ]);

        foreach ($cart as $id => $details) {
            OrderItem::create([
                'order_id' => $order->id,
                'product_id' => $id,
                'quantity' => $details['quantity'],
                'price' => $details['price'],
            ]);

            $product = Product::find($id);
            if ($product) {
                if ($request->payment_method === 'cod') {
                    // COD: langsung sold karena pembayaran akan diselesaikan saat terima barang
                    $product->status = 'sold';
                    $product->stock = max(0, ($product->stock ?? 1) - $details['quantity']);
                    $product->save();

                    \App\Models\ProductLog::create([
                        'product_id' => $product->id,
                        'type' => 'out',
                        'quantity' => $details['quantity'],
                        'description' => 'Terjual via COD ke '.$request->customer_name.' (Order: '.$orderNumber.')',
                    ]);
                } else {
                    // Online: masih booked sampai Midtrans konfirmasi
                    $product->status = 'booked';
                    $product->save();
                }
            }
        }

        // ====================================================
        // PERCABANGAN: COD vs ONLINE
        // ====================================================
        if ($request->payment_method === 'cod') {
            // COD: Skip Midtrans — langsung ke halaman sukses
            $this->clearCart($cart);

            return redirect()->route('front.payment.success', $order->id)
                ->with('success_cod', 'Pesanan COD berhasil dibuat! Siapkan uang tunai saat kurir tiba.');
        }

        // ONLINE: Proses Midtrans
        Config::$serverKey = env('MIDTRANS_SERVER_KEY');
        Config::$isProduction = env('MIDTRANS_IS_PRODUCTION', false);
        Config::$isSanitized = true;
        Config::$is3ds = true;

        $params = [
            'transaction_details' => [
                'order_id' => $orderNumber,
                'gross_amount' => (int) $grandTotal,
            ],
            'customer_details' => [
                'first_name' => $request->customer_name,
                'email' => $request->customer_email,
                'phone' => $request->customer_phone,
            ],
        ];

        try {
            $snapToken = Snap::getSnapToken($params);
            $order->update(['snap_token' => $snapToken]);
        } catch (\Exception $e) {
            Log::error('Midtrans Error:', ['message' => $e->getMessage()]);

            return redirect()->back()->with('error', 'Midtrans Error: '.$e->getMessage());
        }

        $this->clearCart($cart);

        return redirect()->route('front.payment', $order->id);
    }

    private function clearCart($itemsToRemove)
    {
        if (session()->has('buy_now_data')) {
            session()->forget('buy_now_data');
        } elseif (session()->has('checkout_items')) {
            session()->forget('checkout_items');
            $mainCart = session('cart', []);
            foreach ($itemsToRemove as $id => $val) {
                unset($mainCart[$id]);
            }
            session(['cart' => $mainCart]);
        } else {
            session()->forget('cart');
        }
    }

    public function showPayment($id)
    {
        $order = Order::with(['orderItems.product'])->findOrFail($id);

        if (Auth::id() != $order->user_id && ! Auth::user()->is_admin) {
            abort(403);
        }

        $firstItem = null;
        if ($order->orderItems->count() > 0) {
            $product = $order->orderItems->first()->product;
            $firstItem = [
                'image' => $product->image ?? null,
                'name' => $product->name ?? 'Produk',
            ];
        }

        return view('front.payment', compact('order', 'firstItem'));
    }

    public function success($id)
    {
        $order = Order::with(['orderItems.product'])->findOrFail($id);

        if (Auth::id() != $order->user_id && ! Auth::user()->is_admin) {
            abort(403);
        }

        return view('front.success', compact('order'));
    }
}
