<?php

namespace App\Http\Controllers;

use App\Models\Business;
use App\Models\BusinessAttachment;
use App\Models\BusinessCategory;
use App\Models\BusinessReview;
use App\Models\User;
use Carbon\Carbon;
use Illuminate\Http\Request;
use App\Notifications;
use App\Notifications\BusinessContact;
use Illuminate\Notifications\Notification;
use Illuminate\Support\Facades\DB;
use Illuminate\Support\Facades\Notification as FacadesNotification;
use Illuminate\Support\Facades\Storage;
use PDO;
use stdClass;

class BusinessController extends Controller
{
    //
    public function saveBusiness(Request $request,$id)
    {
        $business_logo_base64_code = $request->input('business_logo_base64_code');	

        $business_cover_base64_code = $request->input('business_cover_base64_code');
        
        $business_logo_file_name = $request->input('business_logo_file_name');	

        if($request->input('id') != null)
        {
            $business = Business::find($request->input('id'));
        }
        else
        {
            $business = new Business();
        }

        $business->business_logo =  $request->input('business_logo');							
        $business->name = $request->input('name');								
        $business->about = $request->input('about');								
        $business->contact_title = $request->input('contact_title');								
        $business->contact_first_name = $request->input('contact_first_name');								
        $business->contact_last_name = $request->input('contact_last_name');								
        $business->contact_designation = $request->input('contact_designation');								
        $business->contact_phone = $request->input('contact_phone');							
        $business->contact_ext = $request->input('contact_ext');								
        $business->contact_mobile = $request->input('contact_mobile');
        $business->contact_email = $request->input('contact_email');							
        $business->address_1 = $request->input('address_1');								
        $business->address_2 = $request->input('address_2');
        $business->city = $request->input('city');								
        $business->state = $request->input('state');	
        $business->state1 = $request->input('state1');								
        $business->postal_code = $request->input('postal_code');							
        $business->country_id = $request->input('country_id'); 								
        $business->office_hours = $request->input('office_hours');								
        $business->website = $request->input('website');	
        
        $business->office_twitter = $request->input('office_twitter');	
        $business->office_facebook = $request->input('office_facebook');	
        $business->office_linkedin = $request->input('office_linkedin');	
        
        $business->official_email = $request->input('official_email');								
        $business->office_phone = $request->input('office_phone');
        $business->office_toll_free_phone = $request->input('office_toll_free_phone');
        $business->office_fax_phone = $request->input('office_fax_phone');							
        $business->type_id = $request->input('type_id');							
        $business->additional_details = $request->input('additional_details');								
        $business->special_offfers_discounts_details = $request->input('special_offfers_discounts_details');							
        $business->offer_id = $request->input('offer_id');								
        $business->status_id = $request->input('status_id');								
        $business->user_id = $id;
        $business->created_by = $id;

        $business->save();

        $business_categories_array = $request->input('business_categories');
        $business_sub_categories_array = $request->input('business_sub_categories');
        $business_office_hours_array = $request->input('business_office_hours');
        $business_offers_array = $request->input('business_offers');

        $business->businessCategories()->detach();
        if(sizeof($business_categories_array) > 0)
        {
            $business_categories = array();
            foreach($business_categories_array as $bca)
            {
                $category = new \stdClass();
                $category->category_id = $bca['category_id'];

                $business_categories [] = (array)$category;
            }
            $business->businessCategories()->attach($business_categories);
        }

        $business->businessSubCategories()->detach();
        if(sizeof($business_sub_categories_array) > 0)
        {
            $business_sub_categories = array();
            foreach($business_sub_categories_array as $bsca)
            {
                $sub_category = new \stdClass();
                $sub_category->sub_category_id = $bsca['sub_category_id'];

                $business_sub_categories [] = (array)$sub_category;
            }
            $business->businessSubCategories()->attach($business_sub_categories);
        }

        $business->businessOffers()->detach();
        if(sizeof($business_offers_array) > 0)
        {
            $business_offers = array();
            foreach($business_offers_array as $bo)
            {
                $offer = new \stdClass();
                $offer->offer_id = $bo['offer_id'];

                $business_offers [] = (array)$offer;
            }
            $business->businessOffers()->attach($business_offers);
        }

        $business->businessOfficeHours()->detach();
        if(sizeof($business_office_hours_array) > 0)
        {
            $business_office_hours = array();
            foreach($business_office_hours_array as $boh)
            {
                $hour = new \stdClass();

                $hour->office_hour_id = $boh['office_hour_id'];
                $hour->start_time = isset($boh['start_time']) ? $boh['start_time'] : null;
                $hour->end_time = isset($boh['end_time']) ? $boh['end_time'] : null;
                $hour->is_closed = $boh['is_closed'];

                $business_office_hours [] = (array)$hour;
            }
            $business->businessOfficeHours()->attach($business_office_hours);
        }

        $business_folder_path = $business->id.'_'.str_replace('-','_',str_replace(' ','_',$business->name)).'/';
        
        $folder_path =  'public/uploads/businessattachments/' . $business_folder_path ;

        if($business_logo_base64_code != null)
        {

            if($request->input('id') != null)
            {
                Storage::disk('local')->delete('public/'.$business->business_logo_url);
            }

            preg_match("/data:image\/(.*?);/", $business_logo_base64_code, $file_extension);
            @list($type, $file_data) = explode(';', $business_logo_base64_code);
            @list(, $file_data) = explode(',', $file_data);
            
    
            $fileName = 'file_' . time() . '_' . rand(pow(10, 3 - 1), pow(10, 3) - 1) . '.' . $file_extension[1];
    
            Storage::disk('local')->put($folder_path.'logo/'. $fileName, base64_decode($file_data));
    
            $business->business_logo_url ='uploads/businessattachments/' .$business_folder_path. 'logo/'.$fileName;
    
            $business->save();
        }

        if($business_cover_base64_code != null)
        {

            if($request->input('id') != null)
            {
                Storage::disk('local')->delete('public/'.$business->business_cover_url);
            }

            preg_match("/data:image\/(.*?);/", $business_cover_base64_code, $file_extension);
            @list($type, $file_data) = explode(';', $business_cover_base64_code);
            @list(, $file_data) = explode(',', $file_data);
            
    
            $fileName = 'file_' . time() . '_' . rand(pow(10, 3 - 1), pow(10, 3) - 1) . '.' . $file_extension[1];
    
            Storage::disk('local')->put($folder_path.'cover/'. $fileName, base64_decode($file_data));
    
            $business->business_cover_url ='uploads/businessattachments/' .$business_folder_path. 'cover/'.$fileName;
    
            $business->save();
        }

        $business_attachments = $request->input('business_attachments');

        if (sizeof($business_attachments) > 0) {
                foreach ($business_attachments as $d) {

                    if($d['is_deleted'] == 1)
                    {
                        Storage::disk('local')->delete('public/'.$d['encrypted_name']);

                        $attachment = BusinessAttachment::find($d['id']);
                        $attachment->delete();
                    }
                    else
                    {
                        if($d['is_new'] == 1)
                        {
                            preg_match("/data:image\/(.*?);/", $d['base64_code'], $file_extension) ||
                            preg_match("/data:text\/(.*?);/", $d['base64_code'], $file_extension) ||
                            preg_match("/data:application\/(.*?);/", $d['base64_code'], $file_extension) ||
                            preg_match("/data:video\/(.*?);/", $d['base64_code'], $file_extension);
                            @list($type, $file_data) = explode(';', $d['base64_code']);
                            @list(, $file_data) = explode(',', $file_data);



                            $fileName = 'file_' . time() . '_' . rand(pow(10, 3 - 1), pow(10, 3) - 1) . '.' . $file_extension[1];

                            $folder_path =  'public/uploads/businessattachments/' . $business_folder_path .'attachments/';



                            Storage::disk('local')->put($folder_path . $fileName, base64_decode($file_data));

                            $fileName = 'uploads/businessattachments/' .$business_folder_path. 'attachments/'.$fileName;


                            $attachment = new BusinessAttachment();
                            $attachment->original_name = $d['original_name'];
                            $attachment->encrypted_name = $fileName;
                            $attachment->ext = $d['ext'];
                            $attachment->mime_type = $d['mime_type'];
                            $attachment->size = $d['size'];
                            $attachment->attachment_type_id = $d['attachment_type_id'];
                            $attachment->attachment_category_id = $d['attachment_category_id'];
                            $attachment->business_id = $business->id;
                            $attachment->created_by = $id;

                            $attachment->save();
                        }

                     }

                                    }
                                }
        return response()->json(['sucess' => 'saved'],200);
            
    }

