<?php

namespace App\Traits;

use App\Models\Area;
use App\Models\Shippingzone;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\DB;

trait VerifiesPaymentTotal
{
    /**
     * Re-calculate the grand total on the server to prevent front-end tampering.
     * 
     * @param array $details
     * @return float
     */
    protected function verifyTotalAmount($details)
    {
        $productIds = !empty($details['productid']) ? explode(',', $details['productid']) : [];
        $orderColors = !empty($details['order_color']) ? explode(',', $details['order_color']) : [];
        $orderQuantities = !empty($details['order_qty']) ? explode(',', $details['order_qty']) : [];
        
        $subtotal = 0;
        $totalTaxAmount = 0;
        $totalWeight = 0;
        
        foreach ($productIds as $index => $productId) {
            $color = $orderColors[$index] ?? null;
            $qty = (int)($orderQuantities[$index] ?? 1);
            
            $productdata = DB::table('product')
                ->join('product_color', 'product.id', '=', 'product_color.product_id')
                ->select('product.product_name', 'product.product_price', 'product.cutted_price', 'product.weight', 'product_color.price')
                ->where('product.id', $productId)
                ->where('product_color.product_color', $color)
                ->first();
                
            if (!$productdata) {
                throw new \Exception("Product or color variant not found for ID: $productId, Color: $color");
            }
            
            $price = $productdata->price ?? $productdata->product_price;
            $subtotal += $price * $qty;
            
            // Calculate tax per item to be consistent with controller/DB
            $itemTax = 0;
            if (Auth::check() && Auth::user()->is_corporate) {
                $taxBaseSetting = \App\Models\SystemSetting::get('tax_calculation_base', 'selling_price');
                $taxBasePrice = ($taxBaseSetting === 'cutted_price' && isset($productdata->cutted_price)) 
                    ? $productdata->cutted_price 
                    : $price;
                $taxRate = (float) \App\Models\SystemSetting::get('corporate_tax_percentage', 18.00);
                $itemTax = round(($taxBasePrice * $qty * $taxRate) / 100, 2);
            }
            $totalTaxAmount += $itemTax;
            
            $totalWeight += $productdata->weight * $qty;
        }
        
        // Shipping calculation (Centralized)
        $city = $details['cus_city'] ?? 'Pagoda';
        $areaData = Area::where('area_name', $city)->first(); 
        if (!$areaData) {
            $areaData = Area::where('area_name', 'Pagoda')->first();
        }
        
        $serviceid = $areaData->serviceid;
        $zonedata = Shippingzone::where('id', $serviceid)->first();
        if (!$zonedata) {
            throw new \Exception("Shipping zone not found for city: $city");
        }
        
        // Weight based shipping: first 1kg is included in zone price, 
        // but every kg above 1kg adds 100 LKR.
        $productweightcost = $totalWeight > 1000 ? ceil(($totalWeight - 1000) / 1000) * 100 : 0;
        $shippingPrice = ($zonedata->price ?? 0) + $productweightcost;
        
        // Tax
        $taxAmount = $totalTaxAmount;
        
        // Discount & Voucher Validation
        $voucherCode = $details['voucher_code'] ?? null;
        $discount = (float)($details['discount_amount'] ?? 0);

        if (!empty($voucherCode)) {
            if (!Auth::check()) {
                throw new \Exception('Login is required to use a voucher.');
            }
            
            $voucher = \App\Models\Voucher::where('code', $voucherCode)->first();
            if ($voucher) {
                if ($voucher->redeemed_by !== null) {
                    throw new \Exception('This voucher has already been redeemed.');
                }
                
                $user = Auth::user();
                $alreadyUsed = \App\Models\Order::where('userid', $user->id)
                    ->where('voucher_code', $voucherCode)
                    ->exists();
                
                if ($alreadyUsed) {
                    throw new \Exception('You have already used this voucher code.');
                }

                $orderTotalBeforeDiscount = $subtotal + $shippingPrice + $taxAmount;
                if ($orderTotalBeforeDiscount < $voucher->min_spend) {
                    throw new \Exception('Minimum spend of LKR ' . number_format($voucher->min_spend, 2) . ' is required to use this voucher.');
                }
            }
        }        
        // Final Grand Total
        $grandTotal = max(0, $subtotal + $shippingPrice + $taxAmount - $discount);
        
        return round($grandTotal, 2);
    }
}
