Passed
Pull Request — master (#1696)
by Arnaud
08:39 queued 03:42
created

Pagination::generate()   F

Complexity

Conditions 20
Paths 264

Size

Total Lines 122
Code Lines 83

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 88
CRAP Score 20.0143

Importance

Changes 3
Bugs 0 Features 0
Metric Value
cc 20
eloc 83
c 3
b 0
f 0
nc 264
nop 0
dl 0
loc 122
ccs 88
cts 91
cp 0.967
crap 20.0143
rs 2.5333

How to fix   Long Method    Complexity   

Long Method

Small methods make your code easier to understand, in particular if combined with a good name. Besides, if your method is small, finding a good name is usually much easier.

For example, if you find yourself adding comments to a method's body, this is usually a good sign to extract the commented part to a new method, and use the comment as a starting point when coming up with a good name for this new method.

Commonly applied refactorings include:

1
<?php
2
3
declare(strict_types=1);
4
5
/*
6
 * This file is part of Cecil.
7
 *
8
 * Copyright (c) Arnaud Ligny <[email protected]>
9
 *
10
 * For the full copyright and license information, please view the LICENSE
11
 * file that was distributed with this source code.
12
 */
13
14
namespace Cecil\Generator;
15
16
use Cecil\Collection\Page\Collection as PagesCollection;
17
use Cecil\Collection\Page\Page;
18
use Cecil\Collection\Page\Type;
19
20
/**
21
 * Class Generator\Pagination.
22
 */
23
class Pagination extends AbstractGenerator implements GeneratorInterface
24
{
25
    /**
26
     * {@inheritdoc}
27
     */
28 1
    public function generate(): void
29
    {
30 1
        if ($this->config->get('pagination.enabled') === false) {
31
            return;
32
        }
33
34
        // filters list pages (home, sections and terms)
35 1
        $filteredPages = $this->builder->getPages()->filter(function (Page $page) {
36 1
            return \in_array($page->getType(), [Type::HOMEPAGE, Type::SECTION, Type::TERM]);
37 1
        });
38
        /** @var Page $page */
39 1
        foreach ($filteredPages as $page) {
40 1
            $pages = $page->getPages()->filter(function (Page $page) {
41 1
                return $page->getVariable('published');
42 1
            });
43
            // if no sub-pages: by-pass
44 1
            if ($pages === null) {
45
                continue;
46
            }
47 1
            $path = $page->getPath();
48 1
            $sortby = $page->getVariable('sortby');
49
            // site pagination configuration
50 1
            $paginationPerPage = intval($this->config->get('pagination.max') ?? 5);
51 1
            $paginationPath = (string) $this->config->get('pagination.path') ?? 'page';
52
            // page pagination configuration
53 1
            $pagePagination = $page->getVariable('pagination');
54 1
            if ($pagePagination) {
55 1
                if (isset($pagePagination['enabled']) && $pagePagination['enabled'] == false) {
56
                    continue;
57
                }
58 1
                if (isset($pagePagination['max'])) {
59 1
                    $paginationPerPage = intval($pagePagination['max']);
60
                }
61 1
                if (isset($pagePagination['path'])) {
62 1
                    $paginationPath = (string) $pagePagination['path'];
63
                }
64
            }
65 1
            $pagesTotal = count($pages);
66
            // is pagination not necessary?
67 1
            if ($pagesTotal <= $paginationPerPage) {
68 1
                continue;
69
            }
70
            // sorts pages
71 1
            $pages = $pages->sortByDate();
72 1
            if ($sortby) {
73 1
                $sortMethod = \sprintf('sortBy%s', ucfirst($sortby));
74 1
                if (method_exists($pages, $sortMethod)) {
75 1
                    $pages = $pages->$sortMethod();
76
                }
77
            }
78
            // builds paginator
79 1
            $paginatorPagesCount = \intval(ceil($pagesTotal / $paginationPerPage));
80 1
            for ($i = 0; $i < $paginatorPagesCount; $i++) {
81 1
                $itPagesInPagination = new \LimitIterator($pages->getIterator(), ($i * $paginationPerPage), $paginationPerPage);
82 1
                $pagesInPagination = new PagesCollection(
83 1
                    $page->getId() . '-page-' . ($i + 1),
84 1
                    iterator_to_array($itPagesInPagination)
85 1
                );
86 1
                $alteredPage = clone $page;
87
                // first page (ie: blog/page/1 -> blog)
88 1
                if ($i == 0) {
89 1
                    $pageId = $page->getId();
90 1
                    $alteredPage
91 1
                        ->setVariable('alias', [
92 1
                            \sprintf('%s/%s/%s', $path, $paginationPath, 1),
93 1
                        ]);
94
                // others pages (ie: blog/page/X)
95
                } else {
96 1
                    $pageId = Page::slugify(\sprintf('%s/%s/%s', $page->getId(), $paginationPath, $i + 1));
97 1
                    $alteredPage
98 1
                        ->setId($pageId)
99 1
                        ->setVirtual(true)
100 1
                        ->setPath(Page::slugify(\sprintf('%s/%s/%s', $path, $paginationPath, $i + 1)))
101 1
                        ->unVariable('menu')
102 1
                        ->unVariable('alias')
103 1
                        ->unVariable('aliases') // backward compatibility
104 1
                        ->unVariable('langref')
105 1
                        ->setVariable('paginated', true);
106
                }
107
                // set paginator values
108 1
                $paginator = [
109 1
                    'totalpages' => $pagesTotal,
110 1
                    'pages'      => $pagesInPagination,
111 1
                    'count'      => $paginatorPagesCount,
112 1
                    'current'    => $i + 1,
113 1
                ];
114
                // adds links
115 1
                $paginator['links'] = ['first' => $page->getId() ?: 'index'];
116 1
                if ($i == 1) {
117 1
                    $paginator['links'] += ['prev' => $page->getId() ?: 'index'];
118
                }
119 1
                if ($i > 1) {
120 1
                    $paginator['links'] += ['prev' => Page::slugify(\sprintf(
121 1
                        '%s/%s/%s',
122 1
                        $page->getId(),
123 1
                        $paginationPath,
124 1
                        $i
125 1
                    ))];
126
                }
127 1
                $paginator['links'] += ['self' => $pageId ?: 'index'];
128 1
                if ($i < $paginatorPagesCount - 1) {
129 1
                    $paginator['links'] += ['next' => Page::slugify(\sprintf(
130 1
                        '%s/%s/%s',
131 1
                        $page->getId(),
132 1
                        $paginationPath,
133 1
                        $i + 2
134 1
                    ))];
135
                }
136 1
                $paginator['links'] += ['last' => Page::slugify(\sprintf(
137 1
                    '%s/%s/%s',
138 1
                    $page->getId(),
139 1
                    $paginationPath,
140 1
                    $paginatorPagesCount
141 1
                ))];
142 1
                $paginator['links'] += ['path' => Page::slugify(\sprintf('%s/%s', $page->getId(), $paginationPath))];
143
                // set paginator to cloned page
144 1
                $alteredPage->setPaginator($paginator);
145 1
                $alteredPage->setVariable('pagination', $paginator); // backward compatibility
146
                // updates date with the first element of the collection
147 1
                $alteredPage->setVariable('date', $pagesInPagination->first()->getVariable('date'));
148
149 1
                $this->generatedPages->add($alteredPage);
150
            }
151
        }
152
    }
153
}
154