    public function getBusinesses($page_no,$id)
    {

        $pdo = DB::connection()->getPdo();

        $pdo->setAttribute(PDO::ATTR_EMULATE_PREPARES, true);


        $stmt = $pdo->prepare('CALL get_businesses(:puserid,:page_no)');

        $stmt->execute(array('puserid' => $id,'page_no' => $page_no));

        $business_count = $stmt->fetchAll(PDO::FETCH_CLASS, 'stdClass');
        $business_count = $business_count != null ? $business_count[0]->business_count : 0;

        $stmt->nextRowset();

        $businesses = $stmt->fetchAll(PDO::FETCH_CLASS, 'stdClass');


        return response()->json([
            'businesses' => $businesses,
            'business_count' => $business_count 
        ],200,[], JSON_NUMERIC_CHECK) ;
    }

    public function deleteBusiness($id)
    {
        $business = Business::find($id);

        $business_folder_path = $business->id.'_'.str_replace('-','_',str_replace(' ','_',$business->name)).'/';

        $business->businessAttachments()->delete();

        $business->businessCategories()->detach();

        $business->businessSubCategories()->detach();
        
        Storage::disk('local')->delete('public/uploads/businessattachments/'.$business_folder_path);

        $business->delete();
    }

    public function getBusiness($id,$user_id)
    {
        $business = Business::find($id);
        $business_attachments = $business->businessAttachments()->get();
        $business_categories = $business->businessCategories()->select('id as category_id','name')->get();
        $business_sub_categories = $business->businessSubCategories()->select('id as sub_category_id','name')->get();
        $business_office_hours = $business->businessOfficeHours()->get();
        $business_offers = $business->businessOffers()->select('id as offer_id','name')->get();

        $business_office_hours_array = array();
        foreach($business_office_hours as $boh)
        {
            $hour = new \stdClass();
            $hour->office_hour_id = $boh->pivot->office_hour_id;
            $hour->start_time = $boh->pivot->start_time;
            $hour->end_time = $boh->pivot->end_time;
            $hour->is_closed = $boh->pivot->is_closed;

            $business_office_hours_array [] = (array) $hour; 
        }


        $pdo = DB::connection()->getPdo();

        $pdo->setAttribute(PDO::ATTR_EMULATE_PREPARES, true);

        $user = User::find($user_id);

        if($user->role_id == 1)
        {
            $stmt = $pdo->prepare('CALL get_admin_business_categories()');
        }
        else
        {
            $stmt = $pdo->prepare('CALL get_business_categories(?)');
        }

        $stmt->execute(array($id));

        $categories = $stmt->fetchAll(PDO::FETCH_CLASS, 'stdClass');

        $stmt->nextRowset();

        $sub_categories = $stmt->fetchAll(PDO::FETCH_CLASS, 'stdClass');

        $stmt->nextRowset();

        $office_hours = $stmt->fetchAll(PDO::FETCH_CLASS, 'stdClass');

        $stmt->nextRowset();

        $offers = $stmt->fetchAll(PDO::FETCH_CLASS, 'stdClass');

        $office_hours_array = array();

        foreach($office_hours as $oh)
        {
            $hour = new \stdClass();
            $hour = $oh ;

            $business_hour = collect($business_office_hours_array)->where('office_hour_id',$hour->office_hour_id)->first();

            if($business_hour != null)
            {
                $hour->is_checked = true;
                $hour->start_time = $business_hour['start_time'];
                $hour->end_time = $business_hour['end_time'];
                $hour->is_closed = $business_hour['is_closed'];

            }
            else
            {
                $hour->is_checked = false;
            }

            $office_hours_array [] = (array) $hour;
        }

        return response()->json([
            'business' => $business, 
            'business_attachments' => $business_attachments,
            'business_categories' => $business_categories,
            'business_sub_categories' => $business_sub_categories,
            'business_office_hours' => $office_hours_array,
            'business_offers' =>  $business_offers,
            'categories' => $categories,
            'sub_categories' => $sub_categories,
            'offers' => $offers
        ],200,[], JSON_NUMERIC_CHECK);
    }

