<?php
namespace App\Http\Controllers\Api\Purchase;

use App\Http\Controllers\Controller;
use App\Models\Bill;
use App\Models\BillItem;
use App\Models\User;
use App\Service\StockEntryService;
use App\Models\Customers;
use App\Models\Transaction;
use App\Models\DsrSupplierSummary;
use App\Models\MiceSupplierSummary;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Redirect;
use App\Service\AccountsTransactionService;
use Auth;
use App\Service\StaticMaster;
use Log;
use Carbon\Carbon;
// use validator;

class BillsController extends Controller
{
    public function list(Request $request)
    {
        $user=Auth::user();
        $validator=validator($request->all(),[

            'fy'=>'required',
            // 'warehouse_id'=>'required'

        ]);

        if ($validator->fails()) { 

            return [
                'success' => false, 
                'message' => $validator->errors()->first()
            ];

        } else {

            $bills= Bill::where('is_disabled',0)
                ->with("items","vendor","items.item:id,name")
                // ->where('warehouse_id',$request['warehouse_id'])
                ->where('fy',$request['fy']);

            if ($request['status']!='' && isset($request['status'])) {
                $bills=$bills->where('status',$request['status']);
            }

            if($request['statuses']!='' && isset($request['statuses'])){
                $bills=$bills->whereIn('status',$request['statuses']);
            }

            // for pending credit note invoices
            // sending is_credit_note_close=1 from frontend
            if($request['is_debit_note_close']==1 && isset($request['is_debit_note_close'])){
                $bills=$bills->where('is_debit_note_close',0);
            }

            if($request['search']!=null && $request['search']!=''){

                // $searchTerm = $request['search'];

                $bills = $bills->where(function ($query) use ($request) {

                    $query->where('bill_no', 'LIKE', '%' . $request['search'] . '%')

                        ->orWhere('reference_no', 'LIKE', '%' . $request['search'] . '%')

                        ->orWhere('display_name', 'LIKE', '%' . $request['search'] . '%')

                        ->orWhere('vendor_type', 'LIKE', '%' . $request['search'] . '%')

                        // ->orWhere('mobile_no', 'LIKE', '%' . $request['search'] . '%')

                        ->orWhere('phone', 'LIKE', '%' . $request['search'] . '%')

                        ->orWhere('email', 'LIKE', '%' . $request['search'] . '%');
                });

            }

            if(isset($request['vendor_id']) && $request['vendor_id']!='' && $request['vendor_id']!=null){
                $bills=$bills->where('vendor_id',$request['vendor_id']);
            }

            // get custom_date data by transaction_date

            if ($request['custom_date']!='' && isset($request['custom_date'])) {

                $customDate = $request->custom_date;

                $bills = $bills->whereDate('transaction_date', $customDate);

            }

                // get last modified data by updated_at

            if ($request['updated_at']!='' && isset($request['updated_at'])) {

                $bills=$bills->orderBy('updated_at');

            }

                // get fromDate toDate data by created_at

            if ($request['from_date']!='' && isset($request['to_date'])) {

                $fromDate = $request->from_date;

                $toDate = $request->to_date;

                // 'fromDate' and 'toDate'

                $bills = $bills->whereBetween('transaction_date', [$fromDate, $toDate]);

            }

            
            $count=$bills->count();

            if(isset($request['sort_by']) && $request['sort_by']!='' && $request['sort_by']!=null){
                
                $sort_order=$request['sort_order']==1?'asc':'desc';

                $bills = $bills->orderby($request['sort_by'],$sort_order);

            }else{
                $bills = $bills->orderby('id','desc');
            }
        
            $bills=$bills->skip($request['noofrec']*($request['currentpage']-1))->take($request['noofrec']??100)->get();

            $response=[
                'message'=>'Bills List Fetched Successfully',
                'success'=>true,
                'count'=>$count,
                'bills'=>$bills
            ];

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

    public function details(Request $request)
    {
        // Validate Item
        $user=Auth::user();

        $validator=validator($request->all(),[
            'id'=>'required'
        ]);

        if ($validator->fails()) { 
            return [
                'success' => false, 
                'message' => $validator->errors()->first()
            ];
        } else {

            $bill = Bill::where('id',$request['id'])
                ->with('items','vendor','items.item','activity')
                ->first();

            if ($bill['items']->count() > 0) {
                foreach ($bill['items'] as $key => $item) {
                    if (!empty($item->service_data)) {
                        $service_data = $item->service_data; // already array

                        // Getting Guests 
                        $guestIds = explode(',', $service_data['guest_ids'] ?? '');
                        $service_data['guests'] = User::whereIn('id', $guestIds)->get();

                        // Laravel will auto re-encode to JSON when saving
                        $item->service_data = $service_data;
                        $item->save();
                    }
                }
            }

            $transaction=Transaction::where('transaction_type',StaticMaster::$PURCAHSE_TRANSACTION_TYPE)
                ->where('transaction_id',$request['id'])
                ->where('is_disabled',0)
                ->with('account:id,account_name,account_code')
                ->get();

            $response=[
                'message'=>"Bill details fetch successfully",
                'success'=>true,
                'bill'=>$bill,
                'transaction'=>$transaction
            ];

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

    }

    public function destroy(Request $request)
    {

        $user=Auth::user();

        $validator=validator($request->all(),[
            'id'=>'required'
        ]);

        if ($validator->fails()) { 

            return [
                'success' => false, 
                'message' => $validator->errors()->first()
            ];

        } else {

            try{
                $bills = Bill::findOrFail($request['id']);

            } catch (\Illuminate\Database\Eloquent\ModelNotFoundException $e) {
                // Return error message in JSON if ID not found
                return response()->json(['success'=>false,'message' => 'Invalid Id to delete '], 404);
            }

            if($bills['is_approved']==0){

                $bills['is_disabled']=1;

                $bills->update();

                $bill_items=BillItem::where('transaction_id',$bills['id'])->get();
                
                foreach ($bill_items as $value){
                    $value['is_disabled'];

                    $value->update();
                }

                $response=[
                    'success'=>true,
                    'message'=>'Bill deleted Successfully'
                ];

            }else{

                $response=[
                    'success'=>false,
                    'message'=>'Bill is Approved. You can\'t delete this bill.'
                ];

            }

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

    public function approveBill(Request $request){
        $validator=validator($request->all(),[
            'bill_id'=>'required'
        ]);


        $entity='Bill';

        if ($validator->fails()) {
            # code...
            
            $response=[ 
                'success'=>false,
                'message'=>$validator->errors()->first()
                
            ];
            return response()->json($response);    
        }

        else{
            $transaction = Bill::find($request->bill_id);
            $transaction['is_approved']=1;
            $transaction->update();  

            $stockEntryService = new StockEntryService;
            $stockEntryService->saveStockEntries( $transaction,$entity,1);
        }
        $response=[ 
            'success'=>true,
            'message'=>'Bill Approved Successfully'
        ];

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

    public function statusBill(Request $request){
        // Validate Item
        $status_change='';
        $today_date = Carbon::now()->format('Y-m-d');

        $validator=validator($request->all(),[
            'id'=>'required',
            'status'=>'required'
        ]);

        if ($validator->fails()) { 

            return [
                'success' => false, 
                'message' => $validator->errors()->first()
            ];

        } else {

            $transaction = Bill::findOrFail($request->id);

            $transaction['status']=$request['status'];

            if($request['status']==1){
                //Bill Approved

                $status_change='Approved';

                $entity='Bill';

                if($transaction['is_grn_convert']==0){
                    Log::info("Bill Approved :".$transaction['transaction_type']);
                    $stockEntryService = new StockEntryService;
                    $stockEntryService->saveStockEntries( $transaction,$entity,1);
                }

                // Setting Approving Date as today date
                $transaction['approved_date']=$today_date;

                // Saving Accounts Entries
                $accountsEntryService = new AccountsTransactionService;
                $accountsEntryService->purchase_accounts_transaction($transaction);

                //Naksha if Supplier bill is approved
                //Check supplier_summary_ids is not null
                if($transaction['supplier_summary_ids']!=null){
                    //convert stringyfy to array
                    $supplier_summary_ids = json_decode($transaction['supplier_summary_ids'], true);

                    foreach($supplier_summary_ids as $supplier_summary_id){
                        if($transaction['is_dsr']==1){
                            $supplier_summary = DsrSupplierSummary::where('id',$supplier_summary_id)->first();
                            if($supplier_summary){
                                $supplier_summary['is_billed'] = 1;
                                $supplier_summary->update();
                            }
                        }
                        if($transaction['is_mice']==1){
                            $supplier_summary = MiceSupplierSummary::where('id',$supplier_summary_id)->first();
                            if($supplier_summary){
                                $supplier_summary['is_billed'] = 1;
                                $supplier_summary->update();
                            }
                        }
                    }
                }

                $transaction['is_approved']=1;

                $transaction->update();

            }
            if($request['status']==2){
                $status_change='Declined';
                $transaction['is_approved']=0;
            }
            if($request['status']==0){
                $status_change='Draft';
            }

            $transaction->update();  

            $response=[ 

                'success'=>true,
    
                'message'=>'Bill '.$status_change.' Updated Successfully'
    
            ];

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

        }
    }

    public function pendingBill(Request $request){
        $user = Auth::user();

        $validator=validator($request->all(),[
            'fy'=>'required',
            // 'warehouse_id'=>'required',
            'vendor_id'=>'required'
        ]);

        if ($validator->fails()) { 

            return [
                'success' => false, 
                'message' => $validator->errors()->first()
            ];

        } else {

            $bill=Bill::whereRaw('amount_paid < total');
                // ->where('organisation_id',$user['active_organisation'])
                // 
                // ->where('fy',$request['fy']);
                // ->where('warehouse_id',$request['warehouse_id']);

            if(isset($request['vendor_id']) && $request['vendor_id']!='' && $request['vendor_id']!=null){
                $bill=$bill->where('vendor_id',$request['vendor_id']);
            }

            if(isset($request['bill_no']) && $request['bill_no']!='' && $request['bill_no']!=null){
                $bill=$bill->where('bill_no',$request['bill_no']);
            }

            // $unpaid_amount=$bill->sum('total');

            $unpaid_amount = $bill->get()->sum(function($inv) {
                return $inv->total - $inv->amount_paid;
            });

            $bill=$bill->get();

            $vendor=User::where('id',$request['vendor_id'])
                ->with('billing_address','shipping_address','address','bank_details')
                ->first();

            $response=[
                'success'=>true,
                'unpaid_amount'=>$unpaid_amount,
                'message'=>'Total pending Bills retrieved successfully',
                'bills'=>$bill,
                'vendor'=>$vendor
            ];

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

    }

}