941 lines
31 KiB
PHP
941 lines
31 KiB
PHP
<?php
|
|
|
|
namespace App\Controllers;
|
|
|
|
use CodeIgniter\RESTful\ResourceController;
|
|
use App\Models\UserModel;
|
|
use App\Models\MailTemplateModel;
|
|
use App\Models\UserFrequentFlierInformationModel;
|
|
use App\Models\UserHotelMembershipModel;
|
|
use App\Models\UserVisaDetailsModel;
|
|
|
|
use PhpOffice\PhpSpreadsheet\IOFactory;
|
|
|
|
class UserController extends ResourceController
|
|
{
|
|
protected $format = 'json';
|
|
protected $myLogger;
|
|
protected $userModel;
|
|
protected $mailTemplateModel;
|
|
protected $userFrequentFlierInformationModel;
|
|
protected $userHotelMembershipModel;
|
|
protected $userVisaDetailsModel;
|
|
|
|
public function __construct()
|
|
{
|
|
$this->myLogger = \Config\Services::mylogger();
|
|
$this->userModel = new UserModel();
|
|
$this->mailTemplateModel = new MailTemplateModel();
|
|
$this->userFrequentFlierInformationModel = new UserFrequentFlierInformationModel();
|
|
$this->userHotelMembershipModel = new UserHotelMembershipModel();
|
|
$this->userVisaDetailsModel = new UserVisaDetailsModel();
|
|
}
|
|
|
|
|
|
public function index()
|
|
{
|
|
$orgId = $this->request->getGet('org_id');
|
|
$for = $this->request->getGet('for');
|
|
if(isset($for)){ $active = [0,1]; }else{ $active = [1]; }
|
|
|
|
$users = $this->userModel->getUsers($orgId,$active,[1,2,3,4]);
|
|
|
|
if (!$users) {
|
|
return $this->failNotFound('No users found');
|
|
}
|
|
|
|
return $this->respond([
|
|
'status' => 200,
|
|
'message' => 'Users retrieved successfully',
|
|
'data' => $users
|
|
]);
|
|
}
|
|
|
|
public function agentList()
|
|
{
|
|
$orgId = $this->request->getGet('org_id');
|
|
$for = $this->request->getGet('for');
|
|
if(isset($for)){ $active = [0,1]; }else{ $active = [1]; }
|
|
|
|
$users = $this->userModel->getUsers($orgId,$active,[5]);
|
|
|
|
if (!$users) {
|
|
return $this->failNotFound('No users found');
|
|
}
|
|
|
|
return $this->respond([
|
|
'status' => 200,
|
|
'message' => 'Users retrieved successfully',
|
|
'data' => $users
|
|
]);
|
|
}
|
|
|
|
public function create()
|
|
{
|
|
$rules = [
|
|
'first_name' => 'required',
|
|
'email' => 'required|valid_email|is_unique[m_users.email]',
|
|
];
|
|
|
|
|
|
|
|
$postData = $this->request->getPost();
|
|
|
|
//mailcontent data
|
|
$mailData = [
|
|
'first_name' => $postData['first_name'],
|
|
'last_name' => $postData['last_name'],
|
|
'email' => $postData['email'],
|
|
'password' => $postData['password'],
|
|
'org_id' => env('ORG_id'),
|
|
'site_url' => env('FE_URL'),
|
|
'template' => 'user_creation_notification',
|
|
];
|
|
|
|
|
|
|
|
if (!$this->validate($rules)) {
|
|
return $this->failValidationErrors($this->validator->getErrors());
|
|
}
|
|
|
|
// $postData = $this->request->getJSON(true);
|
|
$data = $this->formatUserData($postData);
|
|
|
|
|
|
// Hash password before inserting into the database
|
|
if (isset($data['password'])) {
|
|
$data['password'] = password_hash($data['password'], PASSWORD_DEFAULT);
|
|
}
|
|
|
|
$data['org_id'] = env('ORG_id');
|
|
|
|
// Handle file upload
|
|
$file = $this->request->getFile('passport_document');
|
|
if ($file && $file->isValid() && !$file->hasMoved()) {
|
|
$newName = $file->getRandomName(); // Generate a unique name
|
|
$uploadPath = FCPATH.'assets/images/passport';
|
|
|
|
// Move file to the specified directory
|
|
$file->move($uploadPath, $newName);
|
|
|
|
// Save file path in database
|
|
$data['passport_document'] = $uploadPath . '/' . $newName;
|
|
} else {
|
|
// return $this->failValidationErrors(['passport_document' => 'Invalid file upload']);
|
|
}
|
|
|
|
try {
|
|
$insert_id = $this->userModel->insert($data);
|
|
//insert other user data ( hotal membership, visa details, frequent filler )
|
|
$this->createOrUpdateUserOtherDetails($insert_id, $data);
|
|
//trigger Mail
|
|
sendUserCreationMail($mailData);
|
|
return $this->respondCreated([
|
|
'status' => 201,
|
|
'message' => 'User created successfully',
|
|
'data' => $postData
|
|
]);
|
|
} catch (\Exception $e) {
|
|
return $this->failServerError('Failed to create user: ' . $e->getMessage());
|
|
}
|
|
}
|
|
|
|
public function find($id = null)
|
|
{
|
|
if (!$id) {
|
|
return $this->failNotFound('User ID is required');
|
|
}
|
|
|
|
// Fetch user by ID
|
|
$user = $this->userModel->find($id);
|
|
|
|
if (!$user) {
|
|
return $this->failNotFound('User not found');
|
|
}
|
|
|
|
$user = $this->formatUserDataForEdit($user);
|
|
$frequentFlierInformation = $this->userFrequentFlierInformationModel->where('user_id', $id)->findAll() ?? [];
|
|
$hotelMembership = $this->userHotelMembershipModel->where('user_id', $id)->findAll() ?? [];
|
|
$visaDetails = $this->userVisaDetailsModel->where('user_id', $id)->findAll() ?? [];
|
|
|
|
$user['travel_details']['frequent_flier_information'] = $frequentFlierInformation;
|
|
$user['travel_details']['hotel_membership'] = $hotelMembership;
|
|
$user['travel_details']['visa_details'] = $visaDetails;
|
|
|
|
|
|
//formate the date to the indian date format
|
|
$user = $this->convertDateToDBFormat($user, 'd-m-Y');
|
|
|
|
|
|
|
|
return $this->respond([
|
|
'status' => 200,
|
|
'message' => 'User retrieved successfully',
|
|
'data' => $user
|
|
]);
|
|
}
|
|
|
|
public function update($id = null)
|
|
{
|
|
if (!$id) {
|
|
return $this->failNotFound('User ID is required');
|
|
}
|
|
|
|
$postData = $this->request->getPost();
|
|
// $postData = $this->request->getJSON(true);
|
|
$data = $this->formatUserData($postData);
|
|
|
|
if (empty($data)) {
|
|
return $this->failValidationErrors('No data provided for update');
|
|
}
|
|
|
|
// Check if user exists
|
|
$user = $this->userModel->find($id);
|
|
if (!$user) {
|
|
return $this->failNotFound('User not found');
|
|
}
|
|
|
|
// Handle file upload
|
|
$file = $this->request->getFile('passport_document');
|
|
if ($file && $file->isValid() && !$file->hasMoved()) {
|
|
$newName = $file->getRandomName(); // Generate a unique file name
|
|
$uploadPath = FCPATH.'assets/images/passport';
|
|
|
|
// Move file to the directory
|
|
$file->move($uploadPath, $newName);
|
|
|
|
// Delete the old file if it exists
|
|
if (!empty($user['passport_document']) && file_exists($user['passport_document'])) {
|
|
unlink($user['passport_document']); // Remove old file
|
|
}
|
|
|
|
// Save the new file path
|
|
$data['passport_document'] = $uploadPath . '/' . $newName;
|
|
}
|
|
|
|
// Update user details
|
|
try {
|
|
unset($data['password']);
|
|
$this->userModel->update($id, $data);
|
|
//update other user data ( hotal membership, visa details, frequent filler )
|
|
$this->createOrUpdateUserOtherDetails($id, $data);
|
|
return $this->respond([
|
|
'status' => 200,
|
|
'message' => 'User updated successfully',
|
|
'data' => $postData
|
|
]);
|
|
} catch (\Exception $e) {
|
|
return $this->failServerError('Failed to update user: ' . $e->getMessage());
|
|
}
|
|
}
|
|
|
|
public function changePassword($id = null)
|
|
{
|
|
if (!$id) {
|
|
return $this->failNotFound('User ID is required');
|
|
}
|
|
|
|
$data = $this->request->getJSON(true);
|
|
|
|
// Fetch user details
|
|
$user = $this->userModel->find($id);
|
|
if (!$user) {
|
|
return $this->failNotFound('User not found');
|
|
}
|
|
|
|
// Hash new password
|
|
$newPasswordHash = password_hash($data['password'], PASSWORD_DEFAULT);
|
|
|
|
// Update password
|
|
try {
|
|
$this->userModel->update($id, ['password' => $newPasswordHash]);
|
|
return $this->respond([
|
|
'status' => 200,
|
|
'message' => 'Password changed successfully'
|
|
]);
|
|
} catch (\Exception $e) {
|
|
return $this->failServerError('Failed to change password: ' . $e->getMessage());
|
|
}
|
|
}
|
|
|
|
public function updateUserStatus($id)
|
|
{
|
|
// Fetch user by ID
|
|
$user = $this->userModel->find($id);
|
|
|
|
if (!$user) {
|
|
return $this->failNotFound('User not found');
|
|
}
|
|
|
|
// Toggle the is_active status
|
|
$newStatus = $user['is_active'] == 1 ? 0 : 1;
|
|
|
|
// Update user status
|
|
$this->userModel->update($id, ['is_active' => $newStatus]);
|
|
|
|
return $this->respond([
|
|
'status' => 200,
|
|
'message' => $newStatus ? 'User activated successfully' : 'User deactivated successfully',
|
|
'is_active' => $newStatus
|
|
]);
|
|
}
|
|
|
|
public function roleList()
|
|
{
|
|
// Fetch all roles
|
|
$roles = db_connect()->table('m_role')->orderBy('id', 'asc')->get()->getResultArray();
|
|
|
|
// Check roles exist
|
|
if (!$roles) {
|
|
log_message('error', 'No roles found in roleList()');
|
|
return $this->failNotFound('No roles found');
|
|
}
|
|
|
|
log_message('error', 'Roles retrieved successfully in roleList()');
|
|
|
|
return $this->respond([
|
|
'status' => 200,
|
|
'message' => 'Roles retrieved successfully',
|
|
'data' => $roles
|
|
]);
|
|
}
|
|
|
|
public function verifyUser()
|
|
{
|
|
$data = $this->request->getJSON(true);
|
|
|
|
if (empty($data)) {
|
|
log_message('error', "No data provided for user verification");
|
|
return $this->failValidationErrors('No data provided for verification');
|
|
}
|
|
|
|
if (!isset($data['email']) || empty($data['email'])) {
|
|
log_message('error', "Email is missing or empty for user verification");
|
|
return $this->failValidationErrors('Email is required for user verification');
|
|
}
|
|
|
|
//featch user data for the give email
|
|
$userData = $this->userModel->where('email', $data['email'])->first();
|
|
|
|
if(empty($userData)){
|
|
log_message('error', "User not found");
|
|
return $this->failNotFound('User not found');
|
|
}
|
|
|
|
if ($userData['is_active'] == 0) {
|
|
log_message('error', "User found but not active");
|
|
return $this->failNotFound('User found but not active, no further action to be made');
|
|
}
|
|
|
|
//generate random number for OTP
|
|
$temp_password = random_int(100000, 999999);
|
|
$userData['otp'] = $temp_password;
|
|
log_message('error', "Generated temp password : ".$temp_password ?? "-");
|
|
|
|
//update otp to the given email user
|
|
$return_value = $this->userModel->where('email', $data['email'])->set('temp_password', $temp_password)->update();
|
|
log_message('error', "Temp password updated successfully aginst the user email");
|
|
|
|
//mail send function
|
|
$mail_response = send_email($userData['org_id'], $data['email'], 'forgot_password_otp', $userData);
|
|
// print_r($mail_response);
|
|
|
|
$data = [
|
|
"request_data" => $data,
|
|
"mail_response" => $mail_response,
|
|
];
|
|
|
|
return $this->respond([
|
|
'status' => 200,
|
|
'message' => 'User verified successfully. Mail send to the given mail-id',
|
|
'data' => $data,
|
|
]);
|
|
|
|
}
|
|
|
|
public function forgotChangePassword()
|
|
{
|
|
$data = $this->request->getJSON(true);
|
|
|
|
if (empty($data)) {
|
|
log_message('error', "No data provided for forgot change password");
|
|
return $this->failValidationErrors('No data provided for change password');
|
|
}
|
|
|
|
if (!isset($data['email']) || empty($data['email'])) {
|
|
log_message('error', "email is missing or empty for forgot change password");
|
|
return $this->failValidationErrors('Email id is required for change password');
|
|
}
|
|
|
|
if (!isset($data['otp']) || empty($data['otp'])) {
|
|
log_message('error', "Temp password is missing or empty for forgot change password");
|
|
return $this->failValidationErrors('OTP is required for change password');
|
|
}
|
|
|
|
if (!isset($data['new_password']) || empty($data['new_password'])) {
|
|
log_message('error', "New password is missing or empty for forgot change password");
|
|
return $this->failValidationErrors('New password is required for change password');
|
|
}
|
|
|
|
if (!isset($data['confirm_password']) || empty($data['confirm_password'])) {
|
|
log_message('error', "Confirm password is missing or empty for forgot change password");
|
|
return $this->failValidationErrors('Confirm password is required for change password');
|
|
}
|
|
|
|
if (!isset($data['confirm_password']) || empty($data['confirm_password'])) {
|
|
log_message('error', "Confirm password is missing or empty for forgot change password");
|
|
return $this->failValidationErrors('Confirm password is required for change password');
|
|
}
|
|
|
|
//featch user data for the give email
|
|
$userData = $this->userModel->where('email', $data['email'])->first();
|
|
|
|
if(empty($userData)){
|
|
log_message('error', "User not found");
|
|
return $this->failNotFound('User not found');
|
|
}
|
|
|
|
if ($userData['is_active'] == 0) {
|
|
log_message('error', "User found but not active");
|
|
return $this->failNotFound('User found but not active, no further action to be made');
|
|
}
|
|
|
|
if($userData['temp_password'] !== $data['otp']){
|
|
log_message('error', "Invalid OTP");
|
|
return $this->failValidationErrors('Invalid OTP');
|
|
}
|
|
|
|
if($data['new_password'] !== $data['confirm_password']){
|
|
log_message('error', "New password as not same as the confirm password");
|
|
return $this->failValidationErrors('New password as not same as the confirm password');
|
|
}
|
|
|
|
//construct the updated data
|
|
$update_data = [
|
|
'password' => password_hash($data['new_password'], PASSWORD_DEFAULT),
|
|
'temp_password' => null
|
|
];
|
|
|
|
$return_value = $this->userModel->where('user_id', $userData['user_id'])->set($update_data)->update();
|
|
log_message('error', "Password changed successfully and Temp password reseted successfully aginst the user id");
|
|
|
|
return $this->respond([
|
|
'status' => 200,
|
|
'message' => 'Password changed successfully.',
|
|
]);
|
|
}
|
|
|
|
public function createOrUpdateUserOtherDetails($user_id, $data)
|
|
{
|
|
|
|
//insert or update frequent flier information
|
|
if(!empty($data) && isset($data['frequent_flier_information']) && !empty($data['frequent_flier_information'])){
|
|
foreach ($data['frequent_flier_information'] as $key => $value) {
|
|
$value['user_id'] = $user_id;
|
|
if(isset($value['id']) && !empty($value['id'])){
|
|
$this->userFrequentFlierInformationModel->update($value['id'], $value);
|
|
}else{
|
|
$this->userFrequentFlierInformationModel->insert($value);
|
|
}
|
|
}
|
|
}
|
|
|
|
//insert or update hotel membership
|
|
if(!empty($data) && isset($data['hotel_membership']) && !empty($data['hotel_membership'])){
|
|
foreach ($data['hotel_membership'] as $key => $value) {
|
|
$value['user_id'] = $user_id;
|
|
if(isset($value['id']) && !empty($value['id'])){
|
|
$this->userHotelMembershipModel->update($value['id'], $value);
|
|
}else{
|
|
$this->userHotelMembershipModel->insert($value);
|
|
}
|
|
}
|
|
}
|
|
|
|
//insert or update visa details
|
|
if(!empty($data) && isset($data['visa_details']) && !empty($data['visa_details'])){
|
|
foreach ($data['visa_details'] as $key => $value) {
|
|
$value['user_id'] = $user_id;
|
|
if(isset($value['id']) && !empty($value['id'])){
|
|
$this->userVisaDetailsModel->update($value['id'], $value);
|
|
}else{
|
|
$this->userVisaDetailsModel->insert($value);
|
|
}
|
|
}
|
|
}
|
|
|
|
return true;
|
|
}
|
|
|
|
public function formatUserData($data)
|
|
{
|
|
if (empty($data)) {
|
|
return $data;
|
|
}
|
|
|
|
if (isset($data['travel_details'])) {
|
|
|
|
if (!is_array($data['travel_details'])) {
|
|
$decoded = json_decode($data['travel_details'], true);
|
|
if (json_last_error() === JSON_ERROR_NONE) {
|
|
$data['travel_details'] = $decoded;
|
|
|
|
//format the date to the database format
|
|
$data = $this->convertDateToDBFormat($data);
|
|
|
|
} else {
|
|
return $data;
|
|
}
|
|
}
|
|
|
|
$data = array_merge($data, $data['travel_details']);
|
|
unset($data['travel_details']);
|
|
}
|
|
|
|
return $data;
|
|
}
|
|
|
|
public function formatUserDataForEdit($data)
|
|
{
|
|
if (!empty($data)) {
|
|
|
|
$travelKeys = [
|
|
'passport_firstname',
|
|
'passport_middlename',
|
|
'passport_lastname',
|
|
'nationality',
|
|
'passport_number',
|
|
'place_of_issue',
|
|
'passport_document',
|
|
'date_of_expiry',
|
|
'd_meal_preference',
|
|
'd_seat_preference',
|
|
'd_additonalInfo',
|
|
'i_meal_preference',
|
|
'i_seat_preference',
|
|
'i_additonalInfo',
|
|
'emergency_contact_number',
|
|
'date_of_issue',
|
|
'forex_pre_paid_card_number',
|
|
'forex_expiry_date',
|
|
];
|
|
|
|
$data['travel_details'] = [];
|
|
|
|
foreach ($travelKeys as $key) {
|
|
if (array_key_exists($key, $data)) {
|
|
$data['travel_details'][$key] = $data[$key];
|
|
unset($data[$key]);
|
|
} else {
|
|
$data['travel_details'][$key] = null;
|
|
}
|
|
}
|
|
|
|
|
|
}
|
|
|
|
return $data;
|
|
}
|
|
|
|
//Function for date conversion
|
|
public function convertDateToDBFormat($data, $format = 'Y-m-d')
|
|
{
|
|
if (!empty($data)) {
|
|
|
|
// Handle date_of_birth
|
|
if (isset($data['date_of_birth'])) {
|
|
$dob = trim($data['date_of_birth']);
|
|
$timestamp = ($dob && $dob !== '0000-00-00' && $dob !== '0000-00-00 00:00:00') ? strtotime($dob) : false;
|
|
$data['date_of_birth'] = ($timestamp) ? date($format, $timestamp) : null;
|
|
}
|
|
|
|
// Handle delegation_start_date
|
|
if (isset($data['delegation_start_date'])) {
|
|
$dob = trim($data['delegation_start_date']);
|
|
$timestamp = ($dob && $dob !== '0000-00-00' && $dob !== '0000-00-00 00:00:00') ? strtotime($dob) : false;
|
|
$data['delegation_start_date'] = ($timestamp) ? date($format, $timestamp) : null;
|
|
}
|
|
|
|
// Handle delegation_end_date
|
|
if (isset($data['delegation_end_date'])) {
|
|
$dob = trim($data['delegation_end_date']);
|
|
$timestamp = ($dob && $dob !== '0000-00-00' && $dob !== '0000-00-00 00:00:00') ? strtotime($dob) : false;
|
|
$data['delegation_end_date'] = ($timestamp) ? date($format, $timestamp) : null;
|
|
}
|
|
|
|
if (!empty($data['travel_details']) && is_array($data['travel_details'])) {
|
|
|
|
// Handle date_of_issue
|
|
if (isset($data['travel_details']['date_of_issue'])) {
|
|
$doi = trim($data['travel_details']['date_of_issue']);
|
|
$timestamp = ($doi && $doi !== '0000-00-00' && $doi !== '0000-00-00 00:00:00') ? strtotime($doi) : false;
|
|
$data['travel_details']['date_of_issue'] = ($timestamp) ? date($format, $timestamp) : null;
|
|
}
|
|
|
|
// Handle date_of_expiry
|
|
if (isset($data['travel_details']['date_of_expiry'])) {
|
|
$doe = trim($data['travel_details']['date_of_expiry']);
|
|
$timestamp = ($doe && $doe !== '0000-00-00' && $doe !== '0000-00-00 00:00:00') ? strtotime($doe) : false;
|
|
$data['travel_details']['date_of_expiry'] = ($timestamp) ? date($format, $timestamp) : null;
|
|
}
|
|
|
|
// Handle forex_expiry_date
|
|
if (isset($data['travel_details']['forex_expiry_date'])) {
|
|
$fed = trim($data['travel_details']['forex_expiry_date']);
|
|
$timestamp = ($fed && $fed !== '0000-00-00' && $fed !== '0000-00-00 00:00:00') ? strtotime($fed) : false;
|
|
$data['travel_details']['forex_expiry_date'] = ($timestamp) ? date($format, $timestamp) : null;
|
|
}
|
|
|
|
// Handle visa_details
|
|
if (!empty($data['travel_details']['visa_details']) && is_array($data['travel_details']['visa_details'])) {
|
|
foreach ($data['travel_details']['visa_details'] as $key => &$value) {
|
|
|
|
// valid_from
|
|
$from = trim($value['valid_from'] ?? '');
|
|
$timestamp1 = ($from && $from !== '0000-00-00' && $from !== '0000-00-00 00:00:00') ? strtotime($from) : false;
|
|
$value['valid_from'] = ($timestamp1) ? date($format, $timestamp1) : null;
|
|
|
|
// valid_upto
|
|
$upto = trim($value['valid_upto'] ?? '');
|
|
$timestamp2 = ($upto && $upto !== '0000-00-00' && $upto !== '0000-00-00 00:00:00') ? strtotime($upto) : false;
|
|
$value['valid_upto'] = ($timestamp2) ? date($format, $timestamp2) : null;
|
|
}
|
|
unset($value);
|
|
}
|
|
}
|
|
}
|
|
|
|
return $data;
|
|
}
|
|
|
|
|
|
public function checkDuplicate()
|
|
{
|
|
$request = $this->request->getGet();
|
|
|
|
// Define supported fields
|
|
$validFields = ['email', 'mobile_no', 'forex_pre_paid_card_number', 'employee_code', 'passport_number'];
|
|
|
|
$conditions = [];
|
|
$fieldName = null;
|
|
|
|
// Determine which field is provided
|
|
foreach ($validFields as $field) {
|
|
if (!empty($request[$field])) {
|
|
$conditions[$field] = $request[$field];
|
|
$fieldName = $field;
|
|
break; // only one field allowed at a time
|
|
}
|
|
}
|
|
|
|
if (!$fieldName) {
|
|
return $this->response->setJSON([
|
|
'status' => 'error',
|
|
'message' => 'One of the following is required: email, mobile_no, forex_pre_paid_card_number, employee_code'
|
|
])->setStatusCode(400);
|
|
}
|
|
|
|
$builder = $this->userModel->where($fieldName, $conditions[$fieldName]);
|
|
|
|
// Optional: exclude user_id
|
|
if (!empty($request['user_id'])) {
|
|
$builder->where('user_id !=', $request['user_id']);
|
|
}
|
|
|
|
$user = $builder->first();
|
|
|
|
if ($user) {
|
|
return $this->response->setJSON(['status' => 'exists', 'field' => $fieldName]);
|
|
} else {
|
|
return $this->response->setJSON(['status' => 'not', 'field' => $fieldName]);
|
|
}
|
|
}
|
|
|
|
|
|
public function userUpload()
|
|
{
|
|
|
|
$predefinedHeaders = ['First Name', 'Last Name', 'Email', 'Mobile Number', 'Password' , 'Role' ,'Employee Code','Group Name',
|
|
'First Approver Email','Second Approver Email','Third Approver Email','Exceptional Approver Email'];
|
|
|
|
$uploadDir = WRITEPATH . 'uploads/userUploadFiles/';
|
|
|
|
// Create folder if not exists
|
|
createDirectoryWith0777Permission($uploadDir);
|
|
|
|
|
|
$file = $this->request->getFile('user_file');
|
|
|
|
if (!isValidUploadedFile($file)) {
|
|
return $this->response->setJSON([
|
|
'status' => 'failed',
|
|
'message' => "Invalid file or file not uploaded.",
|
|
'data' => ['successfulUsers' => [],'failedUsers' => [] ]
|
|
]);
|
|
}
|
|
|
|
if (!isAllowedExtension($file, ['xlsx', 'xls'])) {
|
|
return $this->response->setJSON([
|
|
'status' => 'failed',
|
|
'message' => "Only Excel files are allowed.",
|
|
'data' => ['successfulUsers' => [],'failedUsers' => [] ]
|
|
]);
|
|
}
|
|
|
|
// Move file temporarily
|
|
$randomName = $file->getRandomName();
|
|
$file->move($uploadDir, $randomName);
|
|
$filePath = $uploadDir . $randomName;
|
|
|
|
// Load Excel
|
|
$spreadsheet = IOFactory::load($filePath);
|
|
$sheetData = $spreadsheet->getActiveSheet()->toArray(null, true, true, true);
|
|
|
|
$maxColumns = 12;
|
|
|
|
$trimmedData = array_map(function ($row) use ($maxColumns) {
|
|
return array_slice($row, 0, $maxColumns);
|
|
}, $sheetData);
|
|
|
|
if (!isExcelNotEmpty($sheetData)) {
|
|
// before return remove the empty file
|
|
return $this->response->setJSON([
|
|
'status' => 'failed',
|
|
'message' => "Excel sheet is empty or has no data.",
|
|
'data' => ['successfulUsers' => [],'failedUsers' => [] ]
|
|
]);
|
|
}
|
|
|
|
// Validate headers
|
|
// Sanitize headers: remove spaces/special characters and convert to lowercase
|
|
$rawHeaders = array_values($trimmedData[1]);
|
|
|
|
$headers = array_map(function ($header) {
|
|
return strtolower(preg_replace('/[^a-zA-Z0-9]/', '', trim($header)));
|
|
}, $rawHeaders);
|
|
|
|
$predefinedHeaders = array_map(function ($header) {
|
|
return strtolower(preg_replace('/[^a-zA-Z0-9]/', '', $header));
|
|
}, $predefinedHeaders);
|
|
|
|
|
|
unset($trimmedData[1]); // Remove header row
|
|
|
|
$success = 0 ;
|
|
$fail = 0 ;
|
|
$successfulUsers = [];
|
|
$failedUsers = [];
|
|
$insertUsers = [];
|
|
|
|
$dbHeaders = ['first_name','last_name','email','mobile_no','password','role_id','employee_code','group_id',
|
|
'first_approver_email','second_approver_email','third_approver_email','exceptional_approver_email'];
|
|
|
|
$rolesList = $this->userModel->getRolesList();
|
|
|
|
$groupsList = $this->userModel->getgroupsList();
|
|
|
|
|
|
foreach ($trimmedData as $row) {
|
|
|
|
$user = array_combine($dbHeaders, array_values($row));
|
|
$email = $user['email'] ?? 'N/A';
|
|
|
|
// Email validation
|
|
if (!isset($user['email']) || empty($user['email'])) {
|
|
$fail++;
|
|
$failedUsers[] = ['data' => $user['first_name'].' '.$user['last_name'], 'reason' => 'Email is missing'];
|
|
continue;
|
|
}
|
|
|
|
if (!filter_var($user['email'], FILTER_VALIDATE_EMAIL)) {
|
|
$fail++;
|
|
$failedUsers[] = ['data' => $email, 'reason' => 'Invalid email format'];
|
|
continue;
|
|
}
|
|
|
|
// Check duplicate
|
|
$userExists = $this->userModel->userExists($user['email']);
|
|
if ($userExists) {
|
|
$fail++;
|
|
$failedUsers[] = ['data' => $email, 'reason' => 'User already exists'];
|
|
continue;
|
|
}
|
|
|
|
// Check approver mail valid
|
|
if (!empty($user['first_approver_email']) && !filter_var($user['first_approver_email'], FILTER_VALIDATE_EMAIL)) {
|
|
$fail++;
|
|
$failedUsers[] = ['data' => $user['first_name'].' '.$user['last_name'], 'reason' => 'Invalid first approver email format' ];
|
|
continue;
|
|
}
|
|
|
|
if (!empty($user['second_approver_email']) && !filter_var($user['second_approver_email'], FILTER_VALIDATE_EMAIL)) {
|
|
$fail++;
|
|
$failedUsers[] = ['data' => $user['first_name'].' '.$user['last_name'], 'reason' => 'Invalid second_approver_email format' ];
|
|
continue;
|
|
}
|
|
|
|
if (!empty($user['third_approver_email']) && !filter_var($user['third_approver_email'], FILTER_VALIDATE_EMAIL)) {
|
|
$fail++;
|
|
$failedUsers[] = ['data' => $user['first_name'].' '.$user['last_name'], 'reason' => 'Invalid third_approver_email format' ];
|
|
continue;
|
|
}
|
|
|
|
|
|
if (!empty($user['exceptional_approver_email']) && !filter_var($user['exceptional_approver_email'], FILTER_VALIDATE_EMAIL)) {
|
|
$fail++;
|
|
$failedUsers[] = ['data' => $user['first_name'].' '.$user['last_name'], 'reason' => 'Invalid exceptional_approver_email format' ];
|
|
continue;
|
|
}
|
|
|
|
|
|
|
|
$role = strtolower(preg_replace('/[^A-Za-z0-9]/', '', $user['role_id']));
|
|
$group = strtolower(preg_replace('/[^A-Za-z0-9]/', '', $user['group_id']));
|
|
|
|
// Sanitize and prepare for insert
|
|
$user['password_string'] = $user['password'];
|
|
$user['password'] = password_hash($user['password'], PASSWORD_DEFAULT);
|
|
$user['email'] = filter_var($user['email'], FILTER_SANITIZE_EMAIL);
|
|
$user['first_approver_email'] = filter_var($user['first_approver_email'], FILTER_SANITIZE_EMAIL);
|
|
$user['second_approver_email'] = filter_var($user['second_approver_email'], FILTER_SANITIZE_EMAIL);
|
|
$user['third_approver_email'] = filter_var($user['third_approver_email'], FILTER_SANITIZE_EMAIL);
|
|
$user['exceptional_approver_email'] = filter_var($user['exceptional_approver_email'], FILTER_SANITIZE_EMAIL);
|
|
$user['role_id'] = $rolesList[$role] ?? 4;
|
|
$user['group_id'] = $groupsList[$group] ?? null;
|
|
$user['org_id'] = env('ORG_id');
|
|
|
|
$insertUsers[] = $user;
|
|
$success++;
|
|
$successfulUsers[] = $user['email'];
|
|
}
|
|
|
|
|
|
$insertedIds = [];
|
|
|
|
foreach ($insertUsers as $user) {
|
|
$insertSuccess = $this->userModel->insert($user);
|
|
|
|
if ($insertSuccess) {
|
|
$insertedIds[] = $this->userModel->getInsertID();
|
|
|
|
// Prepare mail content
|
|
$mailData = [
|
|
'first_name' => $user['first_name'],
|
|
'last_name' => $user['last_name'],
|
|
'email' => $user['email'],
|
|
'password' => $user['password_string'],
|
|
'org_id' => env('ORG_id'),
|
|
'site_url' => env('FE_URL'),
|
|
'template' => 'user_creation_notification',
|
|
];
|
|
|
|
// Trigger mail
|
|
sendUserCreationMail($mailData);
|
|
}
|
|
}
|
|
|
|
|
|
|
|
//since email id directly stored in first_approver_email need to update in first_approver with id
|
|
|
|
$this->userModel->updateApprover('first', $insertedIds);
|
|
$this->userModel->updateApprover('second', $insertedIds);
|
|
$this->userModel->updateApprover('third', $insertedIds);
|
|
$this->userModel->updateApprover('exceptional', $insertedIds);
|
|
|
|
|
|
return $this->response->setJSON([
|
|
'status' => 'success',
|
|
'message' => "$success users processed successfully, $fail failed.",
|
|
'data' => [
|
|
'successfulUsers' => $successfulUsers,
|
|
'failedUsers' => $failedUsers
|
|
]
|
|
]);
|
|
}
|
|
|
|
public function userUploadTemplate()
|
|
{
|
|
$uploadDir = WRITEPATH . 'uploads/template';
|
|
|
|
createDirectoryWith0777Permission($uploadDir);
|
|
|
|
$filePath = WRITEPATH . 'uploads/template/user_file.xlsx';
|
|
|
|
if (!file_exists($filePath)) {
|
|
return $this->response->setStatusCode(404)->setJSON(['error' => 'Template file not found.']);
|
|
}
|
|
|
|
return $this->response->download($filePath, null);
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
}
|