    public function getBusinessDetails($id,$user_id)
    {
        $current_day = Carbon::now()->formatLocalized('%A');

        $pdo = DB::connection()->getPdo();

        $pdo->setAttribute(PDO::ATTR_EMULATE_PREPARES, true);

        $stmt = $pdo->prepare('CALL get_business_details(?)');

        $stmt->execute(array($id));
        
        $business = $stmt->fetchAll(PDO::FETCH_CLASS, 'stdClass');
        $business = $business[0];
        $stmt->nextRowset();

        $business_attachments = $stmt->fetchAll(PDO::FETCH_CLASS, 'stdClass');

        $stmt->nextRowset();

        $business_office_hours = $stmt->fetchAll(PDO::FETCH_CLASS, 'stdClass');

        $stmt->nextRowset();

        $business_offers = $stmt->fetchAll(PDO::FETCH_CLASS, 'stdClass');

        $stmt->nextRowset();

        $business_reviews = $stmt->fetchAll(PDO::FETCH_CLASS, 'stdClass');

        $stmt->nextRowset();

        $related_businesses = $stmt->fetchAll(PDO::FETCH_CLASS, 'stdClass');

        $stmt->nextRowset();

        $related_business_office_hours = $stmt->fetchAll(PDO::FETCH_CLASS, 'stdClass');

        $stmt->nextRowset();

        $related_business_attachments = $stmt->fetchAll(PDO::FETCH_CLASS, 'stdClass');

        $business_obj = new stdClass();

        $business_obj = $business;

        $business_obj->business_attachments = $business_attachments;
        $business_obj->business_office_hours = $business_office_hours;
        $business_obj->business_offers = $business_offers;
        $business_obj->business_reviews = $business_reviews;
        $business_obj->selected_img = sizeof($business_obj->business_attachments) > 0 ? $business_obj->business_attachments[0] : null;

        $current_office_hour = collect($business_obj->business_office_hours)->where('name',$current_day)->where('is_closed',0)->first();

        $business_obj->closed_in = $current_office_hour == null || ($current_office_hour != null && !Carbon::now()->betweenExcluded(Carbon::parse($current_office_hour->start_time),Carbon::parse($current_office_hour->end_time))) ? 'Closed' : 'Closes '  .date("g:i a", strtotime($current_office_hour->end_time));

        $next_office_hour = $business_obj->closed_in == 'Closed' ?  ($current_office_hour != null && Carbon::now()->lt(Carbon::parse($current_office_hour->start_time)) ? $current_office_hour :  collect($business_obj->business_office_hours)->where('office_hour_id', '>',Carbon::now()->dayOfWeek)->where('is_closed',0)->first()) : null;

        $business_obj->opens_in =  $next_office_hour != null ? 'Opens '.date("g:i a", strtotime($next_office_hour->start_time)).' '.$next_office_hour->name : null; 

        $related_businesses_array = array();
        foreach($related_businesses as $b)
        {
            $bus = new stdClass();
            $bus = $b;

            $bus->selected_img = collect($related_business_attachments )->where('business_id',$bus->id)->first();
         
            $bus->business_office_hours = array_values(collect($related_business_office_hours)->where('business_id',$bus->id)->toArray());

            $current_office_hour = collect($bus->business_office_hours)->where('name',$current_day)->where('is_closed',0)->first();

            // return response()->json(['test' => Carbon::now()],500);

            $bus->closed_in = $current_office_hour == null || ($current_office_hour != null && !Carbon::now()->betweenExcluded(Carbon::parse($current_office_hour->start_time),Carbon::parse($current_office_hour->end_time))) ? 'Closed' : 'Closes '  .date("g:i a", strtotime($current_office_hour->end_time));

            $next_office_hour = $bus->closed_in == 'Closed' ?  ($current_office_hour != null && Carbon::now()->lt(Carbon::parse($current_office_hour->start_time)) ? $current_office_hour :  collect($bus->business_office_hours)->where('office_hour_id', '>',Carbon::now()->dayOfWeek)->where('is_closed',0)->first()) : null;

            $bus->opens_in =  $next_office_hour != null ? 'Opens '.date("g:i a", strtotime($next_office_hour->start_time)).' '.$next_office_hour->name : null; 
        
            $related_businesses_array [] = (array) $bus;
        }

        $business_obj->related_businesses = $related_businesses_array;

        return response()->json([
            'business' => $business_obj,
    ],200,[], JSON_NUMERIC_CHECK);
    

    }

