<?php

namespace App;

use Illuminate\Database\Eloquent\Model;
use Auth;
use DB;
use Crypt;

class Deduction extends Model
{
    private $generic_condition;

    public function __construct()
    {
           
       $this->setCondition(['is_recycle' => '0']);
    }

    public function setCondition($condition = [])
    {
        $this->generic_condition = $condition;
    }

    public function getCondition()
    {
        return $this->generic_condition;
    }

    public function storeDeduction($object)
    {
          
        return DB::transaction(function () use ($object){
        
            $deduction = new Deduction;
            
            $deduction->title           = $object['title'];

            $deduction->amount          = $object['amount'];
      

            $deduction->save();

            return with($deduction);

        });

    } 

    public function updateInstallmentsDate($object)
    {
         return DB::transaction(function () use ($object){
        
            for($i= 0; $i< @count($object['id']); $i++)
            {
              
              
                $deduction = Deduction::find($object['id'][$i]);

            if(isset($deduction->id))
            {
                $deduction->created_at   = $object['installment_date'][$i];
             
                $deduction->update();
          
            }
        }

        return 1;

        });


    }


    // Updating Deduction modal data

    public function updateDeduction($object)
    {
          
        return DB::transaction(function () use ($object){
        
            $deduction = Deduction::find($object['deduction']);


             
            if(isset($deduction->id))
            {

                $deduction->title           = $object['title'];

                $deduction->amount          = $object['amount'];

                $deduction->update();
            }


            return with($deduction);

        });

    } 

    public function updateDeductionStatus($id)
    {
          
        return DB::transaction(function () use ($id){
        
            $deduction = Deduction::find($id);


             
            if(isset($deduction->id))
            {

                $deduction->status           = 'paid';

        

                $deduction->update();
            }


            return with($deduction);

        });

    } 

    public function getDistinctDeduction($distinct_column,$column = "*")
    {
      $condition = $this->getCondition();



      return Deduction::where($condition)->whereNull('loan_id')->distinct($distinct_column)->select($column)->get();
    }

      public function getNewDeductionList($month,$year,$operator,$minute_deductions)
    {
        return Deduction::where($this->getCondition())->whereMonth('created_at',$operator,$month)->whereYear('created_at',$operator,$year)->whereNotIn('id',$minute_deductions)->orderBy('id','desc')->get();
    }

    
     //RETRIEVING Deduction BY ID
    public function getDeductionById($id)
    {
        
       $condition = $this->getCondition();
       $condition += ['id' => $id];
        return Deduction::where($condition)->first();

    }
    public function getDeductionList()
    {
        return Deduction::where($this->getCondition())->orderBy('id','desc')->get();;
    }

     public function getDeductionListByDate($month,$year,$operator)
    {
        return Deduction::where($this->getCondition())->whereMonth('created_at',$operator,$month)->whereYear('created_at',$operator,$year)->orderBy('id','desc')->get();;
    }

    public function getInstallmentsByLoanId($loan_id)
    {
        $condition = $this->getCondition();

        $condition += ['loan_id' => $loan_id,'status' => 'unpaid'];

        return Deduction::where($condition)->whereNull('created_at')->orderBy('id','asc')->get();
    }

      public function getDeductionsByLoan($loan_id)
    {
        $condition = $this->getCondition();

        $condition += ['loan_id' => $loan_id];

        return Deduction::where($condition)->whereNotNull('created_at')->orderBy('id','asc')->get();
    }

       public function GetReturnedAmountSum($loan_id)
    {
        $condition = $this->getCondition();

        $condition += ['loan_id' => $loan_id,'status'=>'paid'];

        return Deduction::where($condition)->sum('amount');
    }

    public function getCurrentInstallment($deduction_id)
    {

      $condition = $this->getCondition();

      return Deduction::where($condition)->whereNotNull('loan_id')->whereIn('id',$deduction_id)->orderBy('id','asc')->first();


    }

    public function updateLoanInstallments($user_id,$deduction_id,$deduction_amount)
    {
         return DB::transaction(function () use ($user_id,$deduction_id,$deduction_amount){



         $condition = $this->getCondition();

         $condition += ['status' => 'unpaid','user_id' => $user_id];

         $curr_installment = $this->getCurrentInstallment($deduction_id);

         $curr_installment_amount = $curr_installment->amount;

         $curr_installment->amount = $deduction_amount;

         $curr_installment->update();


         $next_installments = Deduction::where($condition)->whereNotNull('loan_id')->whereNotIn('id',$deduction_id)->orderBy('id','asc')->get();

         //SUBTRACT EXCEEDING AMOUNT FROM NEXT INSTALLMENTS
         if($curr_installment_amount < $deduction_amount)
         {
          $loan = new Loan;

          $loan_amount = $curr_installment->loan->net_amount;

         if($deduction_amount > $loan_amount)
         {

          return 0;

         }

         
            $exceeding_amount = $deduction_amount - $curr_installment_amount;


            for($i=0; $i< @count($next_installments); $i++)
            {
            
                $next_amount = $next_installments[$i]['amount'];

                if($exceeding_amount <= 0)
                {
                    break;
                }

                if($exceeding_amount <= $next_amount)
                {

                    $next_installments[$i]['amount'] = $next_amount-$exceeding_amount;

                    $next_installments[$i]->update();
          
                    $exceeding_amount = $next_amount - $exceeding_amount;
          
                }
                else
                {
                    $next_installments[$i]['amount'] = 0;

                    $next_installments[$i]->update();
                   

                    $exceeding_amount = $exceeding_amount -$next_amount;
                }

                 
            }

         }
         //ADD EXCEEDING AMOUNT TO NEXT INSTALLMENTS
         elseif($curr_installment_amount > $deduction_amount)
         {
            $lag_amount =  $curr_installment_amount - $deduction_amount;

            if(isset($next_installments[0]->id))
            {
                $next_installments[0]['amount'] = $next_installments[0]['amount'] + $lag_amount;
                $next_installments[0]->update();
            }




         }

         return 1;


       

     });

        

    }

    public function loan()
    {
        return $this->belongsTo(Loan::class,'loan_id')->withDefault();
    }

     
}
