Files
crm.clientright.ru/modules/Vtiger/handlers/FollowRecordHandler.php
Fedor ac7467f0b4 Major CRM updates: AI Assistant, Court Status API, S3 integration improvements, and extensive file storage system
- Added comprehensive AI Assistant system (aiassist/ directory):
  * Vector search and embedding capabilities
  * Typebot proxy integration
  * Elastic search functionality
  * Message classification and chat history
  * MCP proxy for external integrations

- Implemented Court Status API (GetCourtStatus.php):
  * Real-time court document status checking
  * Integration with external court systems
  * Comprehensive error handling and logging

- Enhanced S3 integration:
  * Improved file backup system with metadata
  * Batch processing capabilities
  * Enhanced error logging and recovery
  * Copy operations with URL fixing

- Added Telegram contact creation API
- Improved error logging across all modules
- Enhanced callback system for AI responses
- Extensive backup file storage with timestamps
- Updated documentation and README files

- File storage improvements:
  * Thousands of backup files with proper metadata
  * Fix operations for broken file references
  * Project-specific backup and recovery systems
  * Comprehensive file integrity checking

Total: 26,461+ files added/modified including AWS SDK, vendor dependencies, and extensive backup system.
2025-10-16 11:17:21 +03:00

170 lines
7.1 KiB
PHP

