<?php

namespace App\Http\Controllers\user;

use App\Http\Controllers\Controller;
use App\Models\Package;
use App\Models\Purchase;
use App\Models\Rebate;
use App\Models\User;
use App\Models\SpinChance;
use App\Models\UserLedger;
use Carbon\Carbon;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\DB;

class PurchaseController extends Controller
{
    public function purchaseConfirmation($id)
    {
        try {
            $package = Package::find($id);
            $user = Auth::user();
            $rebate = Rebate::first();

            if (!$package) return back()->with('error', "Package not found.");
            if ($package->status !== 'active') return back()->with('error', "Package is Inactive.");

            $maxPurchases = $package->max_purchase_limit;
            $userPurchaseCount = Purchase::where('user_id', $user->id)
                ->where('package_id', $package->id)
                ->count();

            if ($userPurchaseCount >= $maxPurchases) {
                return back()->with('error', "You have reached the maximum purchase limit.");
            }

            if (!$this->checkIfCanBuyPackage($user, $package)) {
                return back()->with('error', "You must purchase the required packages first.");
            }

            if ($package->price > $user->balance) {
                return back()->with('error', "You currently have low balance.");
            }

            // Deduct balance and save ledger
            $user->balance -= $package->price;
            $user->investor = 1;
            $user->save();

            UserLedger::create([
                'user_id' => $user->id,
                'reason' => 'purchase',
                'perticulation' => 'Purchased Package: ' . $package->name,
                'amount' => $package->price,
                'debit' => $package->price,
                'status' => 'approved',
                'step' => 'self',
                'date' => now()->format('Y-m-d H:i'),
            ]);

            // Calculate income breakdown
            $hourly = $daily = $weekly = 0;
            $nextDrop = now();

            if ($package->category === 'fixed') {
                $hourly = $package->commission_with_avg_amount / ($package->validity * 24);
                $nextDrop = now()->addHour();
            } elseif ($package->category === 'welfare') {
                $daily = $package->commission_with_avg_amount / $package->validity;
                $nextDrop = now()->addDay();
            } elseif ($package->category === 'activity') {
                $weeks = ceil($package->validity / 7);
                $weekly = $package->commission_with_avg_amount / $weeks;
                $nextDrop = now()->addWeek();
            }

            // Save purchase
            $purchase = new Purchase();
            $purchase->user_id = $user->id;
            $purchase->package_id = $package->id;
            $purchase->amount = $package->price;
            $purchase->hourly = $hourly;
            $purchase->daily_income = $daily;
            $purchase->weekly_income = $weekly;
            $purchase->date = $nextDrop;
            $purchase->validity = now()->addDays($package->validity);
            $purchase->status = 'active';
            $purchase->category = $package->category;
            $purchase->save();

            // VIP level upgrade
            $totalInvestment = Purchase::where('user_id', $user->id)->sum('amount');
            $vipLevel = $this->getVipLevel($totalInvestment);

            if ($vipLevel > $user->vip_level) {
                $user->vip_level = $vipLevel;
                $user->save();

                UserLedger::create([
                    'user_id' => $user->id,
                    'reason' => 'vip_upgrade',
                    'perticulation' => "VIP upgraded to level $vipLevel",
                    'amount' => 0,
                    'status' => 'approved',
                    'step' => 'self',
                    'date' => now()->format('Y-m-d H:i'),
                ]);
            }

            // Spin chance reward
            SpinChance::updateOrCreate(
                ['user_id' => $user->id],
                ['chances' => DB::raw('chances + 1')]
            );

            UserLedger::create([
                'user_id' => $user->id,
                'reason' => 'spin_reward',
                'perticulation' => "Spin chance earned for purchase",
                'amount' => 0,
                'status' => 'approved',
                'step' => 'self',
                'date' => now()->format('Y-m-d H:i'),
            ]);

            // Referral Commission
            $this->distributeCommission($user, $package);

            return back()->with('success', "Investment Successful.");
        } catch (\Exception $e) {
            return back()->with('error', "Error: " . $e->getMessage());
        }
    }

    protected function checkIfCanBuyPackage($user, $package)
    {
        $purchased = Purchase::where('user_id', $user->id)->pluck('package_id')->toArray();

        if ($package->category === 'welfare') {
            $fixed = Package::where('category', 'fixed')->first();
            return !$fixed || in_array($fixed->id, $purchased);
        }

        if ($package->category === 'activity') {
            $fixed = Package::where('category', 'fixed')->first();
            $welfare = Package::where('category', 'welfare')->first();
            return (!$fixed || in_array($fixed->id, $purchased)) &&
                   (!$welfare || in_array($welfare->id, $purchased));
        }

        return true;
    }

    protected function getVipLevel($investment)
    {
        if ($investment >= 256000000) return 10;
        if ($investment >= 128000000) return 9;
        if ($investment >= 64000000) return 8;
        if ($investment >= 3200000) return 7;
        if ($investment >= 150000) return 6;
        if ($investment >= 78000) return 5;
        if ($investment >= 35000) return 4;
        if ($investment >= 10000) return 3;
        if ($investment >= 2000) return 2;
        if ($investment >= 500) return 1;
        return 0;
    }

    protected function distributeCommission($user, $package)
    {
        $category = $package->category;

        // Category-based commission
        if ($category === 'fixed') {
            $level1 = 35; $level2 = 1; $level3 = 1;
        } elseif ($category === 'welfare') {
            $level1 = 40; $level2 = 1; $level3 = 1;
        } elseif ($category === 'activity') {
            $level1 = 47; $level2 = 1; $level3 = 1;
        } else {
            $level1 = $level2 = $level3 = 0;
        }

        $first = User::where('ref_id', $user->ref_by)->first();
        if ($first) {
            $amount1 = $package->price * ($level1 / 100);
            $first->increment('balance', $amount1);
            $this->createLedger($first->id, $user->id, "First Level $category Commission ($level1%)", 'first', $amount1);

            $second = User::where('ref_id', $first->ref_by)->first();
            if ($second) {
                $amount2 = $package->price * ($level2 / 100);
                $second->increment('balance', $amount2);
                $this->createLedger($second->id, $user->id, "Second Level $category Commission ($level2%)", 'second', $amount2);

                $third = User::where('ref_id', $second->ref_by)->first();
                if ($third) {
                    $amount3 = $package->price * ($level3 / 100);
                    $third->increment('balance', $amount3);
                    $this->createLedger($third->id, $user->id, "Third Level $category Commission ($level3%)", 'third', $amount3);
                }
            }
        }
    }

    protected function createLedger($userId, $fromUserId, $text, $step, $amount)
    {
        UserLedger::create([
            'user_id' => $userId,
            'get_balance_from_user_id' => $fromUserId,
            'reason' => 'commission',
            'perticulation' => $text,
            'amount' => $amount,
            'debit' => $amount,
            'status' => 'approved',
            'step' => $step,
            'date' => now()->format('Y-m-d H:i'),
        ]);
    }

    public function vip_confirm($vip_id)
    {
        $vip = Package::find($vip_id);
        return view('app.main.vip_confirm', compact('vip'));
    }
}
