PageRenderTime 58ms CodeModel.GetById 27ms RepoModel.GetById 1ms app.codeStats 0ms

/modules/ServiceContracts/ServiceContracts.php

https://bitbucket.org/jhunsinfotech/blue-blues
PHP | 552 lines | 360 code | 94 blank | 98 comment | 80 complexity | 5d4817bfc234d86b399a7d9543f2a96d MD5 | raw file
Possible License(s): LGPL-2.1, GPL-2.0, LGPL-3.0
  1. <?php
  2. /*+**********************************************************************************
  3. * The contents of this file are subject to the vtiger CRM Public License Version 1.0
  4. * ("License"); You may not use this file except in compliance with the License
  5. * The Original Code is: vtiger CRM Open Source
  6. * The Initial Developer of the Original Code is vtiger.
  7. * Portions created by vtiger are Copyright (C) vtiger.
  8. * All Rights Reserved.
  9. ************************************************************************************/
  10. require_once('data/CRMEntity.php');
  11. require_once('data/Tracker.php');
  12. class ServiceContracts extends CRMEntity {
  13. var $db, $log; // Used in class functions of CRMEntity
  14. var $table_name = 'vtiger_servicecontracts';
  15. var $table_index= 'servicecontractsid';
  16. var $column_fields = Array();
  17. /** Indicator if this is a custom module or standard module */
  18. var $IsCustomModule = true;
  19. /**
  20. * Mandatory table for supporting custom fields.
  21. */
  22. var $customFieldTable = Array('vtiger_servicecontractscf', 'servicecontractsid');
  23. /**
  24. * Mandatory for Saving, Include tables related to this module.
  25. */
  26. var $tab_name = Array('vtiger_crmentity', 'vtiger_servicecontracts', 'vtiger_servicecontractscf');
  27. /**
  28. * Mandatory for Saving, Include tablename and tablekey columnname here.
  29. */
  30. var $tab_name_index = Array(
  31. 'vtiger_crmentity' => 'crmid',
  32. 'vtiger_servicecontracts' => 'servicecontractsid',
  33. 'vtiger_servicecontractscf'=>'servicecontractsid');
  34. /**
  35. * Mandatory for Listing (Related listview)
  36. */
  37. var $list_fields = Array (
  38. /* Format: Field Label => Array(tablename, columnname) */
  39. // tablename should not have prefix 'vtiger_'
  40. 'Subject' => Array('servicecontracts', 'subject'),
  41. 'Assigned To' => Array('crmentity','smownerid'),
  42. 'Contract No' => Array('servicecontracts','contract_no'),
  43. 'Used Units' => Array('servicecontracts','used_units'),
  44. 'Total Units' => Array('servicecontracts','total_units')
  45. );
  46. var $list_fields_name = Array (
  47. /* Format: Field Label => fieldname */
  48. 'Subject' => 'subject',
  49. 'Assigned To' => 'assigned_user_id',
  50. 'Contract No' => 'contract_no',
  51. 'Used Units' => 'used_units',
  52. 'Total Units' => 'total_units'
  53. );
  54. // Make the field link to detail view
  55. var $list_link_field = 'subject';
  56. // For Popup listview and UI type support
  57. var $search_fields = Array(
  58. /* Format: Field Label => Array(tablename, columnname) */
  59. // tablename should not have prefix 'vtiger_'
  60. 'Subject' => Array('servicecontracts', 'subject'),
  61. 'Contract No' => Array('servicecontracts', 'contract_no'),
  62. 'Assigned To' => Array('vtiger_crmentity','assigned_user_id'),
  63. 'Used Units' => Array('servicecontracts','used_units'),
  64. 'Total Units' => Array('servicecontracts','total_units')
  65. );
  66. var $search_fields_name = Array (
  67. /* Format: Field Label => fieldname */
  68. 'Subject' => 'subject',
  69. 'Contract No' => 'contract_no',
  70. 'Assigned To' => 'assigned_user_id',
  71. 'Used Units' => 'used_units',
  72. 'Total Units' => 'total_units'
  73. );
  74. // For Popup window record selection
  75. var $popup_fields = Array ('subject');
  76. // Placeholder for sort fields - All the fields will be initialized for Sorting through initSortFields
  77. var $sortby_fields = Array();
  78. // For Alphabetical search
  79. var $def_basicsearch_col = 'subject';
  80. // Column value to use on detail view record text display
  81. var $def_detailview_recname = 'subject';
  82. // Required Information for enabling Import feature
  83. var $required_fields = Array ('assigned_user_id'=>1);
  84. // Used when enabling/disabling the mandatory fields for the module.
  85. // Refers to vtiger_field.fieldname values.
  86. var $mandatory_fields = Array('subject','assigned_user_id');
  87. // Callback function list during Importing
  88. var $special_functions = Array('set_import_assigned_user');
  89. var $default_order_by = 'subject';
  90. var $default_sort_order='ASC';
  91. function __construct() {
  92. global $log;
  93. $this->column_fields = getColumnFields('ServiceContracts');
  94. $this->db = new PearDatabase();
  95. $this->log = $log;
  96. }
  97. function save_module($module) {
  98. $return_action = $_REQUEST['return_action'];
  99. $for_module = $_REQUEST['return_module'];
  100. $for_crmid = $_REQUEST['return_id'];
  101. if ($return_action && $for_module && $for_crmid) {
  102. if ($for_module == 'HelpDesk') {
  103. $on_focus = CRMEntity::getInstance($for_module);
  104. $on_focus->save_related_module($for_module, $for_crmid, $module, $this->id);
  105. }
  106. }
  107. }
  108. /**
  109. * Return query to use based on given modulename, fieldname
  110. * Useful to handle specific case handling for Popup
  111. */
  112. function getQueryByModuleField($module, $fieldname, $srcrecord) {
  113. // $srcrecord could be empty
  114. }
  115. /**
  116. * Get list view query.
  117. */
  118. function getListQuery($module, $where='') {
  119. $query = "SELECT vtiger_crmentity.*, $this->table_name.*";
  120. // Select Custom Field Table Columns if present
  121. if(!empty($this->customFieldTable)) $query .= ", " . $this->customFieldTable[0] . ".* ";
  122. $query .= " FROM $this->table_name";
  123. $query .= " INNER JOIN vtiger_crmentity ON vtiger_crmentity.crmid = $this->table_name.$this->table_index";
  124. // Consider custom table join as well.
  125. if(!empty($this->customFieldTable)) {
  126. $query .= " INNER JOIN ".$this->customFieldTable[0]." ON ".$this->customFieldTable[0].'.'.$this->customFieldTable[1] .
  127. " = $this->table_name.$this->table_index";
  128. }
  129. $query .= " LEFT JOIN vtiger_users ON vtiger_users.id = vtiger_crmentity.smownerid";
  130. $query .= " LEFT JOIN vtiger_groups ON vtiger_groups.groupid = vtiger_crmentity.smownerid";
  131. $linkedModulesQuery = $this->db->pquery("SELECT distinct fieldname, columnname, relmodule FROM vtiger_field" .
  132. " INNER JOIN vtiger_fieldmodulerel ON vtiger_fieldmodulerel.fieldid = vtiger_field.fieldid" .
  133. " WHERE uitype='10' AND vtiger_fieldmodulerel.module=?", array($module));
  134. $linkedFieldsCount = $this->db->num_rows($linkedModulesQuery);
  135. for($i=0; $i<$linkedFieldsCount; $i++) {
  136. $related_module = $this->db->query_result($linkedModulesQuery, $i, 'relmodule');
  137. $fieldname = $this->db->query_result($linkedModulesQuery, $i, 'fieldname');
  138. $columnname = $this->db->query_result($linkedModulesQuery, $i, 'columnname');
  139. $other = CRMEntity::getInstance($related_module);
  140. vtlib_setup_modulevars($related_module, $other);
  141. $query .= " LEFT JOIN $other->table_name ON $other->table_name.$other->table_index =".
  142. "$this->table_name.$columnname";
  143. }
  144. global $current_user;
  145. $query .= $this->getNonAdminAccessControlQuery($module,$current_user);
  146. $query .= "WHERE vtiger_crmentity.deleted = 0 ".$where;
  147. return $query;
  148. }
  149. /**
  150. * Apply security restriction (sharing privilege) query part for List view.
  151. */
  152. function getListViewSecurityParameter($module) {
  153. global $current_user;
  154. require('user_privileges/user_privileges_'.$current_user->id.'.php');
  155. require('user_privileges/sharing_privileges_'.$current_user->id.'.php');
  156. $sec_query = '';
  157. $tabid = getTabid($module);
  158. if($is_admin==false && $profileGlobalPermission[1] == 1 && $profileGlobalPermission[2] == 1
  159. && $defaultOrgSharingPermission[$tabid] == 3) {
  160. $sec_query .= " AND (vtiger_crmentity.smownerid in($current_user->id) OR vtiger_crmentity.smownerid IN
  161. (
  162. SELECT vtiger_user2role.userid FROM vtiger_user2role
  163. INNER JOIN vtiger_users ON vtiger_users.id=vtiger_user2role.userid
  164. INNER JOIN vtiger_role ON vtiger_role.roleid=vtiger_user2role.roleid
  165. WHERE vtiger_role.parentrole LIKE '".$current_user_parent_role_seq."::%'
  166. )
  167. OR vtiger_crmentity.smownerid IN
  168. (
  169. SELECT shareduserid FROM vtiger_tmp_read_user_sharing_per
  170. WHERE userid=".$current_user->id." AND tabid=".$tabid."
  171. )
  172. OR
  173. (";
  174. // Build the query based on the group association of current user.
  175. if(sizeof($current_user_groups) > 0) {
  176. $sec_query .= " vtiger_groups.groupid IN (". implode(",", $current_user_groups) .") OR ";
  177. }
  178. $sec_query .= " vtiger_groups.groupid IN
  179. (
  180. SELECT vtiger_tmp_read_group_sharing_per.sharedgroupid
  181. FROM vtiger_tmp_read_group_sharing_per
  182. WHERE userid=".$current_user->id." and tabid=".$tabid."
  183. )";
  184. $sec_query .= ")
  185. )";
  186. }
  187. return $sec_query;
  188. }
  189. /**
  190. * Create query to export the records.
  191. */
  192. function create_export_query($where)
  193. {
  194. global $current_user,$currentModule;
  195. $thismodule = $_REQUEST['module'];
  196. include("include/utils/ExportUtils.php");
  197. //To get the Permitted fields query and the permitted fields list
  198. $sql = getPermittedFieldsQuery($thismodule, "detail_view");
  199. $fields_list = getFieldsListFromQuery($sql);
  200. $query = "SELECT $fields_list, vtiger_users.user_name AS user_name
  201. FROM vtiger_crmentity INNER JOIN $this->table_name ON vtiger_crmentity.crmid=$this->table_name.$this->table_index";
  202. if(!empty($this->customFieldTable)) {
  203. $query .= " INNER JOIN ".$this->customFieldTable[0]." ON ".$this->customFieldTable[0].'.'.$this->customFieldTable[1] .
  204. " = $this->table_name.$this->table_index";
  205. }
  206. $query .= " LEFT JOIN vtiger_groups ON vtiger_groups.groupid = vtiger_crmentity.smownerid";
  207. $query .= " LEFT JOIN vtiger_users ON vtiger_crmentity.smownerid = vtiger_users.id and ".
  208. "vtiger_users.status='Active'";
  209. $linkedModulesQuery = $this->db->pquery("SELECT distinct fieldname, columnname, relmodule FROM vtiger_field" .
  210. " INNER JOIN vtiger_fieldmodulerel ON vtiger_fieldmodulerel.fieldid = vtiger_field.fieldid" .
  211. " WHERE uitype='10' AND vtiger_fieldmodulerel.module=?", array($thismodule));
  212. $linkedFieldsCount = $this->db->num_rows($linkedModulesQuery);
  213. for($i=0; $i<$linkedFieldsCount; $i++) {
  214. $related_module = $this->db->query_result($linkedModulesQuery, $i, 'relmodule');
  215. $fieldname = $this->db->query_result($linkedModulesQuery, $i, 'fieldname');
  216. $columnname = $this->db->query_result($linkedModulesQuery, $i, 'columnname');
  217. $other = CRMEntity::getInstance($related_module);
  218. vtlib_setup_modulevars($related_module, $other);
  219. $query .= " LEFT JOIN $other->table_name ON $other->table_name.$other->table_index = ".
  220. "$this->table_name.$columnname";
  221. }
  222. $query .= $this->getNonAdminAccessControlQuery($thismodule,$current_user);
  223. $where_auto = " vtiger_crmentity.deleted=0";
  224. if($where != '') $query .= " WHERE ($where) AND $where_auto";
  225. else $query .= " WHERE $where_auto";
  226. return $query;
  227. }
  228. /**
  229. * Function which will give the basic query to find duplicates
  230. */
  231. function getDuplicatesQuery($module,$table_cols,$field_values,$ui_type_arr,$select_cols='') {
  232. $select_clause = "SELECT ". $this->table_name .".".$this->table_index ." AS recordid, vtiger_users_last_import.deleted,".$table_cols;
  233. // Select Custom Field Table Columns if present
  234. if(isset($this->customFieldTable)) $query .= ", " . $this->customFieldTable[0] . ".* ";
  235. $from_clause = " FROM $this->table_name";
  236. $from_clause .= " INNER JOIN vtiger_crmentity ON vtiger_crmentity.crmid = $this->table_name.$this->table_index";
  237. // Consider custom table join as well.
  238. if(isset($this->customFieldTable)) {
  239. $from_clause .= " INNER JOIN ".$this->customFieldTable[0]." ON ".$this->customFieldTable[0].'.'.$this->customFieldTable[1] .
  240. " = $this->table_name.$this->table_index";
  241. }
  242. $from_clause .= " LEFT JOIN vtiger_users ON vtiger_users.id = vtiger_crmentity.smownerid
  243. LEFT JOIN vtiger_groups ON vtiger_groups.groupid = vtiger_crmentity.smownerid";
  244. $where_clause = " WHERE vtiger_crmentity.deleted = 0";
  245. $where_clause .= $this->getListViewSecurityParameter($module);
  246. if (isset($select_cols) && trim($select_cols) != '') {
  247. $sub_query = "SELECT $select_cols FROM $this->table_name AS t " .
  248. " INNER JOIN vtiger_crmentity AS crm ON crm.crmid = t.".$this->table_index;
  249. // Consider custom table join as well.
  250. if(isset($this->customFieldTable)) {
  251. $sub_query .= " INNER JOIN ".$this->customFieldTable[0]." tcf ON tcf.".$this->customFieldTable[1]." = t.$this->table_index";
  252. }
  253. $sub_query .= " WHERE crm.deleted=0 GROUP BY $select_cols HAVING COUNT(*)>1";
  254. } else {
  255. $sub_query = "SELECT $table_cols $from_clause $where_clause GROUP BY $table_cols HAVING COUNT(*)>1";
  256. }
  257. $query = $select_clause . $from_clause .
  258. " LEFT JOIN vtiger_users_last_import ON vtiger_users_last_import.bean_id=" . $this->table_name .".".$this->table_index .
  259. " INNER JOIN (" . $sub_query . ") AS temp ON ".get_on_clause($field_values,$ui_type_arr,$module) .
  260. $where_clause .
  261. " ORDER BY $table_cols,". $this->table_name .".".$this->table_index ." ASC";
  262. return $query;
  263. }
  264. /**
  265. * Invoked when special actions are performed on the module.
  266. * @param String Module name
  267. * @param String Event Type
  268. */
  269. function vtlib_handler($moduleName, $eventType) {
  270. require_once('include/utils/utils.php');
  271. global $adb;
  272. if($eventType == 'module.postinstall') {
  273. require_once('vtlib/Vtiger/Module.php');
  274. $moduleInstance = Vtiger_Module::getInstance($moduleName);
  275. $accModuleInstance = Vtiger_Module::getInstance('Accounts');
  276. $accModuleInstance->setRelatedList($moduleInstance,'Service Contracts',array('add'),'get_dependents_list');
  277. $conModuleInstance = Vtiger_Module::getInstance('Contacts');
  278. $conModuleInstance->setRelatedList($moduleInstance,'Service Contracts',array('add'),'get_dependents_list');
  279. $helpDeskInstance = Vtiger_Module::getInstance("HelpDesk");
  280. $helpDeskInstance->setRelatedList($moduleInstance,"Service Contracts",Array('ADD','SELECT'));
  281. // Initialize module sequence for the module
  282. $adb->pquery("INSERT into vtiger_modentity_num values(?,?,?,?,?,?)",array($adb->getUniqueId("vtiger_modentity_num"),$moduleName,'SERCON',1,1,1));
  283. // Make the picklist value 'Complete' for status as non-editable
  284. $adb->query("UPDATE vtiger_contract_status SET presence=0 WHERE contract_status='Complete'");
  285. // Mark the module as Standard module
  286. $adb->pquery('UPDATE vtiger_tab SET customized=0 WHERE name=?', array($moduleName));
  287. } else if($eventType == 'module.disabled') {
  288. $em = new VTEventsManager($adb);
  289. $em->setHandlerInActive('ServiceContractsHandler');
  290. } else if($eventType == 'module.enabled') {
  291. $em = new VTEventsManager($adb);
  292. $em->setHandlerActive('ServiceContractsHandler');
  293. } else if($eventType == 'module.preuninstall') {
  294. // TODO Handle actions when this module is about to be deleted.
  295. } else if($eventType == 'module.preupdate') {
  296. // TODO Handle actions before this module is updated.
  297. } else if($eventType == 'module.postupdate') {
  298. // TODO Handle actions after this module is updated.
  299. }
  300. }
  301. /**
  302. * Handle saving related module information.
  303. * NOTE: This function has been added to CRMEntity (base class).
  304. * You can override the behavior by re-defining it here.
  305. */
  306. function save_related_module($module, $crmid, $with_module, $with_crmids) {
  307. if(!is_array($with_crmids)) $with_crmids = Array($with_crmids);
  308. foreach($with_crmids as $with_crmid) {
  309. parent::save_related_module($module, $crmid, $with_module, $with_crmid);
  310. if ($with_module == 'HelpDesk') {
  311. $this->updateHelpDeskRelatedTo($crmid,$with_crmid);
  312. $this->updateServiceContractState($crmid);
  313. }
  314. }
  315. }
  316. // Function to Update the parent_id of HelpDesk with sc_related_to of ServiceContracts if the parent_id is not set.
  317. function updateHelpDeskRelatedTo($focusId, $entityIds) {
  318. global $log;
  319. $log->debug("Entering into function updateHelpDeskRelatedTo(".$entityIds.").");
  320. if(!is_array($entityIds)) $entityIds = array($entityIds);
  321. $selectTicketsQuery = "SELECT ticketid FROM vtiger_troubletickets WHERE (parent_id IS NULL OR parent_id = 0) AND ticketid IN (" . generateQuestionMarks($entityIds) .")";
  322. $selectTicketsResult = $this->db->pquery($selectTicketsQuery, array($entityIds));
  323. $noOfTickets = $this->db->num_rows($selectTicketsResult);
  324. for($i=0; $i < $noOfTickets; ++$i) {
  325. $ticketId = $this->db->query_result($selectTicketsResult,$i,'ticketid');
  326. $updateQuery = "UPDATE vtiger_troubletickets, vtiger_servicecontracts SET parent_id=vtiger_servicecontracts.sc_related_to" .
  327. " WHERE vtiger_servicecontracts.sc_related_to IS NOT NULL AND vtiger_servicecontracts.sc_related_to != 0" .
  328. " AND vtiger_servicecontracts.servicecontractsid = ? AND vtiger_troubletickets.ticketid = ?";
  329. $updateResult = $this->db->pquery($updateQuery, array($focusId, $ticketId));
  330. }
  331. $log->debug("Exit from function updateHelpDeskRelatedTo(".$entityIds.")");
  332. }
  333. // Function to Compute and Update the Used Units and Progress of the Service Contract based on all the related Trouble tickets.
  334. function updateServiceContractState($focusId) {
  335. $this->id = $focusId;
  336. $this->retrieve_entity_info($focusId,'ServiceContracts');
  337. $contractTicketsResult = $this->db->pquery("SELECT relcrmid FROM vtiger_crmentityrel
  338. WHERE module = 'ServiceContracts'
  339. AND relmodule = 'HelpDesk' AND crmid = ?
  340. UNION
  341. SELECT crmid FROM vtiger_crmentityrel
  342. WHERE relmodule = 'ServiceContracts'
  343. AND module = 'HelpDesk' AND relcrmid = ?",
  344. array($focusId,$focusId));
  345. $noOfTickets = $this->db->num_rows($contractTicketsResult);
  346. $ticketFocus = CRMEntity::getInstance('HelpDesk');
  347. $totalUsedUnits = 0;
  348. for($i=0; $i < $noOfTickets; ++$i) {
  349. $ticketId = $this->db->query_result($contractTicketsResult, $i, 'relcrmid');
  350. $ticketFocus->id = $ticketId;
  351. if(isRecordExists($ticketId)) {
  352. $ticketFocus->retrieve_entity_info($ticketId, 'HelpDesk');
  353. if (strtolower($ticketFocus->column_fields['ticketstatus']) == 'closed') {
  354. $totalUsedUnits += $this->computeUsedUnits($ticketFocus->column_fields);
  355. }
  356. }
  357. }
  358. $this->updateUsedUnits($totalUsedUnits);
  359. $this->calculateProgress();
  360. }
  361. // Function to Upate the Used Units of the Service Contract based on the given Ticket id.
  362. function computeUsedUnits($ticketData, $operator='+') {
  363. $trackingUnit = strtolower($this->column_fields['tracking_unit']);
  364. $workingHoursPerDay = 24;
  365. $usedUnits = 0;
  366. if ($trackingUnit == 'incidents') {
  367. $usedUnits = 1;
  368. } elseif ($trackingUnit == 'days') {
  369. if(!empty($ticketData['days'])) {
  370. $usedUnits = $ticketData['days'];
  371. } elseif(!empty($ticketData['hours'])) {
  372. $usedUnits = $ticketData['hours'] / $workingHoursPerDay;
  373. }
  374. } elseif ($trackingUnit == 'hours') {
  375. if(!empty($ticketData['hours'])) {
  376. $usedUnits = $ticketData['hours'];
  377. } elseif(!empty($ticketData['days'])) {
  378. $usedUnits = $ticketData['days'] * $workingHoursPerDay;
  379. }
  380. }
  381. return $usedUnits;
  382. }
  383. // Function to Upate the Used Units of the Service Contract.
  384. function updateUsedUnits($usedUnits) {
  385. $this->column_fields['used_units'] = $usedUnits;
  386. $updateQuery = "UPDATE vtiger_servicecontracts SET used_units = $usedUnits WHERE servicecontractsid = ?";
  387. $this->db->pquery($updateQuery, array($this->id));
  388. }
  389. // Function to Calculate the End Date, Planned Duration, Actual Duration and Progress of a Service Contract
  390. function calculateProgress() {
  391. $updateCols = array();
  392. $updateParams = array();
  393. $startDate = $this->column_fields['start_date'];
  394. $dueDate = $this->column_fields['due_date'];
  395. $endDate = $this->column_fields['end_date'];
  396. $usedUnits = $this->column_fields['used_units'];
  397. $totalUnits = $this->column_fields['total_units'];
  398. $contractStatus = $this->column_fields['contract_status'];
  399. // Update the End date if the status is Complete or if the Used Units reaches/exceeds Total Units
  400. // We need to do this first to make sure Actual duration is computed properly
  401. if($contractStatus == 'Complete' || (!empty($usedUnits) && !empty($totalUnits) && $usedUnits >= $totalUnits)) {
  402. if(empty($endDate)) {
  403. $endDate = date('Y-m-d');
  404. $this->db->pquery('UPDATE vtiger_servicecontracts SET end_date=? WHERE servicecontractsid = ?', array(date('Y-m-d'), $this->id));
  405. }
  406. } else {
  407. $endDate = null;
  408. $this->db->pquery('UPDATE vtiger_servicecontracts SET end_date=? WHERE servicecontractsid = ?', array(null, $this->id));
  409. }
  410. // Calculate the Planned Duration based on Due date and Start date. (in days)
  411. if(!empty($dueDate) && !empty($startDate)) {
  412. $plannedDurationUpdate = " planned_duration = (TO_DAYS(due_date)-TO_DAYS(start_date)+1)";
  413. } else {
  414. $plannedDurationUpdate = " planned_duration = ''";
  415. }
  416. array_push($updateCols, $plannedDurationUpdate);
  417. // Calculate the Actual Duration based on End date and Start date. (in days)
  418. if(!empty($endDate) && !empty($startDate)) {
  419. $actualDurationUpdate = "actual_duration = (TO_DAYS(end_date)-TO_DAYS(start_date)+1)";
  420. } else {
  421. $actualDurationUpdate = "actual_duration = ''";
  422. }
  423. array_push($updateCols, $actualDurationUpdate);
  424. // Update the Progress based on Used Units and Total Units (in percentage)
  425. if(!empty($usedUnits) && !empty($totalUnits)) {
  426. $progressUpdate = 'progress = ?';
  427. $progressUpdateParams = floatval(($usedUnits * 100) / $totalUnits);
  428. } else {
  429. $progressUpdate = 'progress = ?';
  430. $progressUpdateParams = null;
  431. }
  432. array_push($updateCols, $progressUpdate);
  433. array_push($updateParams, $progressUpdateParams);
  434. if(count($updateCols) > 0) {
  435. $updateQuery = 'UPDATE vtiger_servicecontracts SET '. implode(",", $updateCols) .' WHERE servicecontractsid = ?';
  436. array_push($updateParams, $this->id);
  437. $this->db->pquery($updateQuery, $updateParams);
  438. }
  439. }
  440. /**
  441. * Handle deleting related module information.
  442. * NOTE: This function has been added to CRMEntity (base class).
  443. * You can override the behavior by re-defining it here.
  444. */
  445. function delete_related_module($module, $crmid, $with_module, $with_crmid) {
  446. parent::delete_related_module($module, $crmid, $with_module, $with_crmid);
  447. if ($with_module == 'HelpDesk') {
  448. $this->updateServiceContractState($crmid);
  449. }
  450. }
  451. /**
  452. * Handle getting related list information.
  453. * NOTE: This function has been added to CRMEntity (base class).
  454. * You can override the behavior by re-defining it here.
  455. */
  456. //function get_related_list($id, $cur_tab_id, $rel_tab_id, $actions=false) { }
  457. }
  458. ?>