<?php

namespace App\Http\Controllers\Admin;

use App\Http\Controllers\Controller;
use App\Models\Form;
use App\Http\Requests\StoreFormRequest;
use App\Http\Requests\UpdateFormRequest;
use App\Mail\ProjectFormEmail;
use App\Models\Branch;
use App\Models\FormFile;
use App\Models\FormInput;
use App\Models\Project;
use App\Models\ProjectForm;
use App\Models\ProjectFormInput;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\DB;
use Illuminate\Support\Str;
use Illuminate\Support\Facades\Session;
use Carbon\Carbon;
use Maatwebsite\Excel\Facades\Excel;
use App\Traits\FirebaseNotification;
use Illuminate\Support\Facades\Mail;

class FormController extends Controller
{
    use FirebaseNotification;
    /**
     * Display a listing of the resource.
     *
     * @return \Illuminate\Http\Response
     */
    public function index(Request $request)
    {
        $sort_search = null;
        $forms = Form::orderBy('created_at', 'desc');
        if ($request->has('search')) {
            $sort_search = $request->search;
            $forms = $forms->where('name', 'like', '%' . $sort_search . '%');
        }
        $forms = $forms->paginate(15);
        return view('admin.form.index', compact('forms'));
    }

    /**
     * Show the form for creating a new resource.
     *
     * @return \Illuminate\Http\Response
     */
    public function create(Request $request)
    {
        if (!$request->session()->has('temp_serial')) {
            $temp_serial = Str::random(10);
            $request->session()->put('temp_serial', $temp_serial);
        }
        return view('admin.form.create');
    }
    public function addField(Request $request)
    {
        $inputCounter = $request->inputCounter;
        return view('admin.form.partials.field', compact('inputCounter'));
    }

    public function uploadFieldsFile(Request $request)
    {
        if ($request->has('getCounterUpdate')) {
            $file = $request->file('file');
            $data = Excel::toArray([], $file)[0];
            $inputCounter = $request->inputCounter;
            return $inputCounter + sizeof($data);
        } else {
            $file = $request->file('file');
            $data = Excel::toArray([], $file)[0];
            $inputCounter = $request->inputCounter;
            return view('admin.form.partials.fields', compact('inputCounter', 'data'));
        }
    }
    public function getPeriodicTypeSelect(Request $request)
    {
        if ($request->selectedValue == 'week') {
            return view('admin.form.partials.week_select');
        } elseif ($request->selectedValue == 'month') {
            return view('admin.form.partials.month_select');
        } elseif ($request->selectedValue == 'quarter') {
            return view('admin.form.partials.quarter_select');
        }
    }