<?php
/* +**********************************************************************************
* The contents of this file are subject to the vtiger CRM Public License Version 1.1
* ("License"); You may not use this file except in compliance with the License
* The Original Code is: vtiger CRM Open Source
* The Initial Developer of the Original Code is vtiger.
* Portions created by vtiger are Copyright (C) vtiger.
* All Rights Reserved.
* ***********************************************************************************/
require_once 'include/events/VTEventHandler.inc';
class FollowRecordHandler extends VTEventHandler {
function handleEvent($eventName, $entityData) {
if ($eventName == 'vtiger.entity.aftersave') {
global $site_URL;
$db = PearDatabase::getInstance();
//current user details
$currentUserModel = Users_Record_Model::getCurrentUserModel();
$currentUserId = $currentUserModel->getId();
//record details
$recordId = $entityData->getId();
$moduleName = $entityData->getModuleName();
$restrictedModules = array('CustomerPortal', 'Dashboard', 'Emails', 'EmailTemplates', 'ExtensionStore', 'Google', 'Home',
'Import', 'MailManager', 'Mobile', 'ModComments', 'ModTracker', 'PBXManager', 'Portal',
'RecycleBin', 'Reports', 'Rss', 'SMSNotifier', 'Users', 'Webforms', 'Webmails', 'WSAPP');
if (!in_array($moduleName, $restrictedModules)) {
$tableName = Vtiger_Functions::getUserSpecificTableName($moduleName);
//following users
$userIdsList = array();
$result = $db->pquery("SELECT userid FROM $tableName WHERE recordid = ? AND starred = ? AND userid != ?", array($recordId, '1', $currentUserId));
if ($result && $db->num_rows($result)) {
while ($rowData = $db->fetch_row($result)) {
$userIdsList[] = $rowData['userid'];
}
}
if ($userIdsList) {
//changed fields data
$vtEntityDelta = new VTEntityDelta();
$delta = $vtEntityDelta->getEntityDelta($moduleName, $recordId, true);
if ($delta) {
$newEntity = $vtEntityDelta->getNewEntity($moduleName, $recordId);
$label = decode_html(trim($newEntity->get('label')));
$fieldModels = array();
$changedValues = array();
$skipFields = array('modifiedtime', 'modifiedby', 'label');
$moduleModel = Vtiger_Module_Model::getInstance($moduleName);
foreach ($delta as $fieldName => $fieldInfo) {
if (!in_array($fieldName, $skipFields)) {
$fieldModel = Vtiger_Field_Model::getInstance($fieldName, $moduleModel);
if ($fieldModel) {
$fieldModels[$fieldName] = $fieldModel;
$changedValues[$fieldName] = $fieldInfo;
}
}
}
if ($fieldModels) {
$companyDetails = getCompanyDetails();
$userModuleModel = Users_Module_Model::getInstance('Users');
foreach ($userIdsList as $userId) {
$userRecordModel = Users_Record_Model::getInstanceById($userId, $userModuleModel);
if ($userRecordModel && $userRecordModel->get('status') == 'Active') {
$changedFieldString = $this->getChangedFieldString($fieldModels, $changedValues, $userRecordModel);
$detailViewLink = "$site_URL/index.php?module=$moduleName&view=Detail&record=$recordId";
$recordDetailViewLink = '<a style="text-decoration:none;" target="_blank" href="'.$detailViewLink.'">'.$label.'</a>';
$data = vtranslate('LBL_STARRED_RECORD_UPDATED', $moduleName, $currentUserModel->getName(), $recordDetailViewLink).$changedFieldString;
$body = '<table><tbody><tr><td style="padding:10px">'.nl2br(decode_html($data)).'</td></tr></tbody></table>';
$notificationMessage = ucwords($companyDetails['companyname']).' '.vtranslate('LBL_NOTIFICATION', $moduleName).' - '.$currentUserModel->getName();
$subject = vtranslate('LBL_STARRED_RECORD_UPDATED', $moduleName, $notificationMessage, $label);
$this->sendEmail($userRecordModel->get('email1'), $subject, $body, $recordId);
}
}
}
}
}
}
}
}
public function getChangedFieldString($fieldModels, $changedValues, $userRecordModel) {
$userEntity = $userRecordModel->entity;
$changedFieldString = '';
foreach ($fieldModels as $fieldName => $fieldModel) {
$moduleName = $fieldModel->getModule()->getName();
$fieldCurrentValue = $changedValues[$fieldName]['currentValue'];
if ($fieldModel->isReferenceField()) {
$fieldDisplayValue = Vtiger_Util_Helper::getRecordName($fieldCurrentValue);
} else if ($fieldModel->isOwnerField()) {
$fieldDisplayValue = getOwnerName($fieldCurrentValue);
} else if ($fieldModel->get('uitype') == 117 && $fieldCurrentValue) {
$fieldDisplayValue = getCurrencyName($fieldCurrentValue, FALSE);
} else {
$fieldDataType = $fieldModel->getFieldDataType();
switch ($fieldDataType) {
case 'boolean' :
case 'multipicklist': $fieldDisplayValue = $fieldModel->getDisplayValue($fieldCurrentValue);break;
case 'date' : $fieldDisplayValue = DateTimeField::convertToUserFormat($fieldCurrentValue, $userEntity);break;
case 'double' : $fieldDisplayValue = CurrencyField::convertToUserFormat(decimalFormat($fieldCurrentValue), $userEntity, true);break;
case 'time' : if ($userRecordModel->get('hour_format') == '12') {
$fieldDisplayValue = Vtiger_Time_UIType::getTimeValueInAMorPM($fieldCurrentValue);
} else {
$fieldDisplayValue = $fieldModel->getEditViewDisplayValue($fieldCurrentValue);
}
break;
case 'currency' : $skipConversion = false;
if ($fieldModel->get('uitype') == 72) {
$skipConversion = true;
}
$fieldDisplayValue = CurrencyField::convertToUserFormat($fieldCurrentValue, $userEntity, $skipConversion);
break;
default : $fieldDisplayValue = $fieldModel->getEditViewDisplayValue($fieldCurrentValue);break;
}
}
$changedFieldString .= '<br/>'.vtranslate('LBL_STARRED_RECORD_TO', $moduleName, vtranslate($fieldModel->get('label'), $moduleName), $fieldDisplayValue);
}
return $changedFieldString;
}
public function sendEmail($toEmailId, $subject, $body, $recordId) {
//It will not show in CRM
$generatedMessageId = Emails_Mailer_Model::generateMessageID();
Emails_Mailer_Model::updateMessageIdByCrmId($generatedMessageId, $recordId);
$mailer = new Emails_Mailer_Model();
$mailer->reinitialize();
$mailer->Body = $body;
$mailer->Subject = decode_html($subject);
$activeUserModel = $this->getActiveUserModel();
$replyTo = decode_html($activeUserModel->email1);
$replyToName = decode_html($activeUserModel->first_name.' '.$activeUserModel->last_name);
$fromEmail = decode_html($activeUserModel->email1);
$mailer->ConfigSenderInfo($fromEmail, $replyTo, $replyToName);
$mailer->IsHTML();
$mailer->AddCustomHeader("In-Reply-To", $generatedMessageId);
$mailer->AddAddress($toEmailId);
$response = $mailer->Send(true);
}
var $activeAdmin = '';
public function getActiveUserModel() {
if (!$this->activeAdmin) {
$activeUserModel = new Users();
$activeUserModel->retrieveCurrentUserInfoFromFile(Users::getActiveAdminId());
$this->activeAdmin = $activeUserModel;
}
return $this->activeAdmin;
}
}