    public function saveBusinessCategory(Request $request,$id)
    {
        $category = new BusinessCategory();
        $category->name = $request->input('name');
        $category->created_by = $id;

        $category->save();

        return response()->json(['id' => $category->id],200,[], JSON_NUMERIC_CHECK);
    }

    public function getBusinessMeta($id)
    {
        $user = User::find($id);

        $pdo = DB::connection()->getPdo();

        $pdo->setAttribute(PDO::ATTR_EMULATE_PREPARES, true);

        if($user->role_id == 1)
        {
            $stmt = $pdo->prepare('CALL get_admin_business_categories()');
        }
        else
        {
            $stmt = $pdo->prepare('CALL get_business_categories(?)');
        }

        $stmt->execute(array($id));

        $categories = $stmt->fetchAll(PDO::FETCH_CLASS, 'stdClass');

        $stmt->nextRowset();

        $sub_categories = $stmt->fetchAll(PDO::FETCH_CLASS, 'stdClass');

        $stmt->nextRowset();

        $office_hours = $stmt->fetchAll(PDO::FETCH_CLASS, 'stdClass');

        $stmt->nextRowset();

        $offers = $stmt->fetchAll(PDO::FETCH_CLASS, 'stdClass');

        return response()->json([
            'categories' => $categories,
            'sub_categories' => $sub_categories,
            'office_hours' => $office_hours,
            'offers' => $offers
        ],200,[], JSON_NUMERIC_CHECK);
    }

