Completed
Pull Request — master (#300)
by Martin
06:30
created

DoctrineCollectionDataSource   A

Complexity

Total Complexity 26

Size/Duplication

Total Lines 256
Duplicated Lines 8.2 %

Coupling/Cohesion

Components 1
Dependencies 8

Importance

Changes 1
Bugs 0 Features 1
Metric Value
wmc 26
c 1
b 0
f 1
lcom 1
cbo 8
dl 21
loc 256
rs 10

13 Methods

Rating   Name   Duplication   Size   Complexity  
A __construct() 0 6 1
A initialize() 0 8 2
A getCount() 0 6 1
A getData() 0 6 1
A filterOne() 0 9 2
A applyFilterDate() 0 12 2
A applyFilterDateRange() 16 22 3
A applyFilterRange() 0 14 3
A applyFilterText() 5 19 4
A applyFilterMultiSelect() 0 7 1
A applyFilterSelect() 0 7 2
A limit() 0 6 1
A sort() 0 21 3

How to fix   Duplicated Code   

Duplicated Code

Duplicate code is one of the most pungent code smells. A rule that is often used is to re-structure code once it is duplicated in three or more places.

Common duplication problems, and corresponding solutions are:

1
<?php
2
3
/**
4
 * @copyright   Copyright (c) 2015 ublaboo <[email protected]>
5
 * @author      Jakub Kontra <[email protected]>
6
 * @author      Pavel Janda <[email protected]>
7
 * @package     Ublaboo
8
 */
9
10
namespace Ublaboo\DataGrid\DataSource;
11
12
use Doctrine\Common\Collections\Collection;
13
use Doctrine\Common\Collections\Criteria;
14
use Ublaboo\DataGrid\Filter;
15
use Ublaboo\DataGrid\Utils\Sorting;
16
17
class DoctrineCollectionDataSource extends FilterableDataSource implements IDataSource
18
{
19
20
	/**
21
	 * @var Collection
22
	 */
23
	protected $data_source;
24
25
	/**
26
	 * @var string
27
	 */
28
	protected $primary_key;
29
30
	/**
31
	 * @var Criteria
32
	 */
33
	protected $criteria;
34
35
	/**
36
	 * @var Collection
37
	 */
38
	private $matched;
39
40
41
	/**
42
	 * @param Collection  $collection
43
	 * @param string      $primary_key
44
	 */
45
	public function __construct(Collection $collection, $primary_key)
46
	{
47
		$this->criteria = Criteria::create();
48
		$this->data_source = $collection;
49
		$this->primary_key = $primary_key;
50
	}
51
52
53
	protected function initialize()
54
	{
55
		if (isset($this->matched)) {
56
			return NULL;
57
		}
58
59
		$this->matched = $this->data_source->matching($this->criteria);
60
	}
61
62
63
	/********************************************************************************
64
	 *                          IDataSource implementation                          *
65
	 ********************************************************************************/
66
67
68
	/**
69
	 * Get count of data
70
	 * @return int
71
	 */
72
	public function getCount()
73
	{
74
		$this->initialize();
75
76
		return $this->matched->count();
77
	}
78
79
80
	/**
81
	 * Get the data
82
	 * @return array
83
	 */
84
	public function getData()
85
	{
86
		$this->initialize();
87
88
		return $this->matched->toArray();
89
	}
90
91
92
	/**
93
	 * Filter data - get one row
94
	 * @param array $condition
95
	 * @return static
96
	 */
97
	public function filterOne(array $condition)
98
	{
99
		foreach ($condition as $column => $value) {
100
			$expr = Criteria::expr()->eq($column, $value);
101
			$this->criteria->andWhere($expr);
102
		}
103
104
		return $this;
105
	}
106
107
108
	/**
109
	 * Filter by date
110
	 * @param  Filter\FilterDate $filter
111
	 * @return void
112
	 */
113
	public function applyFilterDate(Filter\FilterDate $filter)
114
	{
115
		foreach ($filter->getCondition() as $column => $value) {
116
			$date = \DateTime::createFromFormat($filter->getPhpFormat(), $value)
117
				->format('Y-m-d H:i:s');
118
119
			$from = Criteria::expr()->gte($filter->getColumn(), $date->format('Y-m-d 00:00:00'));
120
			$to = Criteria::expr()->lte($filter->getColumn(), $date->format('Y-m-d 23:59:59'));
121
122
			$this->criteria->andWhere($from)->andWhere($to);
123
		}
124
	}
125
126
127
	/**
128
	 * Filter by date range
129
	 * @param  Filter\FilterDateRange $filter
130
	 * @return void
131
	 */
132
	public function applyFilterDateRange(Filter\FilterDateRange $filter)
133
	{
134
		$values = $conditions[$filter->getColumn()];
0 ignored issues
show
Bug introduced by
The variable $conditions does not exist. Did you forget to declare it?

This check marks access to variables or properties that have not been declared yet. While PHP has no explicit notion of declaring a variable, accessing it before a value is assigned to it is most likely a bug.

Loading history...
135
136 View Code Duplication
		if ($value_from = $values['from']) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
137
			$date_from = \DateTime::createFromFormat($filter->getPhpFormat(), $value_from)
138
				->setTime(0, 0, 0)
139
				->format('Y-m-d H:i:s');
140
141
			$expr = Criteria::expr()->gte($filter->getColumn(), $date_from);
142
			$this->criteria->andWhere($expr);
143
		}
144
145 View Code Duplication
		if ($value_to = $values['to']) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
146
			$date_to = \DateTime::createFromFormat($filter->getPhpFormat(), $value_to)
147
				->setTime(23, 59, 59)
148
				->format('Y-m-d H:i:s');
149
150
			$expr = Criteria::expr()->lte($filter->getColumn(), $date_to);
151
			$this->criteria->andWhere($expr);
152
		}
153
	}
