<?php

namespace App\Modules\Company\Whiteboard;

use App\Http\Resources\Company\AvailableWorkers as AvailableWorkersResource;
use App\Models\Availabilities;
use App\Traits\SortingTraits;
use App\Traits\UserTraits;
use App\Traits\ValidatorTraits;
use App\Models\AssignedWorkers;

class AvailableWorkers
{
    use SortingTraits, UserTraits, ValidatorTraits;

    public function getData($payload)
    {
        $company_id = $this->getCurrentUser()->company_id;
        $start_date = date('Y-m-d', strtotime($payload->start_date));
        $end_date = date('Y-m-d', strtotime($payload->end_date));

        // sorting
        $sortField = $this->sortField($payload, 'first_name'); // first_name = default column to search
        $sortOrder = $this->sortOrder($payload, 'asc');

        // searching
        $nameSearch = $payload->employee_name;
        $employeeTypeSearch = $payload->employee_type;

        // validate query params
        $rules = array(
            'start_date' => 'required',
            'end_date' => 'required',
        );
        $validate = $this->validateRequest($payload, $rules);
        if ($validate) {
            return $validate;
        }

        $assigned = AssignedWorkers::whereNull('deleted_at')->pluck('worker_id');

        return AvailableWorkersResource::collection(
            Availabilities::select(
                'availabilities.id',
                'availabilities.worker_id',
                'availabilities.worker_type',
                'availabilities.rate',
                'workers.profile_picture',
                'workers.first_name',
                'workers.last_name',
                'company_experiences.id as experience_id',
                'company_experiences.name as experience_name')
                ->join('workers', 'workers.id', '=', 'availabilities.worker_id')
                ->join('company_users', 'company_users.worker_id', '=', 'workers.id')
                ->join('worker_experiences', 'worker_experiences.worker_id', '=', 'availabilities.worker_id')
                ->join('company_experiences', 'company_experiences.id', '=', 'worker_experiences.experience_id')
                ->where('company_users.role_id', 5) // 5 = Worker
                ->whereNotNull('workers.email_verified_at')
                ->where('availabilities.max_availability_date', '>=', date("Y-m-d"))
                ->whereNotIn('availabilities.worker_id', $assigned)
                ->where(function ($query) use ($start_date, $end_date) {
                    $query->where('availabilities.min_availability_date', $start_date)
                        ->orWhere('availabilities.max_availability_date', $end_date)
                        ->orWhereBetween('availabilities.min_availability_date', [$start_date, $end_date])
                        ->orWhereBetween('availabilities.max_availability_date', [$start_date, $end_date])
                        ->orWhereRaw('? BETWEEN availabilities.min_availability_date and availabilities.max_availability_date', [$start_date])
                        ->orWhereRaw('? BETWEEN availabilities.min_availability_date and availabilities.max_availability_date', [$end_date]);
                })
                ->when(!empty($nameSearch), function ($query) use ($nameSearch) {
                    return $query->where(function ($query) use ($nameSearch) {
                        $query->where('workers.first_name', 'LIKE', $nameSearch . '%')
                            ->orWhere('workers.last_name', 'LIKE', $nameSearch . '%');
                    });
                })
                ->when(!empty($employeeTypeSearch), function ($query) use ($employeeTypeSearch) {
                    return $query->where(function ($query) use ($employeeTypeSearch) {
                        return $query->whereIn('availabilities.worker_type', $employeeTypeSearch);
                    });
                })
                ->where('availabilities.company_id', $company_id)
                ->groupBy('availabilities.worker_id')
                ->orderBy($sortField, $sortOrder)
                ->paginate(20)
        );
    }
}
