Complex classes like Doctrine 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. You can also have a look at the cohesion graph to spot any un-connected, or weakly-connected components.
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 Doctrine, and based on these observations, apply Extract Interface, too.
1 | <?php |
||
35 | 1 | class Doctrine implements IDataSource |
|
36 | { |
||
37 | use \Nette\SmartObject; |
||
38 | |||
39 | /** @var \Doctrine\ORM\QueryBuilder */ |
||
40 | protected $qb; |
||
41 | |||
42 | /** @var array Map column to the query builder */ |
||
43 | protected $filterMapping; |
||
44 | |||
45 | /** @var array Map column to the query builder */ |
||
46 | protected $sortMapping; |
||
47 | |||
48 | /** @var bool use OutputWalker in Doctrine Paginator */ |
||
49 | protected $useOutputWalkers; |
||
50 | |||
51 | /** @var bool fetch join collection in Doctrine Paginator */ |
||
52 | protected $fetchJoinCollection = TRUE; |
||
53 | |||
54 | /** @var array */ |
||
55 | protected $rand; |
||
56 | |||
57 | /** |
||
58 | * If $sortMapping is not set and $filterMapping is set, |
||
59 | * $filterMapping will be used also as $sortMapping. |
||
60 | * @param \Doctrine\ORM\QueryBuilder $qb |
||
61 | * @param array $filterMapping Maps columns to the DQL columns |
||
62 | * @param array $sortMapping Maps columns to the DQL columns |
||
63 | */ |
||
64 | 1 | public function __construct(\Doctrine\ORM\QueryBuilder $qb, array $filterMapping = NULL, array $sortMapping = NULL) |
|
74 | |||
75 | /** |
||
76 | * @param bool $useOutputWalkers |
||
77 | * @return \Grido\DataSources\Doctrine |
||
78 | */ |
||
79 | public function setUseOutputWalkers($useOutputWalkers) |
||
84 | |||
85 | /** |
||
86 | * @param bool $fetchJoinCollection |
||
87 | * @return \Grido\DataSources\Doctrine |
||
88 | */ |
||
89 | public function setFetchJoinCollection($fetchJoinCollection) |
||
94 | |||
95 | /** |
||
96 | * @return \Doctrine\ORM\Query |
||
97 | */ |
||
98 | 1 | public function getQuery() |
|
102 | |||
103 | /** |
||
104 | * Workaround for https://github.com/Kdyby/DoctrineCache/issues/23 |
||
105 | * |
||
106 | * @param \Doctrine\ORM\QueryBuilder $qb |
||
107 | * @return \Doctrine\ORM\Query |
||
108 | */ |
||
109 | private function _getQuery(\Doctrine\ORM\QueryBuilder $qb) |
||
118 | |||
119 | /** |
||
120 | * @return \Doctrine\ORM\QueryBuilder |
||
121 | */ |
||
122 | public function getQb() |
||
126 | |||
127 | /** |
||
128 | * @return array|NULL |
||
129 | */ |
||
130 | public function getFilterMapping() |
||
134 | |||
135 | 1 | /** |
|
136 | 1 | * @return array|NULL |
|
137 | */ |
||
138 | public function getSortMapping() |
||
142 | 1 | ||
143 | 1 | /** |
|
144 | 1 | * @param Condition $condition |
|
145 | 1 | * @param \Doctrine\ORM\QueryBuilder $qb |
|
146 | 1 | */ |
|
147 | 1 | protected function makeWhere(Condition $condition, \Doctrine\ORM\QueryBuilder $qb = NULL) |
|
184 | |||
185 | /** |
||
186 | * @return string |
||
187 | 1 | */ |
|
188 | 1 | protected function getRand() |
|
197 | |||
198 | /*********************************** interface IDataSource ************************************/ |
||
199 | |||
200 | /** |
||
201 | 1 | * @return int |
|
202 | */ |
||
203 | public function getCount() |
||
210 | 1 | ||
211 | 1 | /** |
|
212 | * It is possible to use query builder with additional columns. |
||
213 | 1 | * In this case, only item at index [0] is returned, because |
|
214 | * it should be an entity object. |
||
215 | 1 | * @return array |
|
216 | */ |
||
217 | public function getData() |
||
235 | |||
236 | 1 | /** |
|
237 | 1 | * Sets filter. |
|
238 | 1 | * @param array $conditions |
|
239 | */ |
||
240 | public function filter(array $conditions) |
||
246 | 1 | ||
247 | 1 | /** |
|
248 | 1 | * Sets offset and limit. |
|
249 | 1 | * @param int $offset |
|
250 | * @param int $limit |
||
251 | 1 | */ |
|
252 | 1 | public function limit($offset, $limit) |
|
257 | |||
258 | /** |
||
259 | * Sets sorting. |
||
260 | * @param array $sorting |
||
261 | */ |
||
262 | public function sort(array $sorting) |
||
272 | 1 | ||
273 | 1 | /** |
|
274 | * @param mixed $column |
||
275 | 1 | * @param array $conditions |
|
276 | 1 | * @param int $limit |
|
277 | 1 | * @return array |
|
278 | * @throws Exception |
||
279 | 1 | */ |
|
280 | 1 | public function suggest($column, array $conditions, $limit) |
|
315 | } |
||
316 |
Our type inference engine has found an assignment of a scalar value (like a string, an integer or null) to a property which is an array.
Either this assignment is in error or the assigned type should be added to the documentation/type hint for that property.
To type hint that a parameter can be either an array or null, you can set a type hint of array and a default value of null. The PHP interpreter will then accept both an array or null for that parameter.
The function can be called with either null or an array for the parameter
$needle
but will only accept an array as$haystack
.