<?php

namespace App\Http\Controllers;

use App\Http\Controllers\ParentFrontendController;
use App\Jobs\InTransaction;
use Illuminate\Http\Request;
use App\Models\Investment;
use App\Models\Plan;
use App\Models\Withdrawal;
use App\Models\Deposit;
use App\Models\In_transaction;
use App\Models\Bid;
use App\Models\Sell;
use App\Models\Ownership;
use App\Models\User;
use App\Models\SiteDetail;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Http;
use App\Services\PaymentService;
use Carbon\Carbon;

class ProfilePageController extends Controller
{
    /**
     * Create a new controller instance.
     *
     * @return void
     */
    public function __construct()
    {
        $this->middleware(['auth', 'verified', 'onboarding', 'activated']);
        $this->middleware(['banned'])->except(['banned']);
        $this->middleware(['2fa'])->except(['banned', 'twoFaVerification', 'verifyTwoFa']);
    }

    /**
     * Show the application user dashboard.
     *
     * @return \Illuminate\Contracts\Support\Renderable
     */
    // public function index()
    // {
    //     $curr = [];
    //     //get currency
    //     try{
    //         $currencies = Http::nowPayment()->get('/full-currencies');
    //         $curr_array = $currencies->collect();
    //         $curr = collect($curr_array['currencies'])->filter( function ($value, $key) {
    //             return $value['code'] == 'USDTTRC20' ;
    //         });
    //     } catch (\Exception $e) {
    //         $errorMessage = $e->getMessage();
    //         // return view('home')('plan', 'errorMessage'));
    //     }

    //     $currency = collect($curr)->flatMap(function (array $values) {
    //         return array_map('strtoupper', $values);
    //     });

    //     // If user have an active investment?
    //     [ Query for the data from the investments.status column]

    //     $deposits = Deposit::where('user_id', auth()->user()->id)->where('status', null)->get();

    //     foreach($deposits as $deposit)
    //     {
    //         PaymentService::payInfo($deposit);
    //     }

    //     $bids = Bid::with('user')->where('user_id', auth()->user()->id)->where('type', 'manual_bid')->orderBy('id', 'desc')->take(100)->get();

    //     $sells = Sell::with('user')->where('user_id', auth()->user()->id)->where('type', 'manual_sell')->orderBy('id', 'desc')->take(100)->get();

    //     $ownerships = Ownership::with('user')->where('user_id', auth()->user()->id)->where('type', 'manual')->get();

    //     $data = [
    //         'bids' => $bids,
    //         'sells' => $sells,
    //         'ownerships' => $ownerships,
    //     ];

    //     return view('home', $data);
    // }
    
    public function index()
    {
        $userId = auth()->id();
        
        // Optimize deposit check - only fetch necessary columns and limit results
        $deposits = Deposit::where('user_id', $userId)
            ->whereNull('status')
            ->get();
        
        foreach($deposits as $deposit) {
            PaymentService::payInfo($deposit);
        }
        
        // Eager load relationships and select only needed columns
        $bids = Bid::with(['product:id,name,image1', 'market:id,name'])
            ->where('user_id', $userId)
            ->where('type', 'manual_bid')
            ->select('id', 'user_id', 'product_id', 'market_id', 'amount', 'quantity', 'status', 'bid_time')
            ->orderBy('id', 'desc')
            ->take(100)
            ->get();
        
        $sells = Sell::with(['product:id,name,image1', 'market:id,name'])
            ->where('user_id', $userId)
            ->where('type', 'manual_sell')
            ->select('id', 'user_id', 'product_id', 'market_id', 'amount', 'quantity', 'status', 'sell_time')
            ->orderBy('id', 'desc')
            ->take(100)
            ->get();
        
        $ownerships = Ownership::with([
            'product:id,name,image1,market_id',
            'product.market:id,name',
            'sells' => function($query) {
                $query->where('status', 0)->select('id', 'ownership_id', 'status', 'sell_time');
            }
        ])
            ->where('user_id', $userId)
            // ->where('type', 'manual')
            ->whereIn('type', ['manual', 'coupon'])
            ->select('id', 'slug', 'user_id', 'product_id', 'value', 'quantity', 'type')
            ->get();
        
        return view('home', [
            'bids' => $bids,
            'sells' => $sells,
            'ownerships' => $ownerships,
        ]);
    }
    
  
    public function profile(){

        return view('profile');

    }

    public function deposit(){
        
        $is_deposit_paused = SiteDetail::where('title', 'is_deposit_paused')->first(); 
    
        if($is_deposit_paused->description == 1 && request('key') !== 'mySuperSecretKey123') {
            // return redirect()->back()->with('message', "Can't make deposits at this time, try again later.");
            return view('deposit-suspended');
        }

        $deposits = Deposit::where('user_id', auth()->user()->id)->where('status', null)->get();
        
        foreach($deposits as $deposit) {
            PaymentService::payInfo($deposit);
        }

        $deposits = Deposit::where('user_id', auth()->user()->id)->get();

        return view('deposit-crypto', compact('deposits'));
    }
    
