Passed
Pull Request — developer (#15936)
by Arkadiusz
16:10
created

Home_Module_Model   B

Complexity

Total Complexity 52

Size/Duplication

Total Lines 273
Duplicated Lines 0 %

Test Coverage

Coverage 1.22%

Importance

Changes 1
Bugs 0 Features 0
Metric Value
wmc 52
eloc 162
dl 0
loc 273
ccs 2
cts 164
cp 0.0122
rs 7.44
c 1
b 0
f 0

6 Methods

Rating   Name   Duplication   Size   Complexity  
A getDefaultViewName() 0 3 1
A getActivityQuery() 0 4 2
A getComments() 0 26 3
C getHistory() 0 56 12
F getCalendarActivities() 0 72 21
C getAssignedProjectsTasks() 0 52 13

How to fix   Complexity   

Complex Class

Complex classes like Home_Module_Model often do a lot of different things. To break such a class down, we need to identify a cohesive component within that class. A common approach to find such a component is to look for fields/methods that share the same prefixes, or suffixes.

Once you have determined the fields that belong together, you can apply the Extract Class refactoring. If the component makes sense as a sub-class, Extract Subclass is also a candidate, and is often faster.

While breaking up the class, it is a good idea to analyze how other classes use Home_Module_Model, and based on these observations, apply Extract Interface, too.

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
 * Contributor(s): YetiForce S.A.
10
 * *********************************************************************************** */
11
12
class Home_Module_Model extends Vtiger_Module_Model
13
{
14
	/**
15
	 * Function returns the default view for the Home module.
16
	 *
17
	 * @return string
18
	 */
19 2
	public function getDefaultViewName()
20
	{
21 2
		return 'DashBoard';
22
	}
23
24
	/**
25
	 * Function returns latest comments across CRM.
26
	 *
27
	 * @param \Vtiger_Paging_Model $pagingModel
28
	 *
29
	 * @return \Vtiger_Record_Model[]
30
	 */
31
	public function getComments($pagingModel)
32
	{
33
		$query = new \App\Db\Query();
34
		$query->select(['*', 'createdtime' => 'vtiger_crmentity.createdtime', 'assigned_user_id' => 'vtiger_crmentity.smownerid',
35
			'parentId' => 'crmentity2.crmid', 'parentModule' => 'crmentity2.setype', ])
36
			->from('vtiger_modcomments')
37
			->innerJoin('vtiger_crmentity', 'vtiger_modcomments.modcommentsid = vtiger_crmentity.crmid')
38
			->innerJoin('vtiger_crmentity crmentity2', 'vtiger_modcomments.related_to = crmentity2.crmid')
39
			->where(['vtiger_crmentity.deleted' => 0, 'crmentity2.deleted' => 0]);
40
		\App\PrivilegeQuery::getConditions($query, 'ModComments');
41
		$query->orderBy(['vtiger_modcomments.modcommentsid' => SORT_DESC])
42
			->limit($pagingModel->getPageLimit())
43
			->offset($pagingModel->getStartIndex());
44
		$dataReader = $query->createCommand()->query();
45
		$comments = [];
46
		while ($row = $dataReader->read()) {
47
			if (\App\Privilege::isPermitted($row['setype'], 'DetailView', $row['related_to'])) {
48
				$commentModel = Vtiger_Record_Model::getCleanInstance('ModComments');
49
				$commentModel->setData($row);
50
				$time = $commentModel->get('createdtime');
51
				$comments[$time] = $commentModel;
52
			}
53
		}
54
		$dataReader->close();
55
56
		return $comments;
57
	}
58
59
	/**
60
	 * Function returns part of the query to  fetch only  activity.
61
	 *
62
	 * @param \App\Db\Query $query
63
	 * @param string        $type
64
	 */
65
	public function getActivityQuery(App\Db\Query $query, $type)
66
	{
67
		if ('updates' == $type) {
68
			$query->andWhere(['<>', 'module', 'ModComments']);
69
		}
70
	}
71
72
	/**
73
	 * Function returns the Calendar Events for the module.
74
	 *
75
	 * @param string              $mode        - upcoming/overdue mode
76
	 * @param Vtiger_Paging_Model $pagingModel - $pagingModel
77
	 * @param string              $user        - all/userid
78
	 * @param string              $recordId    - record id
79
	 * @param mixed               $paramsMore
80
	 *
81
	 * @return array
82
	 */
83
	public function getCalendarActivities($mode, Vtiger_Paging_Model $pagingModel, $user, $recordId = false, $paramsMore = [])
0 ignored issues
show
Unused Code introduced by
The parameter $recordId is not used and could be removed. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-unused  annotation

83
	public function getCalendarActivities($mode, Vtiger_Paging_Model $pagingModel, $user, /** @scrutinizer ignore-unused */ $recordId = false, $paramsMore = [])

This check looks for parameters that have been defined for a function or method, but which are not used in the method body.

Loading history...
84
	{
85
		$activities = [];
86
		$query = new \App\Db\Query();
87
		if (!$user) {
88
			$user = \App\User::getCurrentUserId();
89
		}
90
		$query->select(['vtiger_crmentity.crmid', 'vtiger_crmentity.smownerid', 'vtiger_crmentity.setype', 'vtiger_activity.*'])
91
			->from('vtiger_activity')
92
			->innerJoin('vtiger_crmentity', 'vtiger_crmentity.crmid = vtiger_activity.activityid')
93
			->where(['vtiger_crmentity.deleted' => 0]);
94
		\App\PrivilegeQuery::getConditions($query, 'Calendar');
95
		if ('upcoming' === $mode || 'overdue' === $mode) {
96
			$query->andWhere(['or', ['vtiger_activity.status' => null], ['vtiger_activity.status' => $paramsMore['status']]]);
97
		} elseif ('createdByMeButNotMine' === $mode || 'createdByMeButNotMineOverdue' === $mode) {
98
			$query->andWhere(['or', ['vtiger_activity.status' => null], ['vtiger_activity.status' => $paramsMore['status']]]);
99
			$query->andWhere(['and', ['vtiger_crmentity.smcreatorid' => $paramsMore['user']], ['NOT IN', 'vtiger_crmentity.smownerid', $paramsMore['user']]]);
100
		}
101
		if (isset($paramsMore['activitytype'])) {
102
			$query->andWhere(['vtiger_activity.activitytype' => $paramsMore['activitytype']]);
103
		}
104
		if ('all' !== $user && !empty($user)) {
105
			$userId = (int) $user;
106
			if (\App\User::isExists($userId)) {
107
				$userModel = \App\User::getUserModel($userId);
108
				$userAndGroups = $userModel->getGroups();
109
			}
110
			$userAndGroups[] = $userId;
111
			$subQuery = (new \App\Db\Query())->select(['crmid'])->from('u_#__crmentity_showners')->innerJoin('vtiger_activity', 'u_#__crmentity_showners.crmid=vtiger_activity.activityid')->where(['userid' => $userAndGroups])->distinct('crmid');
0 ignored issues
show
Bug introduced by
'crmid' of type string is incompatible with the type boolean expected by parameter $value of yii\db\Query::distinct(). ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

111
			$subQuery = (new \App\Db\Query())->select(['crmid'])->from('u_#__crmentity_showners')->innerJoin('vtiger_activity', 'u_#__crmentity_showners.crmid=vtiger_activity.activityid')->where(['userid' => $userAndGroups])->distinct(/** @scrutinizer ignore-type */ 'crmid');
Loading history...
112
			$query->andWhere(['or', ['vtiger_crmentity.smownerid' => $userAndGroups], ['vtiger_crmentity.crmid' => $subQuery]]);
113
		}
114
115
		$query->orderBy($pagingModel->get('orderby'))
116
			->limit($pagingModel->getPageLimit() + 1)
117
			->offset($pagingModel->getStartIndex());
118
		$dataReader = $query->createCommand()->query();
119
		while ($row = $dataReader->read()) {
120
			$model = Vtiger_Record_Model::getCleanInstance('Calendar');
121
			$model->setData($row);
122
			$model->setId($row['crmid']);
123
			if (!empty($row['parent_id']) && \App\Record::isExists($row['parent_id'])) {
124
				$record = Vtiger_Record_Model::getInstanceById($row['parent_id']);
125
				if ('Accounts' === $record->getModuleName()) {
126
					$model->set('contractor', $record);
127
				} elseif ('Project' === $record->getModuleName()) {
128
					if (\App\Record::isExists($record->get('linktoaccountscontacts'))) {
129
						$recordContractor = Vtiger_Record_Model::getInstanceById($record->get('linktoaccountscontacts'));
130
						$model->set('contractor', $recordContractor);
131
					}
132
				} elseif ('ServiceContracts' === $record->getModuleName()) {
133
					if (\App\Record::isExists($record->get('sc_realted_to'))) {
134
						$recordContractor = Vtiger_Record_Model::getInstanceById($record->get('sc_realted_to'));
135
						$model->set('contractor', $recordContractor);
136
					}
137
				} elseif ('HelpDesk' === $record->getModuleName()) {
138
					if (\App\Record::isExists($record->get('parent_id'))) {
139
						$recordContractor = Vtiger_Record_Model::getInstanceById($record->get('parent_id'));
140
						$model->set('contractor', $recordContractor);
141
					}
142
				}
143
			}
144
			$activities[] = $model;
145
		}
146
		$pagingModel->calculatePageRange($dataReader->count());
147
		if ($dataReader->count() > $pagingModel->getPageLimit()) {
148
			array_pop($activities);
149
			$pagingModel->set('nextPageExists', true);
150
		} else {
151
			$pagingModel->set('nextPageExists', false);
152
		}
153
		$dataReader->close();
154
		return $activities;
155
	}
156
157
	/**
158
	 * Function returns the Calendar Events for the module.
159
	 *
160
	 * @param string                $mode        - upcoming/overdue mode
161
	 * @param <Vtiger_Paging_Model> $pagingModel - $pagingModel
0 ignored issues
show
Documentation Bug introduced by
The doc comment <Vtiger_Paging_Model> at position 0 could not be parsed: Unknown type name '<' at position 0 in <Vtiger_Paging_Model>.
Loading history...
162
	 * @param string                $user        - all/userid
163
	 * @param string                $recordId    - record id
164
	 *
165
	 * @return <Array>
0 ignored issues
show
Documentation Bug introduced by
The doc comment <Array> at position 0 could not be parsed: Unknown type name '<' at position 0 in <Array>.
Loading history...
166
	 */
167
	public function getAssignedProjectsTasks($mode, $pagingModel, $user, $recordId = false)
0 ignored issues
show
Unused Code introduced by
The parameter $recordId is not used and could be removed. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-unused  annotation

167
	public function getAssignedProjectsTasks($mode, $pagingModel, $user, /** @scrutinizer ignore-unused */ $recordId = false)

This check looks for parameters that have been defined for a function or method, but which are not used in the method body.

Loading history...
168
	{
169
		$currentUser = Users_Record_Model::getCurrentUserModel();
170
		if (!$user) {
171
			$user = $currentUser->getId();
172
		}
173
		$nowInUserFormat = App\Fields\DateTime::formatToDisplay(date('Y-m-d H:i:s'));
174
		$nowInDBFormat = App\Fields\DateTime::formatToDb($nowInUserFormat);
175
		[$currentDate] = explode(' ', $nowInDBFormat);
176
		$query = (new App\Db\Query())
177
			->select(['vtiger_crmentity.crmid', 'vtiger_crmentity.smownerid', 'vtiger_crmentity.setype', 'vtiger_projecttask.*'])
178
			->from('vtiger_projecttask')
179
			->innerJoin('vtiger_crmentity', 'vtiger_crmentity.crmid = vtiger_projecttask.projecttaskid')
180
			->where(['vtiger_crmentity.deleted' => 0, 'vtiger_crmentity.smcreatorid' => $currentUser->getId()]);
181
		\App\PrivilegeQuery::getConditions($query, 'ProjectTask');
182
		if ('upcoming' === $mode) {
183
			$query->andWhere(['>=', 'targetenddate', $currentDate]);
184
		} elseif ('overdue' === $mode) {
185
			$query->andWhere(['<', 'targetenddate', $currentDate]);
186
		}
187
		$accessibleUsers = \App\Fields\Owner::getInstance(false, $currentUser)->getAccessibleUsers();
0 ignored issues
show
Bug introduced by
false of type false is incompatible with the type string expected by parameter $moduleName of App\Fields\Owner::getInstance(). ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

187
		$accessibleUsers = \App\Fields\Owner::getInstance(/** @scrutinizer ignore-type */ false, $currentUser)->getAccessibleUsers();
Loading history...
188
		$accessibleGroups = \App\Fields\Owner::getInstance(false, $currentUser)->getAccessibleGroups();
189
		if ('all' != $user && '' != $user && (\array_key_exists($user, $accessibleUsers) || \array_key_exists($user, $accessibleGroups))) {
190
			$query->andWhere(['vtiger_crmentity.smownerid' => $user]);
191
		}
192
		$query->orderBy('targetenddate')
193
			->limit($pagingModel->getPageLimit() + 1)
194
			->offset($pagingModel->getStartIndex());
195
		$dataReader = $query->createCommand()->query();
196
		$projecttasks = [];
197
		while ($row = $dataReader->read()) {
198
			$model = Vtiger_Record_Model::getCleanInstance('ProjectTask');
199
			$model->setData($row);
200
			$model->setId($row['crmid']);
201
			if ($row['projectid'] && \App\Record::isExists($row['projectid'])) {
202
				$record = Vtiger_Record_Model::getInstanceById($row['projectid'], 'Project');
203
				if (\App\Record::isExists($record->get('linktoaccountscontacts'))) {
204
					$model->set('account', '<a href="index.php?module=' . \App\Record::getType($record->get('linktoaccountscontacts')) . '&view=Detail&record=' . $record->get('linktoaccountscontacts') . '">' . vtlib\Functions::getCRMRecordLabel($record->get('linktoaccountscontacts')) . '</a>');
0 ignored issues
show
Bug introduced by
Are you sure vtlib\Functions::getCRMR...nktoaccountscontacts')) of type array|mixed|string can be used in concatenation? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

204
					$model->set('account', '<a href="index.php?module=' . \App\Record::getType($record->get('linktoaccountscontacts')) . '&view=Detail&record=' . $record->get('linktoaccountscontacts') . '">' . /** @scrutinizer ignore-type */ vtlib\Functions::getCRMRecordLabel($record->get('linktoaccountscontacts')) . '</a>');
Loading history...
205
				}
206
			}
207
			$projecttasks[] = $model;
208
		}
209
		$pagingModel->calculatePageRange($dataReader->count());
210
		if ($dataReader->count() > $pagingModel->getPageLimit()) {
211
			array_pop($projecttasks);
212
			$pagingModel->set('nextPageExists', true);
213
		} else {
214
			$pagingModel->set('nextPageExists', false);
215
		}
216
		$dataReader->close();
217
218
		return $projecttasks;
219
	}
220
221
	/**
222
	 * Function returns comments and recent activities across module.
223
	 *
224
	 * @param <Vtiger_Paging_Model> $pagingModel
0 ignored issues
show
Documentation Bug introduced by
The doc comment <Vtiger_Paging_Model> at position 0 could not be parsed: Unknown type name '<' at position 0 in <Vtiger_Paging_Model>.
Loading history...
225
	 * @param string                $type        - comments, updates or all
226
	 *
227
	 * @return <Array>
0 ignored issues
show
Documentation Bug introduced by
The doc comment <Array> at position 0 could not be parsed: Unknown type name '<' at position 0 in <Array>.
Loading history...
228
	 */
229
	public function getHistory($pagingModel, $type = false)
230
	{
231
		if (empty($type)) {
232
			$type = 'all';
233
		}
234
		$comments = [];
235
		if ('all' == $type || 'comments' == $type) {
236
			$modCommentsModel = Vtiger_Module_Model::getInstance('ModComments');
237
			if ($modCommentsModel->isPermitted('DetailView')) {
238
				$comments = $this->getComments($pagingModel);
239
			}
240
			if ('comments' == $type) {
241
				return $comments;
242
			}
243
		}
244
		//As getComments api is used to get comment infomation,no need of getting
245
		//comment information again,so avoiding from modtracker
246
		//updateActivityQuery api is used to update a query to fetch a only activity
247
		if ('updates' == $type || 'all' == $type) {
248
			$query = new \App\Db\Query();
249
			$query->select(['vtiger_modtracker_basic.*'])
250
				->from('vtiger_modtracker_basic')
251
				->innerJoin('vtiger_crmentity', 'vtiger_modtracker_basic.crmid = vtiger_crmentity.crmid')
252
				->where(['vtiger_crmentity.deleted' => 0]);
253
254
			$this->getActivityQuery($query, $type);
255
			$query->orderBy(['vtiger_modtracker_basic.id' => SORT_DESC])
256
				->limit($pagingModel->getPageLimit())
257
				->offset($pagingModel->getStartIndex());
258
			$dataReader = $query->createCommand()->query();
259
			$activites = [];
260
			while ($row = $dataReader->read()) {
261
				$moduleName = $row['module'];
262
				$recordId = $row['crmid'];
263
				if (\App\Privilege::isPermitted($moduleName, 'DetailView', $recordId)) {
264
					$modTrackerRecorModel = new ModTracker_Record_Model();
265
					$modTrackerRecorModel->setData($row)->setParent($recordId, $moduleName);
266
					$time = $modTrackerRecorModel->get('changedon');
267
					$activites[$time] = $modTrackerRecorModel;
268
				}
269
			}
270
			$dataReader->close();
271
		}
272
		$history = array_merge($activites, $comments);
0 ignored issues
show
Comprehensibility Best Practice introduced by
The variable $activites does not seem to be defined for all execution paths leading up to this point.
Loading history...
273
274
		$dateTime = [];
275
		foreach ($history as $time => $model) {
276
			$dateTime[] = $time;
277
		}
278
279
		if (!empty($history)) {
280
			array_multisort($dateTime, SORT_DESC, SORT_STRING, $history);
0 ignored issues
show
Bug introduced by
SORT_DESC cannot be passed to array_multisort() as the parameter $rest expects a reference. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

280
			array_multisort($dateTime, /** @scrutinizer ignore-type */ SORT_DESC, SORT_STRING, $history);
Loading history...
Bug introduced by
SORT_STRING cannot be passed to array_multisort() as the parameter $rest expects a reference. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

280
			array_multisort($dateTime, SORT_DESC, /** @scrutinizer ignore-type */ SORT_STRING, $history);
Loading history...
281
282
			return $history;
283
		}
284
		return false;
285
	}
286
}
287