Passed
Push — develop ( 37d230...30ebd1 )
by Brent
03:14
created

PaginationAdapter   A

Complexity

Total Complexity 16

Size/Duplication

Total Lines 146
Duplicated Lines 0 %

Coupling/Cohesion

Components 1
Dependencies 2

Test Coverage

Coverage 98.36%

Importance

Changes 0
Metric Value
dl 0
loc 146
ccs 60
cts 61
cp 0.9836
rs 10
c 0
b 0
f 0
wmc 16
lcom 1
cbo 2

10 Methods

Rating   Name   Duplication   Size   Complexity  
A __construct() 0 13 2
A make() 0 6 1
A transform() 0 21 2
A isValidConfiguration() 0 7 3
A getEntries() 0 9 1
A createPageConfiguration() 0 19 1
A createPaginationVariable() 0 12 1
A createPreviousPagination() 0 15 2
A createNextPagination() 0 16 2
A createPaginatedUrl() 0 4 1
1
<?php
2
3
namespace Stitcher\Page\Adapter;
4
5
use Stitcher\Exception\InvalidPaginationAdapter;
6
use Stitcher\Page\Adapter;
7
use Stitcher\Configureable;
8
use Stitcher\Variable\VariableParser;
9
10
class PaginationAdapter implements Adapter, Configureable
11
{
12
    /** @var \Stitcher\Variable\VariableParser */
13
    private $variableParser;
14
15
    /** @var mixed */
16
    private $variable;
17
18
    /** @var int */
19
    private $perPage;
20
21
    /** @var string */
22
    private $parameter;
23
24 16
    public function __construct(
25
        array $adapterConfiguration,
26
        VariableParser $variableParser
27
    ) {
28 16
        if (! $this->isValidConfiguration($adapterConfiguration)) {
29
            throw InvalidPaginationAdapter::create();
30
        }
31
32 16
        $this->variable = $adapterConfiguration['variable'];
33 16
        $this->parameter = $adapterConfiguration['parameter'];
34 16
        $this->perPage = $adapterConfiguration['perPage'] ?? 12;
35 16
        $this->variableParser = $variableParser;
36 16
    }
37
38 16
    public static function make(
39
        array $adapterConfiguration,
40
        VariableParser $variableParser
41
    ): PaginationAdapter {
42 16
        return new self($adapterConfiguration, $variableParser);
43
    }
44
45 15
    public function transform(array $pageConfiguration): array
46
    {
47 15
        $paginationPageConfiguration = [];
48 15
        $entries = $this->getEntries($pageConfiguration);
49 15
        $pageCount = (int) ceil(count($entries) / $this->perPage);
50
51 15
        for ($pageIndex = 1; $pageIndex <= $pageCount; $pageIndex++) {
52 15
            $entriesForPage = array_splice($entries, 0, $this->perPage);
53
54 15
            $entryConfiguration = $this->createPageConfiguration(
55 15
                $pageConfiguration,
56 15
                $entriesForPage,
57 15
                $pageIndex,
58 15
                $pageCount
59
            );
60
61 15
            $paginationPageConfiguration[$entryConfiguration['id']] = $entryConfiguration;
62
        }
63
64 15
        return $paginationPageConfiguration;
65
    }
66
67 16
    public function isValidConfiguration($subject): bool
68
    {
69
        return
70 16
            is_array($subject)
71 16
            && isset($subject['variable'])
72 16
            && isset($subject['parameter']);
73
    }
74
75 15
    protected function getEntries(array $pageConfiguration): ?array
76
    {
77 15
        $variable = $pageConfiguration['variables'][$this->variable] ?? null;
78 15
        $entries = $this->variableParser->parse($variable)['entries']
79 15
            ?? $this->variableParser->parse($variable)
80 15
            ?? $variable;
81
82 15
        return $entries;
83
    }
84
85 15
    protected function createPageConfiguration(
86
        array $entryConfiguration,
87
        array $entriesForPage,
88
        int $pageIndex,
89
        int $pageCount
90
    ): array {
91 15
        $pageId = rtrim($entryConfiguration['id'], '/');
92 15
        $paginatedId = $this->createPaginatedUrl($pageId, $pageIndex);
93
94 15
        $entryConfiguration['id'] = $paginatedId;
95 15
        $entryConfiguration['variables'][$this->variable] = $entriesForPage;
96
97 15
        $paginationVariable = $this->createPaginationVariable($pageId, $pageIndex, $pageCount);
98 15
        $entryConfiguration['variables']['_pagination'] = $paginationVariable;
99
100 15
        unset($entryConfiguration['config']['pagination']);
101
102 15
        return $entryConfiguration;
103
    }
104
105 15
    protected function createPaginationVariable(
106
        string $pageId,
107
        int $pageIndex,
108
        int $pageCount
109
    ): array {
110
        return [
111 15
            'current'  => $pageIndex,
112 15
            'previous' => $this->createPreviousPagination($pageId, $pageIndex),
113 15
            'next'     => $this->createNextPagination($pageId, $pageIndex, $pageCount),
114 15
            'pages'    => $pageCount,
115
        ];
116
    }
117
118 15
    protected function createPreviousPagination(
119
        string $pageId,
120
        int $pageIndex
121
    ): ?array {
122 15
        if ($pageIndex <= 1) {
123 15
            return null;
124
        }
125
126 15
        $previous = $pageIndex - 1;
127
128
        return [
129 15
            'url'   => $this->createPaginatedUrl($pageId, $previous),
130 15
            'index' => $previous,
131
        ];
132
    }
133
134 15
    protected function createNextPagination(
135
        string $pageId,
136
        int $pageIndex,
137
        int $pageCount
138
    ): ?array {
139 15
        if ($pageIndex >= $pageCount) {
140 15
            return null;
141
        }
142
143 15
        $next = $pageIndex + 1;
144
145
        return [
146 15
            'url'   => $this->createPaginatedUrl($pageId, $next),
147 15
            'index' => $next,
148
        ];
149
    }
150
151 15
    protected function createPaginatedUrl(string $pageId, int $index): string
152
    {
153 15
        return str_replace('{' .$this->parameter. '}', $index, $pageId);
154
    }
155
}
156