    public function depositAlt(){
        
        $is_deposit_paused = SiteDetail::where('title', 'is_deposit_paused')->first(); 
    
        if($is_deposit_paused->description == 1 && request('key') !== 'mySuperSecretKey123') {
            // return redirect()->back()->with('message', "Can't make deposits at this time, try again later.");
            return view('deposit-suspended');
        }

        $deposits = Deposit::where('user_id', auth()->user()->id)->where('status', null)->get();
        
        foreach($deposits as $deposit) {
            PaymentService::payInfo($deposit);
        }

        $deposits = Deposit::where('user_id', auth()->user()->id)
            ->orderBy('created_at', 'desc')
            ->get();

        return view('deposit-crypto', compact('deposits'));
    }
    
    public function dep(){
        
        return view('deposit-suspended');
    }

    // public function firstGen(){
    //     $referrals = Auth::user()->referrals()->with(['investment' => function ($q) {
    //         $q->where('status', 2);
    //     }])->get();

    //     return view('one-gen', compact('referrals'));
    // }

    // public function secondGen(){
    //     $firstGenReferrals = Auth::user()->referrals()->with([
    //         'referrals' => function ($query) {
    //             $query->with(['investment' => function ($q) {
    //                 $q->where('status', 2);
    //             }]);
    //         }
    //     ])->get();

    //     return view('two-gen', compact('firstGenReferrals'));
    // }

    // public function thirdGen(){
    //     $referrals = Auth::user()->referrals()->with([
    //         'referrals.referrals' => function ($q) {
    //             $q->with(['investment' => function ($inv) {
    //                 $inv->where('status', 2);
    //             }]);
    //         }
    //     ])->get();

    //     return view('three-gen', compact('referrals'));
    // }
    
    public function firstGen()
    {
        $referrals = User::where('referrer_id', auth()->id())
            ->withCount([
                'investment as running_bots' => function($q) {
                    $q->where('status', 2);
                },
                'investment as expired_bots' => function($q) {
                    $q->where('status', 3);
                },
                'referrals as downline_count',
                'bids as manual_bids_count' => function($q) {
                    $q->where('type', 'manual_bid');
                },
                'bids as manual_bids_successful' => function($q) {
                    $q->where('type', 'manual_bid')->where('status', 1);
                },
                'bids as manual_bids_pending' => function($q) {
                    $q->where('type', 'manual_bid')->where('status', 0);
                },
                'bids as manual_bids_failed' => function($q) {
                    $q->where('type', 'manual_bid')->where('status', 2);
                },
                'sells as manual_sells_count' => function($q) {
                    $q->where('type', 'manual_sell');
                },
                'sells as manual_sells_successful' => function($q) {
                    $q->where('type', 'manual_sell')->where('status', 1);
                },
                'sells as manual_sells_pending' => function($q) {
                    $q->where('type', 'manual_sell')->where('status', 0);
                },
                'sells as manual_sells_failed' => function($q) {
                    $q->where('type', 'manual_sell')->where('status', 2);
                }
            ])
            ->withSum([
                'investment as running_bots_total' => function($q) {
                    $q->where('status', 2);
                }
            ], 'amount')
            ->withSum([
                'investment as expired_bots_total' => function($q) {
                    $q->where('status', 3);
                }
            ], 'amount')
            ->select('id', 'first_name', 'last_name', 'username', 'email', 'balance', 'rebates', 'email_verified_at', 'kyc_status', 'created_at')
            ->paginate(20);
        
        return view('one-gen', compact('referrals'));
    }
    
    public function secondGen()
    {
        $firstGenIds = User::where('referrer_id', auth()->id())->pluck('id');
        
        $referrals = User::whereIn('referrer_id', $firstGenIds)
            ->withCount([
                'investment as running_bots' => function($q) {
                    $q->where('status', 2);
                },
                'investment as expired_bots' => function($q) {
                    $q->where('status', 3);
                },
                'referrals as downline_count',
                'bids as manual_bids_count' => function($q) {
                    $q->where('type', 'manual_bid');
                },
                'bids as manual_bids_successful' => function($q) {
                    $q->where('type', 'manual_bid')->where('status', 1);
                },
                'bids as manual_bids_pending' => function($q) {
                    $q->where('type', 'manual_bid')->where('status', 0);
                },
                'bids as manual_bids_failed' => function($q) {
                    $q->where('type', 'manual_bid')->where('status', 2);
                },
                'sells as manual_sells_count' => function($q) {
                    $q->where('type', 'manual_sell');
                },
                'sells as manual_sells_successful' => function($q) {
                    $q->where('type', 'manual_sell')->where('status', 1);
                },
                'sells as manual_sells_pending' => function($q) {
                    $q->where('type', 'manual_sell')->where('status', 0);
                },
                'sells as manual_sells_failed' => function($q) {
                    $q->where('type', 'manual_sell')->where('status', 2);
                }
            ])
            ->withSum([
                'investment as running_bots_total' => function($q) {
                    $q->where('status', 2);
                }
            ], 'amount')
            ->withSum([
                'investment as expired_bots_total' => function($q) {
                    $q->where('status', 3);
                }
            ], 'amount')
            ->with('referrer:id,username')
            ->select('id', 'first_name', 'last_name', 'username', 'email', 'balance', 'rebates', 'email_verified_at', 'kyc_status', 'created_at', 'referrer_id')
            ->paginate(20);
        
        return view('two-gen', compact('referrals'));
    }
    
