<?php

namespace App\Http\Controllers\backend;

use Illuminate\Http\Request;
use App\Http\Controllers\Controller;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\DB;
use Illuminate\Support\Facades\Input;
use Carbon\Carbon;
use App\Models\Productcategory;
use App\Models\PurchaseDetail;
use App\Models\Product;
use App\Models\Customer;
use App\Models\CustomerLedger;
use App\Models\CustomerAccount;
use App\Models\Sale;
use App\Models\SaleDetail;
use App\Models\CustomerRecord;
use App\Models\StockLedger;
use App\Models\PossibleDate;
use App\Models\SaleDraft;
use App\Models\Type;
use Session;
use PDF;

class SalesController extends Controller
{
    public function index(Request $request){
        $this->checkpermission('sales-list');

        /*$from_date =  date('Y-m-01') ;
        $to_date = date('Y-m-d');
        $show = $request->show;
        if($show != ''){
            //$sales = Sale::whereDate('sale_date', '>=', $from_date)->whereDate('sale_date', '<=', $to_date)->latest()->paginate($show);
            $sales = Sale::latest()->paginate($show);
        }else{
            $sales = Sale::latest()->paginate(setting()->ddspinp);
        }*/
        $show = $request->show ?: setting()->ddspinp;

        $query = Sale::query();
        if ($request->category) {
            // If category is provided, filter by category using whereHas
            $query->whereHas('details', function ($query) use ($request) {
                $query->where('productcategory_id', $request->category);
            });
        }
    
        $sales = $query->orderBy('id','DESC')->paginate($show);
    
        $categories = Productcategory::has('products')->orderBy('name','ASC')->get();
        $sales->withPath(url()->full());
        return view('backend.sales.list', compact('sales','categories'));
    }
    public function invoice_search(Request $request){
        if($request->column == 'name' || $request->column == 'phone'){
            /*$customer = Customer::where($request->column,$request->search_value)->first();
            if($customer){
                $sales = $customer->sales;
            }else{
                $sales = '';
            }*/
            $sales = Sale::join('customers', 'sales.customer_id', '=', 'customers.id')
                        ->where('customers.'.$request->column, '=', $request->search_value)
                        ->orderBy('sales.sale_date', 'DESC')
                        ->paginate(setting()->ddspinp);
        }
        if($request->column == 'invoice_no' || $request->column == 'grand_total_price' || $request->column == 'sale_date' ){
            $sales = Sale::with('customer')->where($request->column,$request->search_value)->orderBy('sale_date','DESC')->paginate($request->has('page') ? 1 : 2);
        }
        if($request->column == ''){
            return redirect()->route('sales.list');
        }
        $categories = Productcategory::has('products')->orderBy('name','ASC')->get();
        $sales->withPath(url()->full());
        if(!empty($sales)){
            return view('backend.sales.list', compact('sales','categories'));
        }else{
            return redirect()->route('sales.list')->with('error','Woops!! no result found');
        }
    }
    public function create(Request $request){
        $this->checkpermission('sales-create');
        if($request->type != ''){
            $type = Type::find($request->type);
            $categories = Productcategory::has('products')->where('type_id',$request->type)->orderBy('name','ASC')->get();
            $drafts = SaleDraft::with('pd')->where('type_id',$request->type)->where('user_id',Auth::id())->get();
            return view('backend.sales.create', compact('categories','type','drafts'));
        }else{
            $types = Type::latest()->get();
            return view('backend.sales.type', compact('types'));
        }
    }
    public function store(Request $request){
        $closing =  DB::table('cash_closings')->where('closing_date', date('Y-m-d',strtotime($request->sale_date)))->exists();
        
        //return $closing;

        if($closing != true){
            // return $request->all();
            $this->validate($request,[
                'customer_name'=>'required',
                'sale_date'=>'required',
            ]);
    
            $data = $request->except('_token','submit');
            
            $invoice = Sale::where('sale_date',date('Y-m-d',strtotime($request->sale_date)))->latest()->first();
            if($invoice != ''){
                $dt = date('dmy',strtotime($request->sale_date));
                $len = strlen((string)$dt);
                $lv = substr($invoice->invoice_no, $len);
                $inv_no = $lv+1;
                $invno = $dt.$inv_no;
            }
            else{
                $invno = date('dmy',strtotime($request->sale_date)).'1';
            }

            $dt = Carbon::parse($request->sale_date);
            $date = $dt->toDateTimeString();
            
            $sale = new Sale();
            $sale->user_id = Auth::id();
            $sale->type_id = $request->invoice_type_id;
            $dt = Carbon::parse($request->sale_date);
            $sale->sale_date = $dt->toDateTimeString();
            $sale->invoice_no = $invno;
            if($request->customer_id == ''){
                $customer = new Customer();
                $customer->name = $request->customer_name;
                $customer->phone = $request->customer_phone;
                $customer->save();

                $sale->customer_id = $customer->id;  
            }else{
                $sale->customer_id = $request->customer_id;
            }

            $sale->total_price = $request->total_price;
            $sale->discount = $request->discount;
            $sale->other_cost = $request->other_cost;
            $sale->grand_total_price = $request->grand_total;
            $sale->payment = $request->payment;
            //$sale->payment_by = $request->payment_by;
            if($request->grand_total >= $request->payment){
                $sale->payment_status = 'Due';
            }else{
                $sale->payment_status = 'Paid';
            }
            $sale->due_amount = $request->due;
            $sale->note = $request->note;
            $sale->created_by = Auth::id();
            $sale->save();
            
            if($request->payment > 0){
                $ca = new CustomerAccount();
                $ca->payment_date = $dt->toDateTimeString();
                $ca->customer_id = $sale->customer_id;
                $ca->sale_id = $sale->id;
                $ca->amount = $request->payment;
                $ca->note = $request->note;
                $ca->created_by = Auth::id();
                $ca->save();
            }


            for($i = 0; $i<count($data['purchase_details_id']); $i++ ){
                $detail = new SaleDetail();
                $detail->sale_id = $sale->id;
                $detail->customer_id = $sale->customer_id;
                $detail->purchase_detail_id = $data['purchase_details_id'][$i];
                $detail->type_id = $data['type_id'][$i];
                // search purchase details 
                $pur = PurchaseDetail::find($data['purchase_details_id'][$i]);

                //$detail->warehouse_id = $pur->warehouse_id;
                $detail->product_id = $pur->product_id;
                $detail->productcategory_id = $pur->productcategory_id;
                //$detail->brand_id = $pur->brand_id;
                $detail->unit_id = $pur->unit_id;
                $detail->invoice_no = $sale->invoice_no;

                $dt2 = Carbon::parse($request->sale_date);
                $data['sale_date'] = $dt2->toDateTimeString();

                $detail->sale_date = $data['sale_date'];
                $detail->height = $data['height'][$i];
                $detail->width = $data['width'][$i];
                $detail->size = $data['size'][$i];
                $detail->quantity = $data['ordered_quantity'][$i];
                $detail->tsqf = $data['tsqf'][$i];
                $detail->unit_price = $data['sale_price'][$i];
                $detail->discount = $data['single_discount'][$i];
                $detail->created_by = Auth::id();
                $detail->save();
                
                $pd = PurchaseDetail::where('product_id',$pur->product_id)->sum('now_stock');
                
                /* for decrement stock quantity*/
                DB::table('purchase_details')
                    ->where('id', '=', $data['purchase_details_id'][$i])
                    ->decrement('now_stock', $data['tsqf'][$i]);
                
                $stock = new StockLedger();
                $stock->transaction_date = $dt->toDateTimeString();
                $stock->category_id = $detail->productcategory_id;
                $stock->unit_id = $detail->unit_id;
                $stock->product_id = $detail->product_id;
                $stock->sale_id = $sale->id;
                $stock->sale_detail_id = $detail->id;
                $stock->invoice_no = $invno;
                $stock->previous_quantity = $pd; 
                $stock->sold_quantity = $detail->tsqf;
                $stock->total_quantity = $pd;
                $stock->current_quantity = $pd - $detail->tsqf;
                $stock->created_by = Auth::id();
                $stock->save();

            };
            
            /*-------customer record section----------*/
            $cus = Customer::with('sales')->find($sale->customer_id);
            
            $record = new CustomerRecord();
            $record->customer_id = $sale->customer_id;
            $record->transaction_date = $dt->toDateTimeString();
            $record->user_id = $sale->user_id;
            $record->total_price = $request->grand_total;
            $record->payment_amount = $request->payment;
            $record->due_amount = $request->due;
            $total_due = $cus->sales->sum('due_amount');
            $record->previous_due = $total_due - $request->due;
            $record->total_due = $total_due;
            $record->note = $request->note;
           // $record->message = //"Dear Customer ".$cus->name.", your invoice total price is ".$request->grand_total."/=, Payment ".$request->payment."/= Due ".$request->due."/= Previous Due ".$total_due - $request->due."/= Current Due ".$total_due." Thanks By ".about()->english_name.", ".about()->address;
            $record->created_by = $sale->user_id;
            $record->save();
            
            $ledger = new CustomerLedger();
            $ledger->customer_id = $sale->customer_id;
            $ledger->sale_id = $sale->id;
            $ledger->transaction_date = $dt->toDateTimeString();
            $ledger->invoice_no = $sale->invoice_no;
            $ledger->transaction_type = 'Sales';
            $ledger->sale_amount = $request->grand_total;
            $ledger->payment_amount = $request->payment;
            $ledger->current_balance = $total_due;
            $ledger->created_by = Auth::id();
            $ledger->save();
            
            if(isset($request->possible_date)){
                $pbdate = new PossibleDate();
                $pbdate->customer_id = $sale->customer_id;
                $pbdate->sale_id = $sale->id;
                $pbdate->possible_date = date('Y-m-d',strtotime($request->possible_date));
                $pbdate->amount = $request->due;
                $pbdate->created_by = Auth::id();
                $pbdate->save();
            }
            /*--------check the sms sending section--------*/
            if(isset($request->sms)){
                //return $request->sms;
                $to = $cus->phone;//"017xxxxxxx,+88016xxxxxxx";
                $token = "7a787dd847f4650b1ba1adfb8771c733";
                $message = about()->english_name." Dear customer invoice total:".$record->total_price.',pay:'.$record->payment_amount.',due:'.$record->due_amount.',prev due:'.$record->previous_due.',total due:'.$record->total_due.',Note:'.$record->note.',Date:'.date('d-m-Y',strtotime($record->transaction_date)).'.'.about()->phone;
                $url = "http://api.greenweb.com.bd/api.php?json";
                $data= array(
                    'to'=>"$to",
                    'message'=>"$message",
                    'token'=>"$token"
                ); // Add parameters in key value

                $ch = curl_init(); // Initialize cURL
                curl_setopt($ch, CURLOPT_URL,$url);
                curl_setopt($ch, CURLOPT_ENCODING, '');
                curl_setopt($ch, CURLOPT_POSTFIELDS, http_build_query($data));
                curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
                $smsresult = curl_exec($ch);
                //Result
                //echo $smsresult;
                //Error Display
                //echo curl_error($ch);
                DB::table('sms')->where('id',1)->decrement('sms_balance',2);
            }
            
            DB::table('sale_drafts')->where('user_id', Auth::id())->where('type_id',$request->invoice_type_id)->delete();
            
            return back()->with('success','Sales Information Save Successfull');
         
        }
        else{
            return redirect()->back()->with('error','Woops! After cash closing all transaction has been stoped');
        }
    }
    /*----------Customer Details Section------------------*/
    public function customerList(){
        $customer = Customer::orderBy('name','ASC')->get();
        $data = [];
        foreach($customer as $cus){
            $data[] = $cus->name.', '.$cus->phone;
        }
        return response()->json($data);
    }
    public function customerDetails(Request $request){
        $customer = $request->customer;
        /**
         * explode customer name and phone then search the customer for detail information
         */
        $value  = explode(',',$customer); 
        $name = $value[0];
        $phone = isset($value[1]) ? $value[1] : null;
       // return response()->json($phone);
        if($name != '' && $phone != ''){
            $data = Customer::where('name',trim($name))->where('phone',trim($phone))->firstOrFail();
        }
        else{
            $data = '';
        }
        return response()->json($data);
    }
    public function productList2(Request $request){
        $products  = DB::table('purchase_stocks')
                        ->join('products', 'purchase_stocks.product_id', '=', 'products.id')
                        ->select('purchase_stocks.*','products.product_name')
                        ->where('purchase_stocks.productcategory_id',$request->type)
                        ->where('purchase_stocks.status',true)
                        //->where('purchase_stocks.now_stock','>',50)
                        ->get(); 
        return response()->json($products);
    }
    public function productDetails2(Request $request){
       //$products = PurchaseDetail::find($request->id);
       $product  = DB::table('purchase_stocks')
                    ->join('products', 'purchase_stocks.product_id', '=', 'products.id')
                    ->join('productcategories', 'purchase_stocks.productcategory_id', '=', 'productcategories.id')
                    ->join('types', 'purchase_stocks.type_id', '=', 'types.id')
                    ->join('units', 'purchase_stocks.unit_id', '=', 'units.id')
                    ->select('purchase_stocks.*','products.product_name','products.sale_price', 'products.code','types.name as type_name','productcategories.name as category_name','units.name as unit_name')
                    ->where('purchase_stocks.id',$request->id)
                    ->first();
                    
        $sdf = new SaleDraft();
        $sdf->user_id = Auth::id();
        $sdf->type_id = $product->type_id;
        $sdf->category_id = $product->productcategory_id;
        $sdf->unit_id = $product->unit_id;
        $sdf->purchase_detail_id = $product->id;
        $sdf->product_id = $product->id;
        $sdf->product_name = $product->product_name;
        $sdf->code_no = $product->code;
        $sdf->height = 1;//$product->height;
        $sdf->width = 1;//$product->width;
        $sdf->size = 1;//$product->size;
        $sdf->purchase_price = $product->rate;
        $sdf->quantity = 1;
        $tsqf = (1 * $product->square_foot);
        //$tsqf = (1 * ($product->height * $product->width) / 144);
        //$sdf->tsqf = $tsqf;//settype($tsqf,'string');
       // $sdf->tsqf = settype($tsqf,'string');
        $sdf->tsqf = (string)$tsqf;
        $sdf->sale_price = $product->sale_price;
        
        $sdf->profit_amount = ($product->sale_price - $product->rate);
        $sdf->profit_total = ($product->sale_price - $product->rate) * 1;
        $sdf->purchase_price_total = $product->rate * 1;

        //$sdf->labour_cost = $product->labour_cost;
        //$sdf->labour_total = 1 * $product->labour_cost;
        if($product->type_name == 'Tiles'){
            $sdf->sub_total = $tsqf * $product->sale_price;
        }else{
            $sdf->sub_total = 1 * $product->sale_price;
        }
        $sdf->created_by = Auth::id();
        $sdf->save();
        
        return response()->json($product);
    }
    public function getallpdf(){
        $report = SaleDetail::join('products', 'products.id', '=', 'sale_details.product_id')
            ->select('sale_details.*', 'products.product_name')
            ->get();
        return view('backend.pdfbill.salesbill', compact('report'));
    }
    public function getcustomreport(Request $request){
        $start = $request->start;
        $end = $request->end;
        $report = SaleDetail::join('products', 'products.id', 'sale_details.product_id')
            ->select('sale_details.*', 'products.product_name')
            ->whereBetween('sale_details.sale_date', [$start, $end])
            ->get();
        $pdf = PDF::loadview('backend.pdfbill.allreport', compact('report', 'start', 'end'));
        return $pdf->download('salesreport.pdf');
    }
    public function show($id){
        $sale = Sale::find($id);
        return view('backend.sales.show',compact('sale'));
    }
    public function print($id){
        $sale = Sale::find($id);
        return view('backend.sales.print',compact('sale'));
    }
    public function sales_draft_update(Request $request){
        // return $request->all();
         $sdf =  SaleDraft::where('purchase_detail_id',$request->pd_id)->first();
        // return $sdf;
         $sdf->height = $request->height;
         $sdf->width = $request->width;
         $sdf->size = $request->size;
         $sdf->quantity = $request->quantity;
         $sdf->tsqf = $request->tsqf;
         
         $sdf->purchase_price = $request->purchase_price;
         $sdf->purchase_price_total = $request->ppt;
         $sdf->profit_amount = $request->profit_amount;
         $sdf->profit_total = $request->profit_total;
 
         $sdf->sale_price = $request->sale_price;
         $sdf->labour_cost = $request->labour_cost;
         $sdf->discount = $request->discount;
         $sdf->discount_type = $request->discount_type;
         $sdf->labour_total = $request->labour_total;
         $sdf->sub_total = $request->sub_total;
       //  $sdf->barcode = $request->barcode;
         $sdf->updated_by = Auth::id();
         $sdf->save();
         return response()->json('success');
     }
    public function sdf_remove(Request $request){
        $sdf = SaleDraft::where('purchase_detail_id',$request->pd_id)->first();
        $sdf->delete();
        return response()->json('Sales Draft Information Delete Success');
    }
}
