Completed
Branch master (099915)
by Fabio
08:02
created

TScaffoldListView::getRecordCriteria()   A

Complexity

Conditions 6
Paths 12

Size

Total Lines 20
Code Lines 14

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 0
CRAP Score 42

Importance

Changes 1
Bugs 0 Features 0
Metric Value
cc 6
eloc 14
c 1
b 0
f 0
nc 12
nop 0
dl 0
loc 20
ccs 0
cts 20
cp 0
crap 42
rs 9.2222
1
<?php
2
/**
3
 * TScaffoldListView class file.
4
 *
5
 * @author Wei Zhuo <weizhuo[at]gmail[dot]com>
6
 * @link https://github.com/pradosoft/prado
7
 * @license https://github.com/pradosoft/prado/blob/master/LICENSE
8
 * @package Prado\Data\ActiveRecord\Scaffold
9
 */
10
11
namespace Prado\Data\ActiveRecord\Scaffold;
12
13
/**
14
 * Load the scaffold base class.
15
 */
16
use Prado\Data\ActiveRecord\TActiveRecordCriteria;
17
use Prado\Exceptions\TConfigurationException;
18
use Prado\Prado;
19
use Prado\TPropertyValue;
20
use Prado\Web\UI\WebControls\IItemDataRenderer;
21
use Prado\Web\UI\WebControls\TListItemType;
22
use Prado\Web\UI\WebControls\TRepeaterCommandEventParameter;
23
24
/**
25
 * TScaffoldListView displays a list of Active Records.
26
 *
27
 * The {@link getHeader Header} property is a TRepeater displaying the
28
 * Active Record property/field names. The {@link getSort Sort} property
29
 * is a drop down list displaying the combination of properties and its possible
30
 * ordering. The {@link getPager Pager} property is a TPager control displaying
31
 * the links and/or buttons that navigate to different pages in the Active Record data.
32
 * The {@link getList List} property is a TRepeater that renders a row of
33
 * Active Record data.
34
 *
35
 * Custom rendering of the each Active Record can be achieved by specifying
36
 * the ItemTemplate or AlternatingItemTemplate property of the main {@linnk getList List}
37
 * repeater.
38
 *
39
 * The TScaffoldListView will listen for two command events named "delete" and
40
 * "edit". A "delete" command will delete a the record for the row where the
41
 * "delete" command is originates. An "edit" command will push
42
 * the record data to be edited by a TScaffoldEditView with ID specified by the
43
 * {@link setEditViewID EditViewID}.
44
 *
45
 * Additional {@link setSearchCondition SearchCondition} and
46
 * {@link setSearchParameters SearchParameters} (takes array values) can be
47
 * specified to customize the records to be shown. The {@link setSearchCondition SearchCondition}
48
 * will be used as the Condition property of TActiveRecordCriteria, and similarly
49
 * the {@link setSearchParameters SearchParameters} will be the corresponding
50
 * Parameters property of TActiveRecordCriteria.
51
 *
52
 * @author Wei Zhuo <weizho[at]gmail[dot]com>
53
 * @package Prado\Data\ActiveRecord\Scaffold
54
 * @since 3.1
55
 */
