<?php

namespace Modules\Company\Controllers;

use App\Controllers\BaseController;
use Modules\Company\Models\CompanyModel;
use Modules\User\Models\UserModel;
use Modules\User\Models\UserDetailModel;
use Modules\Role\Models\RoleModel;
use Modules\Trip\Models\TripModel;
use Modules\Location\Models\LocationModel;
use App\Libraries\Rolepermission;

class Company extends BaseController
{
    protected $Viewpath;
    protected $db;
    protected $userModel;
    protected $userDetailModel;
    protected $companyModel;
    protected $roleModel;
    protected $locationModel;
    protected $tripModel;



    public function __construct()
    {
        $this->Viewpath = "Modules\Company\Views";
        $this->companyModel = new CompanyModel();
        $this->userModel = new UserModel();
        $this->userDetailModel = new UserDetailModel();
        $this->roleModel = new RoleModel();
        $this->tripModel = new TripModel();
        $this->locationModel = new LocationModel();
        $this->db = \Config\Database::connect();
        $this->sourceOptions = [0=> 'None', 1 => 'With Website',2 => 'With App',3 => 'Both'];
    }

    public function index(bool $showTrashOnly = false)
    {
        // build layout data
        $data['pageheading'] = lang("Localize.company_list");
        $data['module'] = lang("Localize.company");
        $data['title']  = lang("Localize.company_list");
        $data['sourceOptions']  = $this->sourceOptions;

        // build perission dat
        $rolepermissionLibrary = new Rolepermission();
        $data['add_company'] = $rolepermissionLibrary->create("add_company");
        $data['edit_company'] = $rolepermissionLibrary->edit("company_list");
        $data['delete_company'] = $rolepermissionLibrary->delete("company_list");

        $userRole = $this->session->get('role_id');
        // $data['companydetail'] = $this->companyModel->findAll();

        $data['companydetail'] = $this->companyModel->select('companies.*, users.login_email, users.login_mobile')
            ->join('users', 'users.id = companies.user_id')
            ->findAll();

        $data['role_id'] = $userRole;

        return view($this->Viewpath . '\company\index', $data);
    }

    public function new()
    {
        // build layout data
        $data['pageheading'] = lang("Localize.add_company");
        $data['module'] = lang("Localize.company");
        $data['title']  = lang("Localize.add_company");
        $data['sourceOptions']  = $this->sourceOptions;
        return view($this->Viewpath . '\company/new', $data);
    }

    public function create()
    {
        $path = 'image/company';
        $slug = bin2hex(random_bytes(5));
        $role_id = 7;
        $status = 1;
        // dd($this->request->getVar());
        // build agent login credintial
        $company_email = $this->request->getVar('email');
        $company_name = $this->request->getVar('name');
        $owner_name  = $this->request->getVar('ownername');
        $address     = $this->request->getVar('address');
        $note        = $this->request->getVar('note');
        $login_mobile = $this->request->getVar('login_mobile');
        $company_status = $this->request->getVar('status');
        $SourceOption = $this->request->getVar('sourceOption');
        

        // build agent password
        $password = $this->request->getVar('password');
        $confirmPassword = $this->request->getVar('confirm');
        $password_hash = password_hash($password, PASSWORD_DEFAULT);

        $userData = array(
            "login_email" => $company_email,
            "login_mobile" => $login_mobile,
            "password" => $password,
            "confirm" => $confirmPassword,
            "slug" => $slug,
            "role_id" => $role_id,
            "status" => $status,
        );

        if ($this->validation->run($userData, 'user')) {
            $this->db->transStart();

            $userId = $this->userModel->insert(array_merge($userData, ['password' => $password_hash]));

            $companyLogoId =  '';
            $company_logo = $this->request->getFile('profile_picture');

            if ($company_logo->isValid() && !$company_logo->hasMoved()) {
                $companyLogoId = $this->imgaeCheck($company_logo, $path);
            }
        
            $companyData = array(
                "user_id"    => $userId,
                "name"       => $company_name,
                "owner_name" => $owner_name,
                "address"    => $address,
                "logo"       => $companyLogoId,
                "source_option" => $SourceOption,
                "note"       => $note,
                "status"     => $company_status
            );

            if ($this->validation->run($companyData, 'company')) {
                $companyID = $this->companyModel->insert($companyData);

                $userDetailsData = array(
                    "user_id" => $userId,
                    "company_id" => $companyID,
                    "first_name" => $this->request->getVar('first_name')?? "",
                    "last_name" => $this->request->getVar('last_name')??"",
                    "country_id" => $this->request->getVar('country_id')??"",
                    "id_type" => $this->request->getVar('id_type') ?: null,
                    "id_number" => $this->request->getVar('id_number') ?: null,
                    "address" => $this->request->getVar('address'),
                    "city" => $this->request->getVar('city')??"",
                    "zip_code" => $this->request->getVar('zip_code')??"",
                );
                $this->userDetailModel->save($userDetailsData);

                $this->db->transComplete();
                return redirect()->route('index-company')->with("success", "Data Save");

            }
        }
        // invalid data posted
        // rollback query operation
        return redirect()->back()->withInput()->with('fail', $this->validation->listErrors());
    }