    private function sendProjectsForm($form, $projects_ids)
    {
        foreach ($projects_ids as $value) {
            $now = Carbon::now();
            $date = $now->addDays(5);
            $projectForm = new ProjectForm;
            $projectForm->serial_number = Str::random(10);
            $projectForm->project_id = $value;
            $projectForm->form_id = $form->id;
            $projectForm->expiration_date = $date;
            // return $projectForm;
            $projectForm->save();
            foreach ($form->formInputs as $key => $value2) {
                $projectFormInput = new ProjectFormInput;
                $projectFormInput->project_form_id = $projectForm->id;
                $projectFormInput->form_input_id = $value2->id;
                $projectFormInput->input_type = $value2->input_type;
                $projectFormInput->calculated = $value2->calculated;
                $projectFormInput->save();
            }
        }
        $project = Project::find($value);
        //send notifications and mail
        $title = "Hello, " . $project->name;
        $type = "fill_form";
        $form_id = $projectForm->id;
        $message = "Hello, " . $project->name . "New Publishable Form " . $form->name . "Petrojet HSE form builder should be filled";
        if ($project->fcm_token) {
            $this->sendNotification($project->id, $title, $message, $type, $form_id);
        }
        Mail::to($project->email)->send(new ProjectFormEmail($project->name, $form->name, $form_id, $type));
        return true;
    }
    /**
     * Store a newly created resource in storage.
     *
     * @param  \App\Http\Requests\StoreFormRequest  $request
     * @return \Illuminate\Http\Response
     */
    public function store(StoreFormRequest $request)
    {
        if ($request->has('form_id')) {
            $form = Form::where('id', $request->form_id)->first();
            if (in_array(0, $request->branches)) {
                $lastProjects_ids = Project::pluck('id')->toArray();
                $form->branches = array_map(function ($id) {
                    return (string) $id;
                }, Branch::pluck('id')->toArray());
            } else {
                $projects_ids = [];
                foreach ($request->projects as $key => $projects) {
                    if (in_array(0, $projects)) {
                        $projects_ids_push = Project::where('branch_id', $key)->pluck('id')->toArray(); //get all branch projects as array
                        array_push($projects_ids, $projects_ids_push);
                    } else {
                        array_push($projects_ids, array_map('intval', $projects));
                    }
                }
                $form->branches = $request->branches;
                $lastProjects_ids = array_merge(...$projects_ids);
            }
            $form->projects()->sync($lastProjects_ids);
            $form->step = 'compleated';
            $form->save();
            if ($form->periodic_onetime == 'onetime') {
                $this->sendProjectsForm($form, $lastProjects_ids);
            } else {
                switch ($form->periodic_type) {
                    case 'week':
                        $now = Carbon::now();
                        $dayOfWeek = $now->dayOfWeek;
                        $N = $form->week_day; // Replace 7 with your desired day (0-6)
                        $dayDifference = ($N - $dayOfWeek + 7) % 7;
                        $date = $now->addDays($dayDifference);
                        if ($date->eq($now)) {
                            $this->sendProjectsForm($form, $lastProjects_ids);
                            $form->nex_send_date = date('Y-m-d', strtotime('+7 day'));
                        } else {
                            $form->nex_send_date = $date;
                        }
                        $form->save();
                        break;

                    case 'month':
                        $dayOfMonth = 30;
                        $now = Carbon::now();
                        $date = Carbon::now()->day($dayOfMonth);
                        if ($date->isSameDay($now)) {
                            $this->sendProjectsForm($form, $lastProjects_ids);
                            $form->nex_send_date = date('Y-m-d', strtotime('+31 day'));
                        } else {
                            $form->nex_send_date = $date;
                        }
                        $form->save();
                        break;

                    case 'quarter':
                        $dateString = $form->quarter_start_date; // Date in string format
                        $now = Carbon::now();
                        $date = Carbon::parse($dateString);
                        if ($date->isSameDay($now) || $date->diffInDays($now) <= 30) {
                            $this->sendProjectsForm($form, $lastProjects_ids);
                            $form->nex_send_date = date('Y-m-d', strtotime('+91 day'));
                        } else {
                            $form->nex_send_date = $date;
                        }
                        $form->save();
                        break;

                    default:
                        # code...
                        break;
                }
            }
            return redirect()->route('form.index');
        } else {

            $form = new Form;
            $form->step = 'registereed';
            $form->name = $request->name;
            $form->periodic_onetime = $request->periodic_onetime;
            $form->periodic_type = $request->periodic_type;
            $form->dead_line_by_num_of_dayes = $request->dead_line_by_num_of_dayes;
            $form->week_day = ($request->week_day) ? $request->week_day : null;
            $form->month_day = ($request->month_day) ? $request->month_day : null;
            $form->quarter_start_date = ($request->quarter_day) ? date('Y-m-d', strtotime($request->quarter_day)) : null;
            $form->save();
            foreach ($request->inputs as $key => $value) {
                $formInputs = new FormInput;
                $formInputs->form_id  = $form->id;
                $formInputs->label  = $value['label'];
                $formInputs->input_type  = $value['input_type'];
                $formInputs->calculated  = (isset($value['calculated'])) ? true : false;
                $formInputs->save();
            }
            if (Session::has('temp_serial')) {
                FormFile::where('temp_serial', Session::get('temp_serial'))
                    ->update(['form_id' => $form->id]);
                Session::forget('temp_serial');
            }
            return redirect()->route('form.continueStoreForm', $form->id);
        }
    }

    public function continueStoreForm($form_id)
    {
        $branches = Branch::pluck('name', 'id')->prepend(trans('messages.All Branches'), 0);
        $projects = Project::pluck('name', 'id')->prepend(trans('messages.All Projects'), 0);

        return view('admin.form.continu_store_form', compact('branches', 'projects', 'form_id'));
    }

    /**
     * Display the specified resource.
     *
     * @param  \App\Models\Form  $form
     * @return \Illuminate\Http\Response
     */
    public function show(Form $form)
    {
        return view('admin.form.show', compact('form'));
    }

    /**
     * Show the form for editing the specified resource.
     *
     * @param  \App\Models\Form  $form
     * @return \Illuminate\Http\Response
     */
    public function edit(Form $form)
    {
        //
    }

    /**
     * Update the specified resource in storage.
     *
     * @param  \App\Http\Requests\UpdateFormRequest  $request
     * @param  \App\Models\Form  $form
     * @return \Illuminate\Http\Response
     */
    public function update(UpdateFormRequest $request, Form $form)
    {
        //
    }

    /**
     * Remove the specified resource from storage.
     *
     * @param  \App\Models\Form  $form
     * @return \Illuminate\Http\Response
     */
    public function destroy(Form $form)
    {
        $formFiles = FormFile::where('form_id', $form->id)->get();
        foreach ($formFiles as $key => $formFile) {
            if ($formFile->file_path && file_exists(public_path($formFile->file_path))) {
                unlink(public_path($formFile->file_path));
            }
        }
        $form->delete();
        session()->flash('notif', trans('messages.Form deleted successfully'));
        return redirect()->route('form.index');
    }
}
