Complex classes like Tools 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 Tools, and based on these observations, apply Extract Interface, too.
1 | <?php |
||
12 | class Tools |
||
13 | { |
||
14 | /** |
||
15 | * Uncountable word forms. |
||
16 | * |
||
17 | * @var array |
||
18 | */ |
||
19 | public static $uncountable = [ |
||
20 | 'audio', |
||
21 | 'bison', |
||
22 | 'chassis', |
||
23 | 'compensation', |
||
24 | 'coreopsis', |
||
25 | 'data', |
||
26 | 'deer', |
||
27 | 'education', |
||
28 | 'emoji', |
||
29 | 'equipment', |
||
30 | 'evidence', |
||
31 | 'feedback', |
||
32 | 'firmware', |
||
33 | 'fish', |
||
34 | 'furniture', |
||
35 | 'gold', |
||
36 | 'hardware', |
||
37 | 'information', |
||
38 | 'jedi', |
||
39 | 'knowledge', |
||
40 | 'love', |
||
41 | 'metadata', |
||
42 | 'money', |
||
43 | 'moose', |
||
44 | 'news', |
||
45 | 'nutrition', |
||
46 | 'offspring', |
||
47 | 'plankton', |
||
48 | 'pokemon', |
||
49 | 'police', |
||
50 | 'rain', |
||
51 | 'rice', |
||
52 | 'series', |
||
53 | 'sheep', |
||
54 | 'software', |
||
55 | 'species', |
||
56 | 'swine', |
||
57 | 'traffic', |
||
58 | 'wheat', |
||
59 | ]; |
||
60 | /** |
||
61 | * Singular inflector rules. |
||
62 | * |
||
63 | * @var array |
||
64 | */ |
||
65 | private static $singular = array ( |
||
66 | 'rules' => array ( |
||
67 | '/(s)tatuses$/i' => '\1\2tatus', |
||
68 | '/^(.*)(menu)s$/i' => '\1\2', |
||
69 | '/(quiz)zes$/i' => '\\1', |
||
70 | '/(matr)ices$/i' => '\1ix', |
||
71 | '/(vert|ind)ices$/i' => '\1ex', |
||
72 | '/^(ox)en/i' => '\1', |
||
73 | '/(alias)(es)*$/i' => '\1', |
||
74 | '/(buffal|her|potat|tomat|volcan)oes$/i' => '\1o', |
||
75 | '/(alumn|bacill|cact|foc|fung|nucle|radi|stimul|syllab|termin|viri?)i$/i' => '\1us', |
||
76 | '/([ftw]ax)es/i' => '\1', |
||
77 | '/(analys|ax|cris|test|thes)es$/i' => '\1is', |
||
78 | '/(shoe|slave)s$/i' => '\1', |
||
79 | '/(o)es$/i' => '\1', |
||
80 | '/ouses$/' => 'ouse', |
||
81 | '/([^a])uses$/' => '\1us', |
||
82 | '/([m|l])ice$/i' => '\1ouse', |
||
83 | '/(x|ch|ss|sh)es$/i' => '\1', |
||
84 | '/(m)ovies$/i' => '\1\2ovie', |
||
85 | '/(s)eries$/i' => '\1\2eries', |
||
86 | '/([^aeiouy]|qu)ies$/i' => '\1y', |
||
87 | '/([lr])ves$/i' => '\1f', |
||
88 | '/(tive)s$/i' => '\1', |
||
89 | '/(hive)s$/i' => '\1', |
||
90 | '/(drive)s$/i' => '\1', |
||
91 | '/(dive)s$/i' => '\1', |
||
92 | '/([^fo])ves$/i' => '\1fe', |
||
93 | '/(^analy)ses$/i' => '\1sis', |
||
94 | '/(analy|diagno|^ba|(p)arenthe|(p)rogno|(s)ynop|(t)he)ses$/i' => '\1\2sis', |
||
95 | '/([ti])a$/i' => '\1um', |
||
96 | '/(p)eople$/i' => '\1\2erson', |
||
97 | '/(m)en$/i' => '\1an', |
||
98 | '/(c)hildren$/i' => '\1\2hild', |
||
99 | '/(f)eet$/i' => '\1oot', |
||
100 | '/(n)ews$/i' => '\1\2ews', |
||
101 | '/eaus$/' => 'eau', |
||
102 | '/^(.*us)$/' => '\\1', |
||
103 | '/s$/i' => '', |
||
104 | ), |
||
105 | 'uninflected' => array ( |
||
106 | '.*[nrlm]ese', |
||
107 | '.*deer', |
||
108 | '.*fish', |
||
109 | '.*measles', |
||
110 | '.*ois', |
||
111 | '.*pox', |
||
112 | '.*sheep', |
||
113 | '.*ss', |
||
114 | 'police', |
||
115 | 'pants', |
||
116 | 'clothes', |
||
117 | ), |
||
118 | 'irregular' => array ( |
||
119 | 'caches' => 'cache', |
||
120 | 'criteria' => 'criterion', |
||
121 | 'curves' => 'curve', |
||
122 | 'emphases' => 'emphasis', |
||
123 | 'foes' => 'foe', |
||
124 | 'hoaxes' => 'hoax', |
||
125 | 'media' => 'medium', |
||
126 | 'neuroses' => 'neurosis', |
||
127 | 'waves' => 'wave', |
||
128 | 'oases' => 'oasis', |
||
129 | ) |
||
130 | ); |
||
131 | |||
132 | /** |
||
133 | * Method cache array. |
||
134 | * |
||
135 | * @var array |
||
136 | */ |
||
137 | private static $cache = array (); |
||
138 | |||
139 | /** |
||
140 | * Determine whether the given value is array accessible. |
||
141 | * |
||
142 | * @param mixed $value |
||
143 | * @return bool |
||
144 | */ |
||
145 | public static function accessible($value) |
||
149 | |||
150 | /** |
||
151 | * Get all of the given array except for a specified array of keys. |
||
152 | * |
||
153 | * @param array $array |
||
154 | * @param array|string $keys |
||
155 | * @return array |
||
156 | */ |
||
157 | public static function except($array, $keys) |
||
163 | |||
164 | /** |
||
165 | * Determine if the given key exists in the provided array. |
||
166 | * |
||
167 | * @param \ArrayAccess|array $array |
||
168 | * @param string|int $key |
||
169 | * @return bool |
||
170 | */ |
||
171 | public static function exists($array, $key) |
||
179 | |||
180 | /** |
||
181 | * Return the first element in an array passing a given truth test. |
||
182 | * |
||
183 | * @param array $array |
||
184 | * @param callable|null $callback |
||
185 | * @param mixed $default |
||
186 | * @return mixed |
||
187 | */ |
||
188 | public static function first($array, callable $callback = null, $default = null) |
||
208 | |||
209 | /** |
||
210 | * Flatten a multi-dimensional array into a single level. |
||
211 | * |
||
212 | * @param array $array |
||
213 | * @param int $depth |
||
214 | * @return array |
||
215 | */ |
||
216 | public static function flatten($array, $depth = INF) |
||
230 | |||
231 | /** |
||
232 | * Remove one or many array items from a given array using "dot" notation. |
||
233 | * |
||
234 | * @param array $array |
||
235 | * @param array|string $keys |
||
236 | * @return void |
||
237 | */ |
||
238 | public static function forget(&$array, $keys) |
||
274 | |||
275 | /** |
||
276 | * Get an item from an array using "dot" notation. |
||
277 | * |
||
278 | * @param \ArrayAccess|array $array |
||
279 | * @param string $key |
||
280 | * @param mixed $default |
||
281 | * @return mixed |
||
282 | */ |
||
283 | public static function get($array, $key, $default = null) |
||
312 | |||
313 | /** |
||
314 | * Shuffle the given array and return the result. |
||
315 | * |
||
316 | * @param array $array |
||
317 | * @return array |
||
318 | */ |
||
319 | public static function shuffle($array) |
||
325 | |||
326 | /** |
||
327 | * Filter the array using the given callback. |
||
328 | * |
||
329 | * @param array $array |
||
330 | * @param callable $callback |
||
331 | * @return array |
||
332 | */ |
||
333 | public static function where($array, callable $callback) |
||
337 | |||
338 | /** |
||
339 | * If the given value is not an array, wrap it in one. |
||
340 | * |
||
341 | * @param mixed $value |
||
342 | * @return array |
||
343 | */ |
||
344 | public static function wrap($value) |
||
348 | |||
349 | /** |
||
350 | * Determine if a given string contains a given substring. |
||
351 | * |
||
352 | * @param string $haystack |
||
353 | * @param string|array $needles |
||
354 | * @return bool |
||
355 | */ |
||
356 | public static function contains($haystack, $needles) |
||
366 | |||
367 | /** |
||
368 | * toValue |
||
369 | * |
||
370 | * @static |
||
371 | * @param $value |
||
372 | * @return mixed |
||
373 | */ |
||
374 | public static function toValue($value) |
||
378 | |||
379 | /** |
||
380 | * Determine if a given string ends with a given substring. |
||
381 | * |
||
382 | * @param string $haystack |
||
383 | * @param string|array $needles |
||
384 | * @return bool |
||
385 | */ |
||
386 | public static function endsWith($haystack, $needles) |
||
396 | |||
397 | /** |
||
398 | * Add an element to an array using "dot" notation if it doesn't exist. |
||
399 | * |
||
400 | * @param array $array |
||
401 | * @param string $key |
||
402 | * @param mixed $value |
||
403 | * @return array |
||
404 | */ |
||
405 | public static function add($array, $key, $value) |
||
413 | |||
414 | /** |
||
415 | * Set an array item to a given value using "dot" notation. |
||
416 | * If no key is given to the method, the entire array will be replaced. |
||
417 | * |
||
418 | * @param array $array |
||
419 | * @param string $key |
||
420 | * @param mixed $value |
||
421 | * @return array |
||
422 | */ |
||
423 | public static function set(&$array, $key, $value) |
||
448 | |||
449 | /** |
||
450 | * Get one or a specified number of random values from an array. |
||
451 | * |
||
452 | * @param array $array |
||
453 | * @param int|null $number |
||
454 | * @return mixed |
||
455 | * @throws \InvalidArgumentException |
||
456 | */ |
||
457 | public static function random($array, $number = null) |
||
487 | |||
488 | /** |
||
489 | * Replace a given value in the string sequentially with an array. |
||
490 | * |
||
491 | * @param string $search |
||
492 | * @param array $replace |
||
493 | * @param string $subject |
||
494 | * @return string |
||
495 | */ |
||
496 | public static function replaceArray($search, array $replace, $subject) |
||
504 | |||
505 | /** |
||
506 | * Replace the first occurrence of a given value in the string. |
||
507 | * |
||
508 | * @param string $search |
||
509 | * @param string $replace |
||
510 | * @param string $subject |
||
511 | * @return string |
||
512 | */ |
||
513 | public static function replaceFirst($search, $replace, $subject) |
||
527 | |||
528 | /** |
||
529 | * Convert a string to snake case. |
||
530 | * |
||
531 | * @param string $value |
||
532 | * @param string $delimiter |
||
533 | * @return string |
||
534 | */ |
||
535 | public static function snake($value, $delimiter = '_') |
||
551 | |||
552 | /** |
||
553 | * Get the plural form of an English word. |
||
554 | * |
||
555 | * @param string $value |
||
556 | * @param int $count |
||
557 | * @return string |
||
558 | */ |
||
559 | public static function plural($value, $count = 2) |
||
569 | |||
570 | /** |
||
571 | * Attempt to match the case on two strings. |
||
572 | * |
||
573 | * @param string $value |
||
574 | * @param string $comparison |
||
575 | * @return string |
||
576 | */ |
||
577 | protected static function matchCase($value, $comparison) |
||
589 | |||
590 | /** |
||
591 | * Determine if the given value is uncountable. |
||
592 | * |
||
593 | * @param string $value |
||
594 | * @return bool |
||
595 | */ |
||
596 | protected static function uncountable($value) |
||
600 | |||
601 | /** |
||
602 | * Returns a word in singular form. |
||
603 | * |
||
604 | * @param string $word The word in plural form. |
||
605 | * @return string The word in singular form. |
||
606 | */ |
||
607 | public static function pluralize($word) |
||
658 | |||
659 | /** |
||
660 | * Basename |
||
661 | * |
||
662 | * @static |
||
663 | * @param $class |
||
664 | * @return string |
||
665 | */ |
||
666 | public static function Basename($class) |
||
672 | |||
673 | /** |
||
674 | * ClassRecursive |
||
675 | * |
||
676 | * @static |
||
677 | * @param $class |
||
678 | * @return array |
||
679 | */ |
||
680 | public static function ClassRecursive($class) |
||
692 | |||
693 | /** |
||
694 | * UsesRecursive |
||
695 | * |
||
696 | * @static |
||
697 | * @param $trait |
||
698 | * @return array |
||
699 | */ |
||
700 | public static function UsesRecursive($trait) |
||
710 | } |
This error could be the result of:
1. Missing dependencies
PHP Analyzer uses your
composer.json
file (if available) to determine the dependencies of your project and to determine all the available classes and functions. It expects thecomposer.json
to be in the root folder of your repository.Are you sure this class is defined by one of your dependencies, or did you maybe not list a dependency in either the
require
orrequire-dev
section?2. Missing use statement
PHP does not complain about undefined classes in
ìnstanceof
checks. For example, the following PHP code will work perfectly fine:If you have not tested against this specific condition, such errors might go unnoticed.