    public function getBusinessListings(Request $request)
    {
        $search_query = $request->input('search_query');

        $page_no = $request->input('page_no');

        $is_open = $request->input('is_open');

        $current_day = Carbon::now()->formatLocalized('%A');

        $pdo = DB::connection()->getPdo();

        $pdo->setAttribute(PDO::ATTR_EMULATE_PREPARES, true);

        $stmt = $pdo->prepare('CALL get_business_listings(?,?)');

        $stmt->execute(array($search_query,$page_no));

        $business_attachments = $stmt->fetchAll(PDO::FETCH_CLASS, 'stdClass');

        $stmt->nextRowset();

        $business_office_hours = $stmt->fetchAll(PDO::FETCH_CLASS, 'stdClass');

        // return response()->json(['sample' => $business_office_hours],500);

        $stmt->nextRowset();

        $categories = $stmt->fetchAll(PDO::FETCH_CLASS, 'stdClass');

        $stmt->nextRowset();

        $sub_categories = $stmt->fetchAll(PDO::FETCH_CLASS, 'stdClass');

        $stmt->nextRowset();

        $business_count = $stmt->fetchAll(PDO::FETCH_CLASS, 'stdClass');
        $business_count = $business_count != null ? $business_count[0]->business_count : 0;

        $stmt->nextRowset();

        $businesses = $stmt->fetchAll(PDO::FETCH_CLASS, 'stdClass');

        $categories_array = array();
        foreach($categories as $ct)
        {
            $cat = new stdClass();
            $cat = $ct;

            $cat->sub_categories = array_values(collect($sub_categories)->where('category_id',$ct->category_id)->toArray());

            $categories_array [] = (array) $cat;
        }

        $businesses_array = array();
        foreach($businesses as $b)
        {
            $bus = new stdClass();
            $bus = $b;
            $bus->is_read_more = false;
            $bus->about_count = strlen($bus->about);

            $bus->business_attachments = array_values(collect($business_attachments)->where('business_id',$bus->id)->toArray());

            $bus->business_office_hours = array_values(collect($business_office_hours)->where('business_id',$bus->id)->toArray());

            $bus->selected_img = sizeof($bus->business_attachments) > 0 ? $bus->business_attachments[0] : null;

            $current_office_hour = collect($bus->business_office_hours)->where('name',$current_day)->where('is_closed',0)->first();

            // return response()->json(['test' => Carbon::now()],500);

            $bus->closed_in = $current_office_hour == null || ($current_office_hour != null && !Carbon::now()->betweenExcluded(Carbon::parse($current_office_hour->start_time),Carbon::parse($current_office_hour->end_time))) ? 'Closed' : 'Closes '  .date("g:i a", strtotime($current_office_hour->end_time));

            $next_office_hour = $bus->closed_in == 'Closed' ?  ($current_office_hour != null && Carbon::now()->lt(Carbon::parse($current_office_hour->start_time)) ? $current_office_hour :  collect($bus->business_office_hours)->where('office_hour_id', '>',Carbon::now()->dayOfWeek)->where('is_closed',0)->first()) : null;

            $bus->opens_in =  $next_office_hour != null ? 'Opens '.date("g:i a", strtotime($next_office_hour->start_time)).' '.$next_office_hour->name : null; 

            if ($is_open == false || ($is_open == true && $bus->closed_in != 'Closed'))
            {
                $businesses_array [] = (array) $bus;
            }
        }



        $business_count = sizeof($businesses_array) == 0 ? 0 :  $business_count;

        return response()->json([
            'businesses' => $businesses_array,
            'categories' => $categories_array,
            'business_count' => $business_count
    ],200,[], JSON_NUMERIC_CHECK);
    }

