Complex classes like SitemapManager 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 SitemapManager, and based on these observations, apply Extract Interface, too.
1 | <?php namespace Arcanedev\LaravelSitemap; |
||
15 | class SitemapManager implements SitemapManagerContract |
||
16 | { |
||
17 | /* ------------------------------------------------------------------------------------------------ |
||
18 | | Properties |
||
19 | | ------------------------------------------------------------------------------------------------ |
||
20 | */ |
||
21 | /** |
||
22 | * @var array |
||
23 | */ |
||
24 | protected $sitemaps = []; |
||
25 | |||
26 | /** |
||
27 | * @var string |
||
28 | */ |
||
29 | protected $title = null; |
||
30 | |||
31 | /** |
||
32 | * @var string |
||
33 | */ |
||
34 | protected $link = null; |
||
35 | |||
36 | /** |
||
37 | * @var Entities\SitemapItemCollection |
||
38 | */ |
||
39 | protected $items; |
||
40 | |||
41 | /** |
||
42 | * Escaping html entities. |
||
43 | * |
||
44 | * @var bool |
||
45 | */ |
||
46 | private $escaping = true; |
||
47 | |||
48 | /** |
||
49 | * Custom max size for limitSize() |
||
50 | * |
||
51 | * @var bool |
||
52 | */ |
||
53 | protected $maxSize = null; |
||
54 | |||
55 | /** |
||
56 | * Enable or disable cache |
||
57 | * |
||
58 | * @var boolean |
||
59 | */ |
||
60 | protected $cacheEnabled = false; |
||
61 | |||
62 | /** |
||
63 | * Unique cache key. |
||
64 | * |
||
65 | * @var string |
||
66 | */ |
||
67 | protected $cacheKey = 'laravel-sitemap.your-key'; |
||
68 | |||
69 | /** |
||
70 | * Cache duration, can be int or timestamp |
||
71 | * |
||
72 | * @var int |
||
73 | */ |
||
74 | protected $cacheDuration = 3600; |
||
75 | |||
76 | /** |
||
77 | * Use limit size for big sitemaps |
||
78 | * |
||
79 | * @var bool |
||
80 | */ |
||
81 | protected $useLimitSize; |
||
82 | |||
83 | /** @var \Illuminate\Contracts\Config\Repository */ |
||
84 | protected $config; |
||
85 | |||
86 | /** @var \Illuminate\Contracts\Cache\Repository */ |
||
87 | protected $cache; |
||
88 | |||
89 | /** @var \Illuminate\Filesystem\Filesystem */ |
||
90 | protected $filesystem; |
||
91 | |||
92 | /** @var \Arcanedev\LaravelSitemap\Contracts\SitemapStyler */ |
||
93 | private $styler; |
||
94 | |||
95 | /* ------------------------------------------------------------------------------------------------ |
||
96 | | Constructor |
||
97 | | ------------------------------------------------------------------------------------------------ |
||
98 | */ |
||
99 | /** |
||
100 | * SitemapManager constructor. |
||
101 | * |
||
102 | * @param \Illuminate\Contracts\Cache\Repository $cache |
||
103 | * @param \Illuminate\Contracts\Config\Repository $config |
||
104 | * @param \Illuminate\Filesystem\Filesystem $filesystem |
||
105 | * @param \Arcanedev\LaravelSitemap\Contracts\SitemapStyler $styler |
||
106 | */ |
||
107 | 32 | public function __construct( |
|
120 | |||
121 | 32 | private function init() |
|
134 | |||
135 | /* ------------------------------------------------------------------------------------------------ |
||
136 | | Getters & Setters |
||
137 | | ------------------------------------------------------------------------------------------------ |
||
138 | */ |
||
139 | /** |
||
140 | * Get all sitemaps. |
||
141 | * |
||
142 | * @return array |
||
143 | */ |
||
144 | public function getSitemaps() |
||
148 | |||
149 | /** |
||
150 | * Adds sitemap to $sitemaps array. |
||
151 | * |
||
152 | * @param array $sitemap |
||
153 | * |
||
154 | * @return self |
||
155 | */ |
||
156 | public function setSitemaps(array $sitemap) |
||
162 | |||
163 | /** |
||
164 | * Get the sitemap items. |
||
165 | * |
||
166 | * @return \Arcanedev\LaravelSitemap\Entities\SitemapItemCollection |
||
167 | */ |
||
168 | 16 | public function getItems() |
|
172 | |||
173 | /** |
||
174 | * Get the title. |
||
175 | * |
||
176 | * @return string |
||
177 | */ |
||
178 | 8 | public function getTitle() |
|
182 | |||
183 | /** |
||
184 | * Set the title. |
||
185 | * |
||
186 | * @param string $title |
||
187 | * |
||
188 | * @return self |
||
189 | */ |
||
190 | 8 | public function setTitle($title) |
|
196 | |||
197 | /** |
||
198 | * Get the link. |
||
199 | * |
||
200 | * @return string |
||
201 | */ |
||
202 | 8 | public function getLink() |
|
206 | |||
207 | /** |
||
208 | * Sets $link value. |
||
209 | * |
||
210 | * @param string $link |
||
211 | * |
||
212 | * @return self |
||
213 | */ |
||
214 | 8 | public function setLink($link) |
|
220 | |||
221 | /** |
||
222 | * Get the sitemap styles location. |
||
223 | * |
||
224 | * @return string |
||
225 | */ |
||
226 | 8 | public function getStyleLocation() |
|
230 | |||
231 | /** |
||
232 | * Set the sitemap styles location. |
||
233 | * |
||
234 | * @param string $location |
||
235 | * |
||
236 | * @return self |
||
237 | */ |
||
238 | 8 | public function setStyleLocation($location) |
|
244 | |||
245 | /** |
||
246 | * Get the escaping value. |
||
247 | * |
||
248 | * @return bool |
||
249 | */ |
||
250 | 24 | public function isEscaped() |
|
254 | |||
255 | /** |
||
256 | * Set the escaping value. |
||
257 | * |
||
258 | * @param bool $escape |
||
259 | * |
||
260 | * @return self |
||
261 | */ |
||
262 | 32 | public function setEscaping($escape) |
|
268 | |||
269 | /** |
||
270 | * Get the max size value. |
||
271 | * |
||
272 | * @return int |
||
273 | */ |
||
274 | 8 | public function getMaxSize() |
|
278 | |||
279 | /** |
||
280 | * Set the max size value. |
||
281 | * |
||
282 | * @param int $maxSize |
||
283 | * |
||
284 | * @return self |
||
285 | */ |
||
286 | 32 | public function setMaxSize($maxSize) |
|
292 | |||
293 | /** |
||
294 | * Set cache options. |
||
295 | * |
||
296 | * @param string|null $key |
||
297 | * @param \Carbon\Carbon|\Datetime|int|null $duration |
||
298 | * @param bool $useCache |
||
299 | */ |
||
300 | 32 | public function setCache($key = null, $duration = null, $useCache = true) |
|
306 | |||
307 | /** |
||
308 | * Get the cache enabled value. |
||
309 | * |
||
310 | * @return bool |
||
311 | */ |
||
312 | 8 | public function isCacheEnabled() |
|
316 | |||
317 | /** |
||
318 | * Set the cache enabled value. |
||
319 | * |
||
320 | * @param bool $cacheEnabled |
||
321 | * |
||
322 | * @return self |
||
323 | */ |
||
324 | 32 | public function setCacheEnabled($cacheEnabled) |
|
330 | |||
331 | /** |
||
332 | * Get the cache key value. |
||
333 | * |
||
334 | * @return string |
||
335 | */ |
||
336 | 8 | public function getCacheKey() |
|
340 | |||
341 | /** |
||
342 | * Set the cache key value. |
||
343 | * |
||
344 | * @param string $key |
||
345 | * |
||
346 | * @return self |
||
347 | */ |
||
348 | 32 | public function setCacheKey($key) |
|
356 | |||
357 | /** |
||
358 | * Get the cache duration value. |
||
359 | * |
||
360 | * @return int |
||
361 | */ |
||
362 | 8 | public function getCacheDuration() |
|
366 | |||
367 | /** |
||
368 | * Set cache duration value. |
||
369 | * |
||
370 | * @param int $duration |
||
371 | * |
||
372 | * @return self |
||
373 | */ |
||
374 | 32 | public function setCacheDuration($duration) |
|
382 | |||
383 | /** |
||
384 | * Checks if content is cached. |
||
385 | * |
||
386 | * @return bool |
||
387 | */ |
||
388 | public function isCached() |
||
392 | |||
393 | /** |
||
394 | * Get the use limit size value. |
||
395 | * |
||
396 | * @return bool |
||
397 | */ |
||
398 | 8 | public function getUseLimitSize() |
|
402 | |||
403 | /** |
||
404 | * Set the use limit size value. |
||
405 | * |
||
406 | * @param bool $useLimitSize |
||
407 | * |
||
408 | * @return self |
||
409 | */ |
||
410 | 32 | public function setUseLimitSize($useLimitSize) |
|
416 | |||
417 | /** |
||
418 | * Limit size of $items array to 50000 elements (1000 for google-news). |
||
419 | * |
||
420 | * @param int $max |
||
421 | * |
||
422 | * @return $this |
||
423 | */ |
||
424 | public function limitSize($max = 50000) |
||
430 | |||
431 | /** |
||
432 | * Get the use styles value. |
||
433 | * |
||
434 | * @return bool |
||
435 | */ |
||
436 | 8 | public function getUseStyles() |
|
440 | |||
441 | /** |
||
442 | * Set the use styles value. |
||
443 | * |
||
444 | * @param bool $useStyles |
||
445 | * |
||
446 | * @return self |
||
447 | */ |
||
448 | 8 | public function setUseStyles($useStyles) |
|
454 | |||
455 | /* ------------------------------------------------------------------------------------------------ |
||
456 | | Main Functions |
||
457 | | ------------------------------------------------------------------------------------------------ |
||
458 | */ |
||
459 | /** |
||
460 | * Add new sitemap item to $items array. |
||
461 | * |
||
462 | * @param string $loc |
||
463 | * @param string|null $lastmod |
||
464 | * @param string|null $priority |
||
465 | * @param string|null $freq |
||
466 | * @param array $images |
||
467 | * @param string|null $title |
||
468 | * @param array $translations |
||
469 | * @param array $videos |
||
470 | * @param array $googlenews |
||
471 | * @param array $alternates |
||
472 | */ |
||
473 | 8 | public function add( |
|
482 | |||
483 | /** |
||
484 | * Add a new sitemap item. |
||
485 | * |
||
486 | * @param array $params |
||
487 | */ |
||
488 | 16 | public function addItem($params = []) |
|
492 | |||
493 | /** |
||
494 | * Add multiple sitemap items. |
||
495 | * |
||
496 | * @param array $items |
||
497 | */ |
||
498 | 8 | public function addItems(array $items) |
|
502 | |||
503 | /** |
||
504 | * Add new sitemap to $sitemaps array. |
||
505 | * |
||
506 | * @param string $loc |
||
507 | * @param string|null $lastmod |
||
508 | */ |
||
509 | public function addSitemap($loc, $lastmod = null) |
||
513 | |||
514 | /** |
||
515 | * Returns document with all sitemap items from $items array. |
||
516 | * |
||
517 | * @param string $format (options: xml, html, txt, ror-rss, ror-rdf, google-news) |
||
518 | * @param string $style (path to custom xls style like '/styles/xsl/xml-sitemap.xsl') |
||
519 | * |
||
520 | * @return \Symfony\Component\HttpFoundation\Response|\Illuminate\Contracts\Routing\ResponseFactory|array |
||
521 | */ |
||
522 | public function render($format = 'xml', $style = null) |
||
538 | |||
539 | /** |
||
540 | * Generates document with all sitemap items from $items array. |
||
541 | * |
||
542 | * @param string $format (options: xml, html, txt, ror-rss, ror-rdf, sitemapindex, google-news) |
||
543 | * @param string|null $style (path to custom xls style like '/styles/xsl/xml-sitemap.xsl') |
||
544 | * |
||
545 | * @return array |
||
546 | */ |
||
547 | public function generate($format = 'xml', $style = null) |
||
604 | |||
605 | /** |
||
606 | * Generate sitemap and store it to a file. |
||
607 | * |
||
608 | * @param string $format (options: xml, html, txt, ror-rss, ror-rdf, sitemapindex, google-news) |
||
609 | * @param string $filename (without file extension, may be a path like 'sitemaps/sitemap1' but must exist) |
||
610 | * @param string $path (path to store sitemap like '/www/site/public') |
||
611 | * @param string $style (path to custom xls style like '/styles/xsl/xml-sitemap.xsl') |
||
612 | * |
||
613 | * @return bool |
||
614 | */ |
||
615 | public function store($format = 'xml', $filename = 'sitemap', $path = null, $style = null) |
||
697 | |||
698 | /** |
||
699 | * Reset the sitemaps container. |
||
700 | * |
||
701 | * @param array $sitemaps |
||
702 | * |
||
703 | * @return self |
||
704 | */ |
||
705 | 32 | public function resetSitemaps(array $sitemaps = []) |
|
711 | |||
712 | /** |
||
713 | * Reset the items array. |
||
714 | * |
||
715 | * @param array $items |
||
716 | * |
||
717 | * @return self |
||
718 | */ |
||
719 | 32 | public function resetItems(array $items = []) |
|
725 | } |
||
726 |
If you return a value from a function or method, it should be a sub-type of the type that is given by the parent type f.e. an interface, or abstract method. This is more formally defined by the Lizkov substitution principle, and guarantees that classes that depend on the parent type can use any instance of a child type interchangably. This principle also belongs to the SOLID principles for object oriented design.
Let’s take a look at an example:
Our function
my_function
expects aPost
object, and outputs the author of the post. The base classPost
returns a simple string and outputting a simple string will work just fine. However, the child classBlogPost
which is a sub-type ofPost
instead decided to return anobject
, and is therefore violating the SOLID principles. If aBlogPost
were passed tomy_function
, PHP would not complain, but ultimately fail when executing thestrtoupper
call in its body.