    public function imgaeCheck($image, $path)
    {
        $newName = $image->getRandomName();
        $path = $path;
        $image->move($path, $newName);
        return $path . '/' . $newName;
    }

    public function edit($id)
    {
        // build layout data
        $data['module'] = lang("Localize.company");
        $data['title']  = lang("Localize.company_list");
        $data['pageheading'] = lang("Localize.company") . ' ' . lang("Localize.edit");
        $data['sourceOptions']  = $this->sourceOptions;

        $data['companydetail'] =  $this->companyModel->select('users.*,companies.*,users.id as userid,companies.id as companyid')->join('users', 'users.id = companies.user_id')->where('users.role_id', 7)->where('companies.id', $id)->first();

        return view($this->Viewpath . '\company/edit', $data);
    }

    public function update($userId, $companyId)
    {
        $path = 'image/company';
        $imagenid = '';
        $company_logo = $this->request->getFile('profile_picture');
        $userId = $this->request->getVar('userId');
        $companyId = $this->request->getVar('companyId');

        // starting database transaction
        $this->db->transStart();

        if ($company_logo->isValid() && !$company_logo->hasMoved()) {
            // profile picture exists
            $imagedocu = $this->imgaeCheck($company_logo, $path);
        } else {
            // profile picture not exists
            // switch back to old image
            $imagedocu = $this->request->getVar('profileoldpic');
        }

        $userData = array(
            "id" => $this->request->getVar('userId'),
            "login_email" => $this->request->getVar('email'),
            "login_mobile" => $this->request->getVar('login_mobile'),
        );

        if ($this->validation->run($userData, 'user')) {

            $this->userModel->save($userData);

            $companyData = array(
                "id" => $this->request->getVar('companyId'),
                "user_id" => $userId,
                "name" => $this->request->getVar('name'),
                "source_option" => $this->request->getVar('sourceOption'),
                "owner_name" => $this->request->getVar('ownername'),
                "address" => $this->request->getVar('address'),
                "logo"       => $imagedocu,
                "note" => $this->request->getVar('note'),
                "status" => $this->request->getVar('status')
            );

            if($this->request->getVar('status') == 0){
                $usercompanyId = $this->request->getVar('companyId');
                $upData = array("id" => $usercompanyId,"status" => 0);
                $this->companyModel->save($upData);

                $trips = $this->tripModel->where('company_id', $usercompanyId)->findAll();

                if (!empty($trips)) {
                    $this->tripModel->where('company_id', $usercompanyId)
                                ->set(['status' => 0])
                                ->update();
                }

                $userDetails = $this->userDetailModel->where('company_id', $usercompanyId)->first();

                if (!empty($userDetails)) {
                    $users = $this->userModel->where('id', $userDetails->user_id)->first();
                    if(!empty($users)){
                        $this->userModel->where('id', $userDetails->user_id)
                                ->set(['deleted_at' => date('Y-m-d H:i:s')])
                                ->update();    
                    }
                    

                    $this->userDetailModel->where('company_id', $usercompanyId)
                                ->set(['deleted_at' => date('Y-m-d H:i:s')])
                                ->update();
                }
            } else if($this->request->getVar('status') == 1) {
                
                $usercompanyId = $this->request->getVar('companyId');
                $upData = array("id" => $usercompanyId,"status" => 1);
                $this->companyModel->save($upData);

                $trips = $this->tripModel->where('company_id', $usercompanyId)->findAll();

                if (!empty($trips)) {
                    $this->tripModel->where('company_id', $usercompanyId)
                                ->set(['status' => 1])
                                ->update();
                }

                $userDetails = $this->userDetailModel
                    ->withDeleted()
                    ->where('company_id', $usercompanyId)
                    ->first();

                if ($userDetails) {
                    // Restore the record by setting deleted_at to NULL
                    $this->userDetailModel->update($userDetails->id, ['deleted_at' => null]);
                    $this->userModel->update($userDetails->user_id, ['deleted_at' => null]);
                }
            }

            if ($this->validation->run($companyData, 'company')) {
                // insert data to user model
                $this->companyModel->save($companyData);
                $userDetailsData = array(
                    "user_id" => $userId,
                    "company_id" => $companyId,
                    "first_name" => $this->request->getVar('first_name')?? "",
                    "last_name" => $this->request->getVar('last_name')??"",
                    "country_id" => $this->request->getVar('country_id')??"",
                    "id_type" => $this->request->getVar('id_type') ?: null,
                    "id_number" => $this->request->getVar('id_number') ?: null,
                    "address" => $this->request->getVar('address'),
                    "city" => $this->request->getVar('city')??"",
                    "zip_code" => $this->request->getVar('zip_code')??"",
                );
                if($this->request->getVar('status') == 1){
                    
                    $CompanyuserDetails = $this->userDetailModel->where('company_id', $usercompanyId)->first();
                    if($CompanyuserDetails){
                        $userDetailsData['id'] = $CompanyuserDetails->id;
                        $this->userDetailModel->save($userDetailsData);
                    } else {
                        $this->userDetailModel->save($userDetailsData);
                    }
                }
                
                $this->db->transComplete();
                return redirect()->route('index-company')->with("success", "Data Save");
            }
        }

        return redirect()->back()->with('fail', $this->validation->listErrors());
    }