    public function contactBusiness(Request $request)
    {  
        $business = Business::find($request->input('business_id'));

        $first_name = $request->input('first_name');
        $last_name = $request->input('last_name');
        $email = $request->input('email');
        $phone_number = $request->input('phone_number');
        $message = $request->input('message');

        $message = $request->input('message');
        $message = $request->input('message');

        $is_contact_by_mail = $request->input('is_contact_by_mail');
        $is_contact_by_phone = $request->input('is_contact_by_phone');

        $via_contact = '';

        if($is_contact_by_mail == true && $is_contact_by_phone == true)
        {
            $contact = 'email and phonenumber';
            $via_contact = 'Contact By '.$contact.' is available';
        }
        else if($is_contact_by_mail == true && $is_contact_by_phone != true)
        {
            $contact = 'email';
            $via_contact = 'Contact By '.$contact.' is available';
        }
        else if($is_contact_by_mail != true && $is_contact_by_phone == true)
        {
            $contact = 'phonenumber';
            $via_contact = 'Contact By '.$contact.' is available';
        }


        
        FacadesNotification::route('mail', $business->contact_email)->notify(new BusinessContact($first_name,$last_name,$email,$phone_number,$message,$via_contact));

        return response()->json(['sucess' => 'saved'],200);

    }


    public function saveBusinessReview(Request $request)
    {
        $review = new BusinessReview();
        
        $review->user_id = $request->input('user_id');
        $review->ip_address = $request->ip();
        $review->feedback = $request->input('feedback');
        $review->rating = $request->input('rating');
        $review->business_id = $request->input('business_id');

        $review->save();

        return response()->json(['sucess' => 'saved'],200);

    }

}


