Passed
Push — master ( 019716...f69765 )
by Alexander
07:16
created

OffsetPaginatorTest.php$0 ➔ testDataReaderWithoutOffsetableInterface()   A

Complexity

Conditions 1

Size

Total Lines 27

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 1
dl 0
loc 27
rs 9.488
c 0
b 0
f 0
1
<?php
2
3
declare(strict_types=1);
4
5
namespace Yiisoft\Data\Tests\Paginator;
6
7
use Yiisoft\Data\Paginator\OffsetPaginator;
8
use Yiisoft\Data\Paginator\PaginatorException;
9
use Yiisoft\Data\Reader\CountableDataInterface;
10
use Yiisoft\Data\Reader\Iterable\IterableDataReader;
11
use Yiisoft\Data\Reader\DataReaderInterface;
12
use Yiisoft\Data\Reader\OffsetableDataInterface;
13
use Yiisoft\Data\Tests\TestCase;
14
15
final class OffsetPaginatorTest extends TestCase
16
{
17
    private function getDataSet(): array
18
    {
19
        return [
20
            [
21
                'id' => 1,
22
                'name' => 'Codename Boris',
23
            ],
24
            [
25
                'id' => 2,
26
                'name' => 'Codename Doris',
27
            ],
28
            [
29
                'id' => 3,
30
                'name' => 'Agent K',
31
            ],
32
            [
33
                'id' => 5,
34
                'name' => 'Agent J',
35
            ],
36
            [
37
                'id' => 6,
38
                'name' => '007',
39
            ],
40
        ];
41
    }
42
43
    public function testDataReaderWithoutOffsetableInterface(): void
44
    {
45
        $nonOffsetableDataReader = new class() implements DataReaderInterface, CountableDataInterface {
46
            public function withLimit(int $limit)
47
            {
48
                // do nothing
49
            }
50
51
            public function read(): iterable
52
            {
53
                return [];
54
            }
55
            public function count(): int
56
            {
57
                return 0;
58
            }
59
        };
60
61
        $this->expectException(\InvalidArgumentException::class);
62
        $this->expectExceptionMessage(
63
            sprintf(
64
                'Data reader should implement %s in order to be used with offset paginator',
65
                OffsetableDataInterface::class
66
            )
67
        );
68
69
        new OffsetPaginator($nonOffsetableDataReader);
70
    }
71
72
    public function testDataReaderWithoutCountableInterface(): void
73
    {
74
        $nonCountableDataReader = new class() implements DataReaderInterface, OffsetableDataInterface {
75
            public function withLimit(int $limit)
76
            {
77
                // do nothing
78
            }
79
            public function read(): iterable
80
            {
81
                return [];
82
            }
83
            public function count(): int
84
            {
85
                return 0;
86
            }
87
            public function withOffset(int $offset)
88
            {
89
                // do nothing
90
            }
91
        };
92
93
        $this->expectException(\InvalidArgumentException::class);
94
        $this->expectExceptionMessage(
95
            sprintf(
96
                'Data reader should implement %s in order to be used with offset paginator',
97
                CountableDataInterface::class
98
            )
99
        );
100
101
        new OffsetPaginator($nonCountableDataReader);
102
    }
103
104
    public function testDefaultState(): void
105
    {
106
        $dataReader = new IterableDataReader($this->getDataSet());
107
        $paginator = new OffsetPaginator($dataReader);
108
109
        $this->assertSame(0, $paginator->getOffset());
110
        $this->assertSame(1, $paginator->getCurrentPage());
111
        $this->assertTrue($paginator->isOnFirstPage());
112
        $this->assertFalse($paginator->isRequired());
113
    }
114
115
    public function testIsRequired(): void
116
    {
117
        $dataReader = new IterableDataReader($this->getDataSet());
118
        $paginator = (new OffsetPaginator($dataReader))
119
            ->withPageSize(2);
120
121
        $this->assertTrue($paginator->isRequired());
122
    }
123
124
    public function testGetTotalItems(): void
125
    {
126
        $dataReader = new IterableDataReader($this->getDataSet());
127
        $paginator = new OffsetPaginator($dataReader);
128
129
        $this->assertSame(5, $paginator->getTotalItems());
130
    }
131
132
    public function testWithCurrentPage(): void
133
    {
134
        $dataReader = new IterableDataReader($this->getDataSet());
135
        $paginator = new OffsetPaginator($dataReader);
136
        $newPaginator = $paginator->withCurrentPage(20);
137
138
        $this->assertSame(1, $paginator->getCurrentPage());
139
        $this->assertSame(20, $newPaginator->getCurrentPage());
140
    }
141
142
    public function testCurrentPageCannotBeLessThanOne(): void
143
    {
144
        $dataReader = new IterableDataReader($this->getDataSet());
145
        $paginator = new OffsetPaginator($dataReader);
146
147
        $this->expectException(PaginatorException::class);
148
        $paginator->withCurrentPage(0);
149
    }
150
151
    public function testCurrentPageCannotBeLargerThanMaxPages(): void
152
    {
153
        $dataReader = new IterableDataReader($this->getDataSet());
154
        $paginator = (new OffsetPaginator($dataReader))
155
            ->withPageSize(2)
156
            ->withCurrentPage(4);
157
158
        $this->assertSame(3, $paginator->getTotalPages());
159
        $this->expectException(PaginatorException::class);
160
        $this->iterableToArray($paginator->read());
161
    }
162
163
    public function testWithPageSize(): void
164
    {
165
        $dataReader = new IterableDataReader($this->getDataSet());
166
        $paginator = new OffsetPaginator($dataReader);
167
        $newPaginator = $paginator->withPageSize(125);
168
169
        $this->assertSame(OffsetPaginator::DEFAULT_PAGE_SIZE, $paginator->getPageSize());
170
        $this->assertSame(125, $newPaginator->getPageSize());
171
    }
172
173
    public function testPageSizeCannotBeLessThanOne(): void
174
    {
175
        $dataReader = new IterableDataReader($this->getDataSet());
176
        $paginator = new OffsetPaginator($dataReader);
177
178
        $this->expectException(PaginatorException::class);
179
        $paginator->withPageSize(0);
180
    }
181
182
    public function testReadFirstPage(): void
183
    {
184
        $dataReader = new IterableDataReader($this->getDataSet());
185
186
        $paginator = (new OffsetPaginator($dataReader))
187
            ->withPageSize(2)
188
            ->withCurrentPage(1);
189
190
        $expected = [
191
            [
192
                'id' => 1,
193
                'name' => 'Codename Boris',
194
            ],
195
            [
196
                'id' => 2,
197
                'name' => 'Codename Doris',
198
            ],
199
        ];
200
201
        $this->assertSame($expected, $this->iterableToArray($paginator->read()));
202
    }
203
204
    public function testReadSecondPage(): void
205
    {
206
        $dataReader = new IterableDataReader($this->getDataSet());
207
208
        $paginator = (new OffsetPaginator($dataReader))
209
            ->withPageSize(2)
210
            ->withCurrentPage(2);
211
212
        $expected = [
213
            [
214
                'id' => 3,
215
                'name' => 'Agent K',
216
            ],
217
            [
218
                'id' => 5,
219
                'name' => 'Agent J',
220
            ],
221
        ];
222
223
        $this->assertSame($expected, $this->iterableToArray($paginator->read()));
224
    }
225
226
    public function testReadLastPage(): void
227
    {
228
        $dataReader = new IterableDataReader($this->getDataSet());
229
230
        $paginator = (new OffsetPaginator($dataReader))
231
            ->withPageSize(2)
232
            ->withCurrentPage(3);
233
234
        $expected = [
235
            [
236
                'id' => 6,
237
                'name' => '007',
238
            ],
239
        ];
240
241
        $this->assertSame($expected, $this->iterableToArray($paginator->read()));
242
    }
243
244
    public function testTotalPages(): void
245
    {
246
        $dataReader = new IterableDataReader($this->getDataSet());
247
        $paginator = (new OffsetPaginator($dataReader))
248
            ->withPageSize(2);
249
250
        $this->assertSame(3, $paginator->getTotalPages());
251
    }
252
253
    public function testIsFirstPageOnFirstPage(): void
254
    {
255
        $dataReader = new IterableDataReader($this->getDataSet());
256
        $paginator = (new OffsetPaginator($dataReader))
257
            ->withPageSize(2)
258
            ->withCurrentPage(1);
259
260
        $this->assertTrue($paginator->isOnFirstPage());
261
    }
262
263
    public function testIsFirstPageOnSecondPage(): void
264
    {
265
        $dataReader = new IterableDataReader($this->getDataSet());
266
        $paginator = (new OffsetPaginator($dataReader))
267
            ->withPageSize(2)
268
            ->withCurrentPage(2);
269
270
        $this->assertFalse($paginator->isOnFirstPage());
271
    }
272
273
    public function testIsLastPageOnFirstPage(): void
274
    {
275
        $dataReader = new IterableDataReader($this->getDataSet());
276
        $paginator = (new OffsetPaginator($dataReader))
277
            ->withPageSize(2)
278
            ->withCurrentPage(1);
279
280
        $this->assertFalse($paginator->isOnLastPage());
281
    }
282
283
    public function testIsLastPageOnLastPage(): void
284
    {
285
        $dataReader = new IterableDataReader($this->getDataSet());
286
        $paginator = (new OffsetPaginator($dataReader))
287
            ->withPageSize(2)
288
            ->withCurrentPage(3);
289
290
        $this->assertTrue($paginator->isOnLastPage());
291
    }
292
293
    public function testIsLastPageBeyondMaxPages(): void
294
    {
295
        $dataReader = new IterableDataReader($this->getDataSet());
296
        $paginator = (new OffsetPaginator($dataReader))
297
            ->withPageSize(2)
298
            ->withCurrentPage(4);
299
300
        $this->assertSame(3, $paginator->getTotalPages());
301
        $this->expectException(PaginatorException::class);
302
303
        $paginator->isOnLastPage();
304
    }
305
306
    public function testGetCurrentPageSizeFirstFullPage(): void
307
    {
308
        $dataReader = new IterableDataReader($this->getDataSet());
309
        $paginator = (new OffsetPaginator($dataReader))
310
            ->withPageSize(3);
311
312
        $this->assertSame(3, $paginator->getCurrentPageSize());
313
    }
314
315
    public function testGetCurrentPageSizeLastPage(): void
316
    {
317
        $dataReader = new IterableDataReader($this->getDataSet());
318
        $paginator = (new OffsetPaginator($dataReader))
319
            ->withPageSize(3)
320
            ->withCurrentPage(2);
321
322
        $this->assertSame(2, $paginator->getCurrentPageSize());
323
        $this->assertSame(5, $paginator->getTotalItems());
324
    }
325
326
    public function testGetCurrentPageSizeFirstNotFullPage(): void
327
    {
328
        $dataReader = new IterableDataReader($this->getDataSet());
329
        $paginator = (new OffsetPaginator($dataReader))
330
            ->withPageSize(30);
331
332
        $this->assertSame(5, $paginator->getCurrentPageSize());
333
        $this->assertSame(5, $paginator->getTotalItems());
334
    }
335
336
    public function testEmptyDataSet(): void
337
    {
338
        $dataReader = new IterableDataReader([]);
339
        $paginator = new OffsetPaginator($dataReader);
340
341
        $this->assertSame(0, $paginator->getTotalItems());
342
        $this->assertSame(0, $paginator->getTotalPages());
343
        $this->assertSame(0, $paginator->getCurrentPageSize());
344
        $this->assertSame(1, $paginator->getCurrentPage());
345
        $this->assertTrue($paginator->isOnFirstPage());
346
        $this->assertTrue($paginator->isOnLastPage());
347
        $this->assertFalse($paginator->isRequired());
348
        $this->assertSame([], $this->iterableToArray($paginator->read()));
349
    }
350
}
351