    public function delete(int $companyId)
    {
        $companyInfo = $this->companyModel->find($companyId);
        $companyUserId = $companyInfo->user_id;
        $companyId = $companyInfo->id;
        $companyName = $companyInfo->name;
        try {
            $this->db->transStart();
            $this->companyModel->delete($companyId);
            $this->userModel->delete($companyUserId);
            $this->db->transComplete();
        } catch (\Throwable $e) {
            return redirect()->back()->with('fail', $e->getMessage());
        }

        return redirect()->back()->with('fail', "Company: {$companyName} deleted");
    }

    public function restore(int $companyId)
    {
        $companyInfo = $this->companyModel->withDeleted()->find($companyId);
        $companyUserId = $companyInfo->user_id;
        $companyId = $companyInfo->id;
        $companyName = $companyInfo->name;

        try {
            $this->db->transStart();
            $this->companyModel->set('deleted_at', null)->update($$companyId);
            $this->userModel->set('deleted_at', null)->update($companyUserId);
            $this->db->transComplete();
        } catch (\Throwable $e) {
            return redirect()->back()->with('fail', $e->getMessage());
        }

        return redirect()->route('trash-index-company')->with('success', "Company: {$companyName} restored");
    }

    public function status($usercompanyId)
    {
        $userStatus = $this->companyModel->find($usercompanyId);

        if ($userStatus->status == 1) {
            $upData = array(
                "id" => $usercompanyId,
                "status" => 0
            );
            $this->companyModel->save($upData);

            $trips = $this->tripModel->where('company_id', $usercompanyId)->findAll();

            if (!empty($trips)) {
                $this->tripModel->where('company_id', $usercompanyId)
                            ->set(['status' => 0])
                            ->update();
            }

            $userDetails = $this->userDetailModel->where('company_id', $usercompanyId)->first();

            if (!empty($userDetails)) {
                $users = $this->userModel->where('id', $userDetails->user_id)->first();
                if(!empty($users)){
                    $this->userModel->where('id', $userDetails->user_id)
                            ->set(['deleted_at' => date('Y-m-d H:i:s')])
                            ->update();    
                }
                

                $this->userDetailModel->where('company_id', $usercompanyId)
                            ->set(['deleted_at' => date('Y-m-d H:i:s')])
                            ->update();
            }

        }
        if ($userStatus->status == 0) {
            $upData = array(
                "id" => $usercompanyId,
                "status" => 1
            );
            $this->companyModel->save($upData);
            
            // $trips = $this->tripModel->where('company_id', $companyId)->findAll();

            // if (!empty($trips)) {
            //     $this->tripModel->where('company_id', $companyId)
            //                 ->set(['status' => 1])
            //                 ->update();
            // }
        }
        return redirect()->route('index-company')->with("success", "Data Update");
    }
    public function serverList()
    {
        $request = service('request');

        // Role ID from session
        $role_id = session()->get('role_id');

        // Source options from controller
        $sourceOptions = $this->sourceOptions;

        // Check permissions
        $rolepermissionLibrary = new Rolepermission();
        $edit_company = $rolepermissionLibrary->edit("company_list");
        $delete_company = $rolepermissionLibrary->delete("company_list");

        // DataTables request values
        $draw   = $request->getPost('draw');
        $start  = $request->getPost('start');
        $length = $request->getPost('length');
        $searchValue = $request->getPost('search')['value'] ?? '';

        // Column map with table prefixes for joined tables
        $columns = [
            0 => 'companies.id',
            1 => 'companies.name',
            2 => 'users.login_email',
            3 => 'users.login_mobile',
            4 => 'companies.status',
            5 => 'companies.source_option'
        ];

        if ($role_id == 1) {
            // Admin sees action column → exclude from DB mapping
            $columns[6] = null;
        }

        // Order column & direction
        $order = $request->getPost('order');
        $orderColumnIndex = !empty($order) && isset($order[0]['column']) ? $order[0]['column'] : 0;
        $orderDirection   = !empty($order) && isset($order[0]['dir']) ? $order[0]['dir'] : 'asc';

        // ---- TOTAL RECORDS ----
        // Use db->table() to get a fresh builder instance and handle soft deletes
        $totalBuilder = $this->db->table('companies');
        $totalBuilder->select('companies.id')
            ->join('users', 'users.id = companies.user_id', 'left')
            ->where('companies.deleted_at IS NULL');
        $totalRecords = $totalBuilder->countAllResults(false);

        // Create fresh builder for filtered query (handle soft deletes)
        $builder = $this->db->table('companies');
        $builder->select('companies.*, users.login_email, users.login_mobile')
            ->join('users', 'users.id = companies.user_id', 'left')
            ->where('companies.deleted_at IS NULL');

        // Global search
        if (!empty($searchValue)) {
            $builder->groupStart()
                ->like('companies.name', $searchValue)
                ->orLike('users.login_email', $searchValue)
                ->orLike('users.login_mobile', $searchValue)
                ->groupEnd();
        }

        // Column-wise filters (individual column search)
        if (!empty($request->getPost('columns'))) {
            foreach ($request->getPost('columns') as $idx => $col) {
                $searchCol = $col['search']['value'] ?? '';
                if ($searchCol !== '' && isset($columns[$idx]) && $columns[$idx] !== null) {
                    $builder->like($columns[$idx], $searchCol);
                }
            }
        }

        // ---- TOTAL FILTERED ----
        $totalRecordwithFilter = $builder->countAllResults(false);

        // ---- ORDERING ----
        if (isset($columns[$orderColumnIndex]) && $columns[$orderColumnIndex] !== null) {
            $builder->orderBy($columns[$orderColumnIndex], $orderDirection);
        } else {
            $builder->orderBy('companies.id', 'desc');
        }

        // ---- PAGINATION ----
        if ($length > 0) {
            $builder->limit($length, $start);
        }

        // ---- FETCH RECORDS ----
        $records = $builder->get()->getResult();

        // ---- FORMAT JSON ----
        $data = [];
        $i = $start + 1;

        foreach ($records as $row) {
            $data[] = [
                "index" => $i++,
                "name" => '<a href="' . base_url(route_to('transaction-company', $row->id)) . '">' . esc($row->name) . '</a>',
                "login_email" => esc($row->login_email ?? ''),
                "login_mobile" => esc($row->login_mobile ?? ''),
                "status" => isset($row->status) && $row->status
                    ? '<span class="badge bg-success">Publish</span>'
                    : '<span class="badge bg-secondary">Unpublish</span>',
                "source_option" => isset($row->source_option) && isset($sourceOptions[$row->source_option]) 
                    ? $sourceOptions[$row->source_option] 
                    : "-",
                "action" => ($role_id == 1)
                    ? $this->generateActionButtons($row, $edit_company, $delete_company)
                    : ""
            ];
        }

        return $this->response->setJSON([
            "draw" => intval($draw),
            "recordsTotal" => $totalRecords,
            "recordsFiltered" => $totalRecordwithFilter,
            "data" => $data
        ]);
    }