154
155
156
	/**
157
	 * Filter by range
158
	 * @param  Filter\FilterRange $filter
159
	 * @return void
160
	 */
161
	public function applyFilterRange(Filter\FilterRange $filter)
162
	{
163
		$values = $conditions[$filter->getColumn()];
0 ignored issues
show
Bug introduced by
The variable $conditions does not exist. Did you forget to declare it?

This check marks access to variables or properties that have not been declared yet. While PHP has no explicit notion of declaring a variable, accessing it before a value is assigned to it is most likely a bug.

Loading history...
164
165
		if ($value_from = $values['from']) {
166
			$expr = Criteria::expr()->gte($filter->getColumn(), $value_from);
167
			$this->criteria->andWhere($expr);
168
		}
169
170
		if ($value_to = $values['to']) {
171
			$expr = Criteria::expr()->lte($filter->getColumn(), $value_to);
172
			$this->criteria->andWhere($expr);
173
		}
174
	}
175
176
177
	/**
178
	 * Filter by keyword
179
	 * @param  Filter\FilterText $filter
180
	 * @return void
181
	 */
182
	public function applyFilterText(Filter\FilterText $filter)
183
	{
184
		$exprs = [];
185
186
		foreach ($filter->getCondition() as $column => $value) {
187 View Code Duplication
			if ($filter->hasSplitWordsSearch() === FALSE) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
188
				$words = [$value];
189
			} else {
190
				$words = explode(' ', $value);
191
			}
192
193
			foreach ($words as $word) {
194
				$exprs[] = Criteria::expr()->contains($column, $word);
195
			}
196
		}
197
198
		$expr = call_user_func_array([Criteria::expr(), 'orX'], $exprs);
199
		$this->criteria->andWhere($expr);
200
	}
201
202
203
	/**
204
	 * Filter by multi select value
205
	 * @param  Filter\FilterMultiSelect $filter
206
	 * @return void
207
	 */
208
	public function applyFilterMultiSelect(Filter\FilterMultiSelect $filter)
209
	{
210
		$values = $filter->getCondition()[$filter->getColumn()];
211
212
		$expr = Criteria::expr()->in($filter->getColumn(), $values);
213
		$this->criteria->andWhere($expr);
214
	}
215
216
217
	/**
218
	 * Filter by select value
219
	 * @param  Filter\FilterSelect $filter
220
	 * @return void
221
	 */
222
	public function applyFilterSelect(Filter\FilterSelect $filter)
223
	{
224
		foreach ($filter->getCondition() as $column => $value) {
225
			$expr = Criteria::expr()->eq($column, $value);
226
			$this->criteria->andWhere($expr);
227
		}
228
	}
229
230
231
	/**
232
	 * Apply limit and offset on data
233
	 * @param int $offset
234
	 * @param int $limit
235
	 * @return static
236
	 */
237
	public function limit($offset, $limit)
238
	{
239
		$this->criteria->setFirstResult($offset)->setMaxResults($limit);
240
241
		return $this;
242
	}
243
244
245
	/**
246
	 * Sort data
247
	 * @param Sorting $sorting
248
	 * @return static
249
	 */
250
	public function sort(Sorting $sorting)
251
	{
252
		if (is_callable($sorting->getSortCallback())) {
253
			call_user_func(
254
				$sorting->getSortCallback(),
255
				$this->criteria,
256
				$sorting->getSort()
257
			);
258
259
			return $this;
260
		}
261
262
		if ($sort = $sorting->getSort()) {
263
			$this->criteria->orderBy($sort);
264
			return $this;
265
		}
266
267
		$this->criteria->orderBy([$this->primary_key => 'ASC']);
268
269
		return $this;
270
	}
271
272
}
273