query($sql); while($row = $database->fetchArray($query)) { $row['type'] = ucfirst($row['type']); $row['type'] = str_replace('_', ' ', $row['type']); $data[$row['type']][] = $row; } return $data; } /** * gets all the user tyeps/roles from the DB * @return Array of user types */ public function getUserTypes() { global $database; $data=[]; $sql = "SELECT id, type AS name FROM ".TABLES['user_types']." "; $query = $database->query($sql); while($row = $database->fetchArray($query)){ $row['name'] = ucfirst($row['name']); $row['name'] = str_replace('_', ' ', $row['name']); $data[] = $row; } return $data; } /** * gets all the commercial leads from the DB * @return Array with all the commercial leads */ public function getCommercialLeads() { global $database; $sql = "SELECT id, name FROM ".TABLES['commercial_leads']." "; return $database->fetchResultArray($sql); } /** * @param info - array with all the details regarding new user * @param commercialLeads - array with all the commercial leads * @return Array array with the code and the message of confirmation for adding the user in the DB */ public function saveUserInDB($info, $commercialLeads = '') { global $database; $info = (array) json_decode($info); $commercialLeads = json_decode($commercialLeads); $data = []; foreach($info as $key => $value) { $info['$key'] = $database->escapeValue($value); $checkMessage = $database->isEmpty($key, $value); if($checkMessage){ $data['messages'][] = $checkMessage; return $data; } } $messageData = $this->validateUserData($info, $commercialLeads); if(!empty($messageData)){ return $messageData; } $token = bin2hex(random_bytes(16)); $idUser = $this->getInsertedIdForUsers($info, $token); if(is_array($idUser)) { return $idUser; } if($data = $this->insertUserTypeRelation($idUser, $info['idUserType'])) { return $data; } $data = $this->insertUserInfo($idUser, $info, $commercialLeads); $info['type'] = $this->getUserTypeByIdForMail($info['idUserType']); $data['messages'][] = UtilsModel::sendUserConfirmationMail($info, $info['mail'], 'create', $token); return $data; } /** * get user type by id for mail * @param Int $idUserType the id of the user type * @return String 'customer' or 'other' based on the user type */ private function getUserTypeByIdForMail($idUserType) { global $database; $sql = "SELECT type FROM ".TABLES['user_types']." ut WHERE ut.id=".$idUserType; $result = $database->fetchResultArray($sql); return $result && $result[0]['type'] === USER_TYPES['CUSTOMER'] ? 'customer' : 'other'; } /** * validate user data from GUI * @param Array $info all information about the user to be inserted * @param Array $commercialLeads all the commercial leads linked to a customer * @return Array empty or error message */ private function validateUserData($info, $commercialLeads) { global $database; $data = []; if(!$info['idUserType']) { $data['messages'][] = [ 'code' => 'error', 'message' => 'SELECT_USER_TYPE' ]; return $data; } if($info['idUserType'] === '2' && empty($commercialLeads)) { $data['messages'][] = [ 'code' => 'error', 'message' => 'NO_COMMERCIAL_LEAD_LINK' ]; return $data; } if(!isset($info['name']) || empty($info['name'])) { $data['messages'][] = [ 'code' => 'error', 'message' => 'ADD_NAME' ]; return $data; } $checkMessage = $database->invalidLength('name', $info['name'], 70); if($checkMessage){ $data['messages'][] = $checkMessage; } if(array_key_exists('selectedCompanyId', $info)) { if(!$info['selectedCompanyId']) { $data['messages'][] = [ 'code' => 'error', 'message' => 'COMPANY_EMPTY' ]; return $data; } } if(!array_key_exists('selectedCompanyId', $info)) { if(!isset($info['companyName']) || empty($info['companyName'])) { $data['messages'][] = [ 'code' => 'error', 'message' => 'ADD_COMPANY_NAME' ]; return $data; } $checkMessage = $database->invalidLength('companyName', $info['companyName'], 100); if($checkMessage){ $data['messages'][] = $checkMessage; } if(!isset($info['vat']) || empty($info['vat'])) { $data['messages'][] = [ 'code' => 'error', 'message' => 'ADD_VAT' ]; return $data; } } if(!isset($info['phone']) || empty($info['phone'])) { $data['messages'][] = [ 'code' => 'error', 'message' => 'ADD_PHONE' ]; return $data; } if(!preg_match('/^([0-9\(\)\/\+ \-]*)$/', $info['phone'])){ $data['messages'][] = [ 'code' => 'error', 'message' => 'INVALID_PHONE_NUMBER' ]; } $checkMessage = $database->invalidLength('phone', $info['phone'], 40); if($checkMessage){ $data['messages'][] = $checkMessage; } if(!isset($info['username']) || empty($info['username'])) { $data['messages'][] = [ 'code' => 'error', 'message' => 'ADD_USERNAME' ]; return $data; } $checkMessage = $database->invalidLength('username', $info['username'], 20); if($checkMessage){ $data['messages'][] = $checkMessage; } if(!preg_match('/^[a-zA-Z\d\.\-_]+$/',$info['username'])) { $data['messages'][] = [ 'code' => 'error', 'message' => 'INVALID_USERNAME' ]; } $sql = "SELECT username FROM ".TABLES['users']." WHERE username='".$info['username']."' LIMIT 1"; $result = $database->query($sql); if($database->numRows($result) > 0) { $data['messages'][] = [ 'code' => 'error', 'message' => 'USERNAME_EXISTS' ]; } if(!isset($info['mail']) || empty($info['mail'])) { $data['messages'][] = [ 'code' => 'error', 'message' => 'ADD_MAIL' ]; return $data; } if(!filter_var($info['mail'], FILTER_VALIDATE_EMAIL)){ $data['messages'][] = [ 'code' => 'error', 'message' => 'INVALID_MAIL' ]; } return $data; } /** * inserts username, password and mail into users table * @param String $info the data array with all user info * @param String $token the token for newly created user * @return Int the id of the user inserted */ private function getInsertedIdForUsers($info, $token) { global $database, $user; $tokenTimestamp = new DateTime(); if(!array_key_exists('selectedCompanyId', $info)) { $idCompany = $this->insertCompanyAndReturnId($info['companyName'], $info['vat']); if(is_array($idCompany)) { return $idCompany; } } else { $idCompany = $info['selectedCompanyId']; } $isCompanyAdmin = array_key_exists('companyAdmin', $info) && $info['companyAdmin'] ? 1 : 0; $sql = "INSERT INTO ".TABLES['users']." (idCompany, username, mail, token, tokenTS, isCompanyAdmin) VALUES ( $idCompany, '".$info['username']."', '".$info['mail']."', '".$token."', '".$tokenTimestamp->format('Y-m-d H:i:s')."', $isCompanyAdmin )"; $result = $database->query($sql); return $database->getInsertId(); } /** * inserts the new company data * @param String $name the name of the company * @param String $vat the vat code for the company * @return Int the id of the company inserted */ private function insertCompanyAndReturnId($name, $vat) { global $database; $sql = "SELECT name FROM ".TABLES['company']." WHERE name='$name'"; $query = $database->query($sql); if($database->numRows($query)) { $data['messages'][] = [ 'code' => 'warning', 'message' => 'COMPANY_EXISTS' ]; return $data; } $sql = "INSERT INTO ".TABLES['company']." (vatCode, name) VALUES ('$vat', '$name') "; $result = $database->query($sql); return $database->getInsertId(); } /** * inserts the relation between user and user type * @param Int $idUser id of the user inserted * @param Int $idType id of the user type to be inserted * @return Array empty or error message */ private function insertUserTypeRelation($idUser, $idType) { global $database; $data = []; $sql = "INSERT INTO ".TABLES['rel_user_type']." VALUES( $idUser, $idType )"; $result = $database->query($sql); if(!$database->affectedRows()) { $data['messages'][] = [ 'code' => 'error', 'message' => 'ERROR_USER_TYPE' ]; } return $data; } /** * insert user information * @param Int $idUser id of the user inserted * @param Array $info all the information needed for the user * @param Array $commercialLeads commercial leads to link to customer * @return Array confirmation message */ private function insertUserInfo($idUser, $info, $commercialLeads) { global $database; $data = []; $shouldLinkCommercialLeads = false; switch ($info['idUserType']) { // broker case '1': $table = TABLES['brokers']; break; // customer case '2': $table = TABLES['customers']; $shouldLinkCommercialLeads = true; break; // commercial lead case '3': $table = TABLES['commercial_leads']; break; // supplier case '4': $table = TABLES['suppliers']; break; default: break; } $sql = "INSERT INTO $table (idUser, name, phone) VALUES ( ".$idUser.", '".$info['name']."', '".$info['phone']."' )"; $result = $database->query($sql); if($database->affectedRows()) { $data['messages'][] = [ 'code' => 'success', 'message' => 'USER_INSERTED' ]; } else { $data['messages'][] = [ 'code' => 'error', 'message' => 'ERROR_USER_INFO' ]; } if($shouldLinkCommercialLeads) { $idCustomer = $database->getInsertId(); $values = ''; foreach($commercialLeads as $commercialLead) { $values .= "(".$commercialLead->id.", $idCustomer),"; } $values = rtrim($values, ','); $sql = "INSERT INTO ".TABLES['rel_commercial_lead_customers']." (idCommercialLead, idCustomer) VALUES $values"; $result = $database->query($sql); if(!$database->affectedRows()) { $data['messages'][] = [ 'code' => 'error', 'message' => 'ERROR_USER_CL' ]; } } return $data; } /** * get customers linked to comemrcial leads * @return Array list of customers grouped by commercial lead id */ private function getCommercialLeadsCustomers(){ global $database; $data = []; $sql = "SELECT rclc.idCommercialLead, rclc.idCustomer as id, c.name FROM ".TABLES['rel_commercial_lead_customers']." rclc INNER JOIN ".TABLES['customers']." c ON c.id=rclc.idCustomer WHERE rclc.isLinkEnabled=1 ORDER BY name"; $query = $database->query($sql); while($row = $database->fetchArray($query)){ $data[$row['idCommercialLead']][] = $row; } return $data; } /** * get all customers and commercial leads in the system (included linked custoemrs to commercial lead) * @return Array list of customers and list of commercial leads */ public function getCustomersAndCl() { global $database; $data = []; $clCustomers = $this->getCommercialLeadsCustomers(); $sql = "SELECT c.id AS id, c.name AS name, 'customers' AS userType FROM ".TABLES['customers']." c UNION ALL SELECT cl.id AS id, cl.name AS name, 'commercialLeads' AS userType FROM ".TABLES['commercial_leads']." cl ORDER BY userType, name"; $query = $database->query($sql); while($row = $database->fetchArray($query)){ if($row['userType'] === 'commercialLeads'){ $row['linkedCustomers'] = isset($clCustomers[$row['id']]) ? $clCustomers[$row['id']] : []; } $data[$row['userType']][] = $row; } return $data; } /** * update customers for a commercial lead * @param INT $idCommercialLead id for the commercial lead * @param Array $customers list of customers to be linked * @return Array update message */ public function updateLinkedCustomers($idCommercialLead, $customers){ global $database; $data = []; $idCommercialLead = $database->escapeValue($idCommercialLead); $customers = json_decode($customers); if(intval($idCommercialLead) == 0){ $data['messages'][] = [ 'code' => 'error', 'message' => 'INVALID_COMMERCIAL_LEAD' ]; } $sqlCustomers = "SELECT rclc.idCustomer FROM ".TABLES['rel_commercial_lead_customers']." rclc WHERE idCommercialLead=$idCommercialLead"; $query = $database->query($sqlCustomers); $availableCustomers = []; while($row = $database->fetchArray($query)){ $availableCustomers[] = $row['idCustomer']; } $sqlIns = ""; $customersToUpdate = []; $updated = 0; foreach ($customers as $customer) { if(!in_array($customer->id, $availableCustomers)){ $customer->id = $database->escapeValue($customer->id); $sqlIns .= "($idCommercialLead, ".$customer->id."),"; } $customersToUpdate[] = $customer->id; } $sqlIns = rtrim($sqlIns, ','); if(!empty($sqlIns)){ $sql = "INSERT IGNORE INTO ".TABLES['rel_commercial_lead_customers']." (idCommercialLead, idCustomer) VALUES $sqlIns"; $query = $database->query($sql); $updated += $database->affectedRows(); } if(!empty($customersToUpdate)){ $customersToUpdate = implode(',', $customersToUpdate); $sqlUpd = "UPDATE ".TABLES['rel_commercial_lead_customers']." SET isLinkEnabled=1 WHERE idCommercialLead=$idCommercialLead AND idCustomer IN($customersToUpdate)"; $query = $database->query($sqlUpd); $updated += $database->affectedRows(); $sqlUnlink = "UPDATE ".TABLES['rel_commercial_lead_customers']." SET isLinkEnabled=0 WHERE idCommercialLead=$idCommercialLead AND idCustomer NOT IN($customersToUpdate)"; $query = $database->query($sqlUnlink); $updated += $database->affectedRows(); } if($updated > 0){ $data['messages'][] = [ 'code' => 'success', 'message' => 'CUSTOMERS_LINKED_TO_CL' ]; }else{ $data['messages'][] = [ 'code' => 'warning', 'message' => 'NO_CHANGES' ]; } return $data; } /** * returns the companies name and id * @return Array companies available in the application */ public function getCompanies() { global $database; $sql = " SELECT c.id, c.name FROM ".TABLES['company']." c ORDER BY name"; return $database->fetchResultArray($sql); } }