    private function generateActionButtons($row, $edit_company, $delete_company)
    {
        $security = \Config\Services::security();
        $csrfToken = $security->getTokenName();
        $csrfHash = $security->getHash();
        
        $actionHtml = '';
        
        if ($edit_company) {
            $actionHtml .= '<a href="' . base_url(route_to('edit-company', $row->id)) . '" class="btn btn-sm btn-info text-white" title="' . lang("Localize.edit") . '"><i class="fas fa-edit"></i></a> ';
        }
        
        if ($delete_company) {
            $actionHtml .= '<form action="' . base_url(route_to('delete-company', $row->id)) . '" method="post" class="d-inline-block deletionForm">';
            $actionHtml .= '<input type="hidden" name="' . esc($csrfToken, 'attr') . '" value="' . esc($csrfHash, 'attr') . '">';
            $actionHtml .= '<input type="hidden" name="_method" value="DELETE">';
            $actionHtml .= '<button type="button" data-modal-confirm="true" class="btn btn-sm btn-danger" title="' . lang("Localize.delete") . '"><i class="far fa-trash-alt"></i></button>';
            $actionHtml .= '</form> ';
        }
        
        // Status toggle button
        $status = isset($row->status) && $row->status ? 0 : 1;
        $statusIcon = isset($row->status) && $row->status ? 'fa-user-slash' : 'fa-user-check';
        $statusTitle = isset($row->status) && $row->status ? lang("Localize.disable") : lang("Localize.active");
        
        $actionHtml .= '<form action="' . base_url(route_to('status-company', $row->id)) . '" method="post" class="d-inline-block">';
        $actionHtml .= '<input type="hidden" name="' . esc($csrfToken, 'attr') . '" value="' . esc($csrfHash, 'attr') . '">';
        $actionHtml .= '<input type="hidden" name="_method" value="PUT">';
        $actionHtml .= '<button type="submit" class="btn btn-sm btn-secondary text-white" title="' . esc($statusTitle, 'attr') . '"><i class="fas ' . esc($statusIcon, 'attr') . '"></i></button>';
        $actionHtml .= '</form>';
        
        return $actionHtml;
    }



}