    public function thirdGen()
    {
        $firstGenIds = User::where('referrer_id', auth()->id())->pluck('id');
        $secondGenIds = User::whereIn('referrer_id', $firstGenIds)->pluck('id');
        
        $referrals = User::whereIn('referrer_id', $secondGenIds)
            ->withCount([
                'investment as running_bots' => function($q) {
                    $q->where('status', 2);
                },
                'investment as expired_bots' => function($q) {
                    $q->where('status', 3);
                },
                'referrals as downline_count',
                'bids as manual_bids_count' => function($q) {
                    $q->where('type', 'manual_bid');
                },
                'bids as manual_bids_successful' => function($q) {
                    $q->where('type', 'manual_bid')->where('status', 1);
                },
                'bids as manual_bids_pending' => function($q) {
                    $q->where('type', 'manual_bid')->where('status', 0);
                },
                'bids as manual_bids_failed' => function($q) {
                    $q->where('type', 'manual_bid')->where('status', 2);
                },
                'sells as manual_sells_count' => function($q) {
                    $q->where('type', 'manual_sell');
                },
                'sells as manual_sells_successful' => function($q) {
                    $q->where('type', 'manual_sell')->where('status', 1);
                },
                'sells as manual_sells_pending' => function($q) {
                    $q->where('type', 'manual_sell')->where('status', 0);
                },
                'sells as manual_sells_failed' => function($q) {
                    $q->where('type', 'manual_sell')->where('status', 2);
                }
            ])
            ->withSum([
                'investment as running_bots_total' => function($q) {
                    $q->where('status', 2);
                }
            ], 'amount')
            ->withSum([
                'investment as expired_bots_total' => function($q) {
                    $q->where('status', 3);
                }
            ], 'amount')
            ->with('referrer:id,username')
            ->select('id', 'first_name', 'last_name', 'username', 'email', 'balance', 'rebates', 'email_verified_at', 'kyc_status', 'created_at', 'referrer_id')
            ->paginate(20);
        
        return view('three-gen', compact('referrals'));
    }

    public function wallet(){

        return view('wallet');

    }

    public function banned(){
        if(auth()->user()->status == 1){
            return redirect(route('home')); 
        }else{
            return view('banned');
        }
    }
    
    public function twofaPage()
    {
        return view('2fa');
    }
    
    public function twofaDecision(Request $request)
    {
        if($request->has('on')){
            tap(auth()->user())->update([
                'is_two_factor' => 1
            ]);
            
            return redirect()->back()->with('message', 'You have successfully enabled 2FA Authentication on your Store Account!');
        } elseif($request->has('off')) {
            tap(auth()->user())->update([
                'is_two_factor' => 0
            ]);
            
            return redirect()->back()->with('message', 'You have successfully disabled 2FA Authentication on your Store Account!');
        }
    }
    
    public function twoFaVerification()
    {
        return view('2fa-verify');
    }
    
    public function resendTwoFaMail(Request $request)
    {
        $user = auth()->user();
        $token = random_int(1000, 9999);

        $expiresAt = Carbon::now()->addMinutes(30);
        $user->two_factor_expiry_date = $expiresAt;
        $user->two_factor_code = $token;
        $user->save();

        try {
            $mail = new MailController();
            $mail->twoFaMail($token, $user->email);
            return redirect()->back()->with('message', 'Your 2FA Authentication Token has been resent to your email inbox');
        } catch (\Throwable $th) {
            return redirect()->back()->with('error', 'A mail cannot be sent at this time');
        }
    }
    
    public function verifyTwoFa(Request $request)
    {
        $request->validate([
            'token' => 'required',
        ]);
        
        $user = auth()->user();
        $token = $request->token;
        $expiryDate = Carbon::parse($user->two_factor_expiry_date);
        $now = Carbon::now();
        
        if($user->two_factor_code != $token){
            return redirect()->back()->with('error', 'Incorrect Token!');
        }
        
        if ($expiryDate->lt($now)) {
            return redirect()->back()->with('error', 'Token Has Expired, Resend Token.');
        }
        
        $user->two_factor_code = null;
        $user->save();
        session()->put('verified_2fa', true);
        return redirect()->route('home');
    }
    
}