56
class TScaffoldListView extends TScaffoldBase
57
{
58
	/**
59
	 * Initialize the sort drop down list and the column names repeater.
60
	 */
61
	protected function initializeSort()
62
	{
63
		$table = $this->getTableInfo();
64
		$sorts = ['Sort By', str_repeat('-', 15)];
65
		$headers = [];
66
		foreach ($table->getColumns() as $name => $colum) {
67
			$fname = ucwords(str_replace('_', ' ', $name));
68
			$sorts[$name . ' ASC'] = $fname . ' Ascending';
69
			$sorts[$name . ' DESC'] = $fname . ' Descending';
70
			$headers[] = $fname;
71
		}
72
		$this->_sort->setDataSource($sorts);
0 ignored issues
show
Bug introduced by
The method setDataSource() does not exist on null. ( Ignorable by Annotation )

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

72
		$this->_sort->/** @scrutinizer ignore-call */ 
73
                setDataSource($sorts);

This check looks for calls to methods that do not seem to exist on a given type. It looks for the method on the type itself as well as in inherited classes or implemented interfaces.

This is most likely a typographical error or the method has been renamed.

Loading history...
Bug Best Practice introduced by
The property _sort does not exist on Prado\Data\ActiveRecord\Scaffold\TScaffoldListView. Since you implemented __get, consider adding a @property annotation.
Loading history...
73
		$this->_sort->dataBind();
74
		$this->_header->setDataSource($headers);
0 ignored issues
show
Bug introduced by
The method setDataSource() does not exist on null. ( Ignorable by Annotation )

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

74
		$this->_header->/** @scrutinizer ignore-call */ 
75
                  setDataSource($headers);

This check looks for calls to methods that do not seem to exist on a given type. It looks for the method on the type itself as well as in inherited classes or implemented interfaces.

This is most likely a typographical error or the method has been renamed.

Loading history...
Bug Best Practice introduced by
The property _header does not exist on Prado\Data\ActiveRecord\Scaffold\TScaffoldListView. Since you implemented __get, consider adding a @property annotation.
Loading history...
75
		$this->_header->dataBind();
76
	}
77
78
	/**
79
	 * Loads and display the data.
80
	 * @param mixed $param
81
	 */
82
	public function onPreRender($param)
83
	{
84
		parent::onPreRender($param);
85
		if (!$this->getPage()->getIsPostBack() || $this->getViewState('CurrentClass') != $this->getRecordClass()) {
86
			$this->initializeSort();
87
			$this->setViewState('CurrentClass', $this->getRecordClass());
88
		}
89
		$this->loadRecordData();
90
	}
91
92
	/**
93
	 * Fetch the records and data bind it to the list.
94
	 */
95
	protected function loadRecordData()
96
	{
97
		$search = new TActiveRecordCriteria($this->getSearchCondition(), $this->getSearchParameters());
98
		$this->_list->setVirtualItemCount($this->getRecordFinder()->count($search));
0 ignored issues
show
Bug Best Practice introduced by
The property _list does not exist on Prado\Data\ActiveRecord\Scaffold\TScaffoldListView. Since you implemented __get, consider adding a @property annotation.
Loading history...
Bug introduced by
The method setVirtualItemCount() does not exist on null. ( Ignorable by Annotation )

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

98
		$this->_list->/** @scrutinizer ignore-call */ 
99
                setVirtualItemCount($this->getRecordFinder()->count($search));

This check looks for calls to methods that do not seem to exist on a given type. It looks for the method on the type itself as well as in inherited classes or implemented interfaces.

This is most likely a typographical error or the method has been renamed.

Loading history...
99
		$finder = $this->getRecordFinder();
100
		$criteria = $this->getRecordCriteria();
101
		$this->_list->setDataSource($finder->findAll($criteria));
102
		$this->_list->dataBind();
103
	}
104
105
	/**
106
	 * @return TActiveRecordCriteria sort/search/paging criteria
107
	 */
108
	protected function getRecordCriteria()
109
	{
110
		$total = $this->_list->getVirtualItemCount();
0 ignored issues
show
Bug Best Practice introduced by
The property _list does not exist on Prado\Data\ActiveRecord\Scaffold\TScaffoldListView. Since you implemented __get, consider adding a @property annotation.
Loading history...
111
		$limit = $this->_list->getPageSize();
112
		$offset = $this->_list->getCurrentPageIndex() * $limit;
113
		if ($offset + $limit > $total) {
114
			$limit = $total - $offset;
115
		}
116
		$criteria = new TActiveRecordCriteria($this->getSearchCondition(), $this->getSearchParameters());
117
		if ($limit > 0) {
118
			$criteria->setLimit($limit);
119
			if ($offset <= $total) {
120
				$criteria->setOffset($offset);
121
			}
122
		}
123
		$order = explode(' ', $this->_sort->getSelectedValue(), 2);
0 ignored issues
show
Bug Best Practice introduced by
The property _sort does not exist on Prado\Data\ActiveRecord\Scaffold\TScaffoldListView. Since you implemented __get, consider adding a @property annotation.
Loading history...
124
		if (is_array($order) && count($order) === 2) {
125
			$criteria->OrdersBy[$order[0]] = $order[1];
0 ignored issues
show
Bug Best Practice introduced by
The property OrdersBy does not exist on Prado\Data\ActiveRecord\TActiveRecordCriteria. Since you implemented __get, consider adding a @property annotation.
Loading history...
126
		}
127
		return $criteria;
128
	}
129
130
	/**
131
	 * @param string $value search condition, the SQL string after the WHERE clause.
132
	 */
133
	public function setSearchCondition($value)
134
	{
135
		$this->setViewState('SearchCondition', $value);
136
	}
137
138
	/**
139
	 * @return string SQL search condition for list display.
140
	 */
141
	public function getSearchCondition()
142
	{
143
		return $this->getViewState('SearchCondition');
144
	}
145
146
	/**
147
	 * @param array $value search parameters
148
	 */
149
	public function setSearchParameters($value)
150
	{
151
		$this->setViewState('SearchParameters', TPropertyValue::ensureArray($value), []);
152
	}
153
154
	/**
155
	 * @return array search parameters
156
	 */
157
	public function getSearchParameters()
158
	{
159
		return $this->getViewState('SearchParameters', []);
160
	}
161
162
	/**
163
	 * Continue bubbling the "edit" command, "delete" command is handled in this class.
164
	 * @param mixed $sender
165
	 * @param mixed $param
166
	 */
167
	public function bubbleEvent($sender, $param)
168
	{
169
		switch (strtolower($param->getCommandName())) {
170
			case 'delete':
171
				return $this->deleteRecord($sender, $param);
0 ignored issues
show
Bug introduced by
Are you sure the usage of $this->deleteRecord($sender, $param) targeting Prado\Data\ActiveRecord\...istView::deleteRecord() seems to always return null.

This check looks for function or method calls that always return null and whose return value is used.

class A
{
    function getObject()
    {
        return null;
    }

}

$a = new A();
if ($a->getObject()) {

The method getObject() can return nothing but null, so it makes no sense to use the return value.

The reason is most likely that a function or method is imcomplete or has been reduced for debug purposes.

Loading history...
172
			case 'edit':
173
				$this->initializeEdit($sender, $param);
174
		}
175
		$this->raiseBubbleEvent($this, $param);
176
		return true;
177
	}
178
179
	/**
180
	 * Initialize the edit view control form when EditViewID is set.
181
	 * @param mixed $sender
182
	 * @param mixed $param
183
	 */
184
	protected function initializeEdit($sender, $param)
0 ignored issues
show
Unused Code introduced by
The parameter $sender 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

184
	protected function initializeEdit(/** @scrutinizer ignore-unused */ $sender, $param)

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...
185
	{
186
		if (($ctrl = $this->getEditViewControl()) !== null) {
187
			if ($param instanceof TRepeaterCommandEventParameter) {
188
				$pk = $param->getItem()->getCustomData();
189
				$ctrl->setRecordPk($pk);
190
				$ctrl->initializeEditForm();
191
			}
192
		}
193
	}
194
195
	/**
196
	 * Deletes an Active Record.
197
	 * @param mixed $sender
198
	 * @param mixed $param
199
	 */
200
	protected function deleteRecord($sender, $param)
0 ignored issues
show
Unused Code introduced by
The parameter $sender 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

200
	protected function deleteRecord(/** @scrutinizer ignore-unused */ $sender, $param)

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...
201
	{
202
		if ($param instanceof TRepeaterCommandEventParameter) {
203
			$pk = $param->getItem()->getCustomData();
204
			$this->getRecordFinder()->deleteByPk($pk);
205
		}
206
	}
207
208
	/**
209
	 * Initialize the default display for each Active Record item.
210
	 * @param mixed $sender
211
	 * @param mixed $param
212
	 */
213
	protected function listItemCreated($sender, $param)
214
	{
215
		$item = $param->getItem();
216
		if ($item instanceof IItemDataRenderer) {
217
			$type = $item->getItemType();
218
			if ($type == TListItemType::Item || $type == TListItemType::AlternatingItem) {
0 ignored issues
show
introduced by
The condition $type == Prado\Web\UI\We...emType::AlternatingItem is always false.
Loading history...
219
				$this->populateField($sender, $param);
220
			}
221
		}
222
	}
223
224
	/**
225
	 * Sets the Record primary key to the current repeater item's CustomData.
226
	 * Binds the inner repeater with properties of the current Active Record.
227
	 * @param mixed $sender
228
	 * @param mixed $param
229
	 */
230
	protected function populateField($sender, $param)
0 ignored issues
show
Unused Code introduced by
The parameter $sender 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

230
	protected function populateField(/** @scrutinizer ignore-unused */ $sender, $param)

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...
231
	{
232
		$item = $param->getItem();
233
		if (($data = $item->getData()) !== null) {
234
			$item->setCustomData($this->getRecordPkValues($data));
235
			if (($prop = $item->findControl('_properties')) !== null) {
0 ignored issues
show
Unused Code introduced by
The assignment to $prop is dead and can be removed.
Loading history...
236
				$item->_properties->setDataSource($this->getRecordPropertyValues($data));
237
				$item->_properties->dataBind();
238
			}
239
		}
240
	}
241
242
	/**
243
	 * Updates repeater page index with the pager new index value.
244
	 * @param mixed $sender
245
	 * @param mixed $param
246
	 */
247
	protected function pageChanged($sender, $param)
0 ignored issues
show
Unused Code introduced by
The parameter $sender 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

247
	protected function pageChanged(/** @scrutinizer ignore-unused */ $sender, $param)

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...
248
	{
249
		$this->_list->setCurrentPageIndex($param->getNewPageIndex());
0 ignored issues
show
Bug Best Practice introduced by
The property _list does not exist on Prado\Data\ActiveRecord\Scaffold\TScaffoldListView. Since you implemented __get, consider adding a @property annotation.
Loading history...
250
	}
251
252
	/**
253
	 * @return TRepeater Repeater control for Active Record instances.
0 ignored issues
show
Bug introduced by
The type Prado\Data\ActiveRecord\Scaffold\TRepeater was not found. Maybe you did not declare it correctly or list all dependencies?

The issue could also be caused by a filter entry in the build configuration. If the path has been excluded in your configuration, e.g. excluded_paths: ["lib/*"], you can move it to the dependency path list as follows:

filter:
    dependency_paths: ["lib/*"]

For further information see https://scrutinizer-ci.com/docs/tools/php/php-scrutinizer/#list-dependency-paths

Loading history...
254
	 */
255
	public function getList()
256
	{
257
		$this->ensureChildControls();
258
		return $this->getRegisteredObject('_list');
259
	}
260
261
	/**
262
	 * @return TPager List pager control.
0 ignored issues
show
Bug introduced by
The type Prado\Data\ActiveRecord\Scaffold\TPager was not found. Maybe you did not declare it correctly or list all dependencies?

The issue could also be caused by a filter entry in the build configuration. If the path has been excluded in your configuration, e.g. excluded_paths: ["lib/*"], you can move it to the dependency path list as follows:

filter:
    dependency_paths: ["lib/*"]

For further information see https://scrutinizer-ci.com/docs/tools/php/php-scrutinizer/#list-dependency-paths

Loading history...
263
	 */
264
	public function getPager()
265
	{
266
		$this->ensureChildControls();
267
		return $this->getRegisteredObject('_pager');
268
	}
269
270
	/**
271
	 * @return TDropDownList Control that displays and controls the record ordering.
0 ignored issues
show
Bug introduced by
The type Prado\Data\ActiveRecord\Scaffold\TDropDownList was not found. Maybe you did not declare it correctly or list all dependencies?

The issue could also be caused by a filter entry in the build configuration. If the path has been excluded in your configuration, e.g. excluded_paths: ["lib/*"], you can move it to the dependency path list as follows:

filter:
    dependency_paths: ["lib/*"]

For further information see https://scrutinizer-ci.com/docs/tools/php/php-scrutinizer/#list-dependency-paths

Loading history...
272
	 */
273
	public function getSort()
274
	{
275
		$this->ensureChildControls();
276
		return $this->getRegisteredObject('_sort');
277
	}
278
279
	/**
280
	 * @return TRepeater Repeater control for record property names.
281
	 */
282
	public function getHeader()
283
	{
284
		$this->ensureChildControls();
285
		return $this->getRegisteredObject('_header');
286
	}
287
288
	/**
289
	 * @return string TScaffoldEditView control ID for editing selected Active Record.
290
	 */
291
	public function getEditViewID()
292
	{
293
		return $this->getViewState('EditViewID');
294
	}
295
296
	/**
297
	 * @param string $value TScaffoldEditView control ID for editing selected Active Record.
298
	 */
299
	public function setEditViewID($value)
300
	{
301
		$this->setViewState('EditViewID', $value);
302
	}
303
304
	/**
305
	 * @return TScaffoldEditView control for editing selected Active Record, null if EditViewID is not set.
306
	 */
307
	protected function getEditViewControl()
308
	{
309
		if (($id = $this->getEditViewID()) !== null) {
0 ignored issues
show
introduced by
The condition $id = $this->getEditViewID() !== null is always true.
Loading history...
310
			$ctrl = $this->getParent()->findControl($id);
311
			if ($ctrl === null) {
312
				throw new TConfigurationException('scaffold_unable_to_find_edit_view', $id);
313
			}
314
			return $ctrl;
315
		}
316
	}
317
}
318