Completed
Push — master ( 4b418f...791c35 )
by Joschi
02:31
created

UrlTest::testUrlSchemeSetter()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 6
Code Lines 4

Duplication

Lines 0
Ratio 0 %

Importance

Changes 2
Bugs 0 Features 0
Metric Value
c 2
b 0
f 0
dl 0
loc 6
rs 9.4285
cc 1
eloc 4
nc 1
nop 0
1
<?php
2
3
/**
4
 * apparat-object
5
 *
6
 * @category    Apparat
7
 * @package     Apparat\Object
8
 * @subpackage  Apparat\Object\Infrastructure
9
 * @author      Joschi Kuphal <[email protected]> / @jkphl
10
 * @copyright   Copyright © 2016 Joschi Kuphal <[email protected]> / @jkphl
11
 * @license     http://opensource.org/licenses/MIT	The MIT License (MIT)
0 ignored issues
show
Coding Style introduced by
Spaces must be used for alignment; tabs are not allowed
Loading history...
12
 */
13
14
/***********************************************************************************
15
 *  The MIT License (MIT)
16
 *
17
 *  Copyright © 2016 Joschi Kuphal <[email protected]> / @jkphl
18
 *
19
 *  Permission is hereby granted, free of charge, to any person obtaining a copy of
20
 *  this software and associated documentation files (the "Software"), to deal in
21
 *  the Software without restriction, including without limitation the rights to
22
 *  use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
23
 *  the Software, and to permit persons to whom the Software is furnished to do so,
24
 *  subject to the following conditions:
25
 *
26
 *  The above copyright notice and this permission notice shall be included in all
27
 *  copies or substantial portions of the Software.
28
 *
29
 *  THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
30
 *  IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
31
 *  FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
32
 *  COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
33
 *  IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
34
 *  CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
35
 ***********************************************************************************/
36
37
namespace Apparat\Object\Domain\Model\Path\ObjectUrl {
38
39
    use Apparat\Object\Domain\Model\Path\ObjectUrl;
40
41
    /**
42
     * URL version with test extension
43
     *
44
     * @package Apparat\Resource
45
     */
46
    class TestUrl extends ObjectUrl
47
    {
48
        /**
49
         * Test the URL getter with override parameters
50
         */
51
        public function getUrlOverride()
52
        {
53
            $override = [
54
                'scheme' => ObjectUrl::SCHEME_HTTPS,
55
                'user' => 'user',
56
                'pass' => 'password',
57
                'host' => 'another.host',
58
                'port' => 443,
59
                'path' => '/path/prefix',
60
                'object' => '/2015/10/01/36704.event/36704-2',
61
                'query' => ['param2' => 'value2'],
62
                'fragment' => 'fragment2',
63
            ];
64
            return $this->_getUrl($override);
65
        }
66
    }
67
}
68
69
namespace Apparat\Object\Tests {
70
71
    use Apparat\Kernel\Tests\AbstractTest;
0 ignored issues
show
Coding Style introduced by
USE declarations must go after the first namespace declaration
Loading history...
72
    use Apparat\Object\Domain\Model\Object\Id;
0 ignored issues
show
Coding Style introduced by
USE declarations must go after the first namespace declaration
Loading history...
73
    use Apparat\Object\Domain\Model\Object\Revision;
0 ignored issues
show
Coding Style introduced by
USE declarations must go after the first namespace declaration
Loading history...
74
    use Apparat\Object\Domain\Model\Object\Type;
0 ignored issues
show
Coding Style introduced by
USE declarations must go after the first namespace declaration
Loading history...
75
    use Apparat\Object\Domain\Model\Path\ApparatUrl;
0 ignored issues
show
Coding Style introduced by
USE declarations must go after the first namespace declaration
Loading history...
76
    use Apparat\Object\Domain\Model\Path\LocalPath;
0 ignored issues
show
Coding Style introduced by
USE declarations must go after the first namespace declaration
Loading history...
77
    use Apparat\Object\Domain\Model\Path\ObjectUrl;
0 ignored issues
show
Coding Style introduced by
USE declarations must go after the first namespace declaration
Loading history...
78
    use Apparat\Object\Domain\Model\Path\Url;
0 ignored issues
show
Coding Style introduced by
USE declarations must go after the first namespace declaration
Loading history...
79
    use Apparat\Object\Domain\Repository\Service;
0 ignored issues
show
Coding Style introduced by
USE declarations must go after the first namespace declaration
Loading history...
80
    use Apparat\Object\Infrastructure\Repository\FileAdapterStrategy;
0 ignored issues
show
Coding Style introduced by
USE declarations must go after the first namespace declaration
Loading history...
81
    use Apparat\Object\Ports\Repository;
0 ignored issues
show
Coding Style introduced by
USE declarations must go after the first namespace declaration
Loading history...
82
83
    /**
84
     * Object URL tests
85
     *
86
     * @package Apparat\Object
87
     * @subpackage ApparatTest
88
     */
89
    class UrlTest extends AbstractTest
0 ignored issues
show
Coding Style Compatibility introduced by
PSR1 recommends that each class should be in its own file to aid autoloaders.

Having each class in a dedicated file usually plays nice with PSR autoloaders and is therefore a well established practice. If you use other autoloaders, you might not want to follow this rule.

Loading history...
90
    {
91
        /**
92
         * Example query fragment
93
         *
94
         * @var string
95
         */
96
        const QUERY_FRAGMENT = '?param=value#fragment';
97
        /**
98
         * Repository URL
99
         *
100
         * @var string
101
         */
102
        const REPOSITORY_URL = '/repo';
103
        /**
104
         * Example path
105
         *
106
         * @var string
107
         */
108
        const PATH = '/2015/10/01/36704.event/36704-1';
109
        /**
110
         * Example URL
111
         *
112
         * @var string
113
         */
114
        const URL = self::REPOSITORY_URL.self::PATH.self::QUERY_FRAGMENT;
115
        /**
116
         * Example URL
117
         *
118
         * @var string
119
         */
120
        const REMOTE_URL = 'http://apparat:[email protected]:80'.self::PATH.self::QUERY_FRAGMENT;
121
        /**
122
         * Example apparat URL
123
         *
124
         * @var string
125
         */
126
        const APPARAT_URL = 'aprts://apparat:[email protected]:80'.self::PATH.self::QUERY_FRAGMENT;
127
128
        /**
129
         * Setup
130
         */
131
        public static function setUpBeforeClass()
132
        {
133
            // Disable repository auto-connection
134
            Service::useAutoConnect(false);
135
        }
136
137
        /**
138
         * Test an URL
139
         *
140
         * @expectedException \Apparat\Object\Domain\Model\Path\InvalidArgumentException
141
         * @expectedExceptionCode 1451515385
142
         */
143
        public function testInvalidRemoteUrl()
144
        {
145
            new ObjectUrl(self::REMOTE_URL);
146
        }
147
148
        /**
149
         * Test an URL
150
         */
151
        public function testRemoteUrl()
152
        {
153
            $url = new ObjectUrl(self::REMOTE_URL, true);
154
            $this->assertInstanceOf(ObjectUrl::class, $url);
155
            $this->assertEquals(self::REMOTE_URL, strval($url));
156
            $this->assertEquals('http', $url->getScheme());
157
            $this->assertEquals('apparat', $url->getUser());
158
            $this->assertEquals('tools', $url->getPassword());
159
            $this->assertEquals('apparat.tools', $url->getHost());
160
            $this->assertEquals(80, $url->getPort());
161
            $this->assertEquals('', $url->getPath());
162
            $this->assertEquals(['param' => 'value'], $url->getQuery());
163
            $this->assertEquals('fragment', $url->getFragment());
164
            $this->assertInstanceOf(\DateTimeImmutable::class, $url->getCreationDate());
165
            $this->assertEquals('2015-10-01', $url->getCreationDate()->format('Y-m-d'));
166
            $this->assertInstanceOf(Id::class, $url->getId());
167
            $this->assertEquals(new Id(36704), $url->getId());
168
            $this->assertInstanceOf(Type::class, $url->getType());
169
            $this->assertEquals(new Type('event'), $url->getType());
170
            $this->assertInstanceOf(Revision::class, $url->getRevision());
171
            $this->assertEquals(new Revision(1), $url->getRevision());
172
        }
173
174
        /**
175
         * Test a local URL with path prefix
176
         */
177
        public function testLeadedLocalUrl()
178
        {
179
            $pathPrefix = '/prefix/path';
180
            $url = new ObjectUrl($pathPrefix.self::PATH);
181
            $this->assertEquals($pathPrefix, $url->getPath());
182
        }
183
184
        /**
185
         * Test an invalid URL
186
         *
187
         * @expectedException \Apparat\Object\Domain\Model\Path\InvalidArgumentException
188
         * @expectedExceptionCode 1449873819
189
         */
190
        public function testInvalidUrl()
191
        {
192
            new ObjectUrl('invalid://');
193
        }
194
195
        /**
196
         * Test an invalid URL path
197
         *
198
         * @expectedException \Apparat\Object\Domain\Model\Path\InvalidArgumentException
199
         * @expectedExceptionCode 1449874494
200
         */
201
        public function testInvalidUrlPath()
202
        {
203
            new ObjectUrl('http://invalid~url*path', true);
204
        }
205
206
        /**
207
         * Test the scheme setter
208
         *
209
         * @expectedException \Apparat\Object\Domain\Model\Path\InvalidArgumentException
210
         * @expectedExceptionCode 1449924914
211
         */
212
        public function testUrlSchemeSetter()
213
        {
214
            $url = new ObjectUrl(self::URL);
215
            $this->assertEquals(ObjectUrl::SCHEME_HTTPS, $url->setScheme(ObjectUrl::SCHEME_HTTPS)->getScheme());
216
            $url->setScheme('invalid');
217
        }
218
219
        /**
220
         * Test the host setter
221
         *
222
         * @expectedException \Apparat\Object\Domain\Model\Path\InvalidArgumentException
223
         * @expectedExceptionCode 1449925567
224
         */
225
        public function testUrlHostSetter()
226
        {
227
            $url = new ObjectUrl(self::URL);
228
            $this->assertEquals('apparat.com', $url->setHost('apparat.com')->getHost());
229
            $url->setHost('_');
230
        }
231
232
        /**
233
         * Test the port setter
234
         *
235
         * @expectedException \Apparat\Object\Domain\Model\Path\InvalidArgumentException
236
         * @expectedExceptionCode 1449925885
237
         */
238
        public function testUrlPortSetter()
239
        {
240
            $url = new ObjectUrl(self::URL);
241
            $this->assertEquals(443, $url->setPort(443)->getPort());
242
            $url->setPort(123456789);
243
        }
244
245
        /**
246
         * Test the remaining setter methods
247
         */
248
        public function testUrlSetters()
249
        {
250
            $url = new ObjectUrl(self::URL);
251
            $this->assertEquals('test', $url->setUser('test')->getUser());
252
            $this->assertEquals(null, $url->setUser(null)->getUser());
253
            $this->assertEquals('password', $url->setPassword('password')->getPassword());
254
            $this->assertEquals(null, $url->setPassword(null)->getPassword());
255
            $this->assertEquals('/path/prefix', $url->setPath('/path/prefix')->getPath());
256
            $this->assertEquals(['param2' => 'value2'], $url->setQuery(['param2' => 'value2'])->getQuery());
257
            $this->assertEquals('fragment2', $url->setFragment('fragment2')->getFragment());
258
259
            $this->assertEquals(
260
                '2016-01-01',
261
                $url->setCreationDate(new \DateTimeImmutable('@1451606400'))->getCreationDate()->format('Y-m-d')
262
            );
263
            $this->assertEquals(123, $url->setId(new Id(123))->getId()->getId());
0 ignored issues
show
Bug introduced by
The method getId cannot be called on $url->setId(new \Apparat...bject\Id(123))->getId() (of type integer).

Methods can only be called on objects. This check looks for methods being called on variables that have been inferred to never be objects.

Loading history...
264
            $this->assertEquals('article', $url->setType(new Type('article'))->getType()->getType());
265
            $this->assertEquals(
266
                Revision::CURRENT,
267
                $url->setRevision(new Revision(Revision::CURRENT))->getRevision()->getRevision()
268
            );
269
        }
270
271
        /**
272
         * Test the override functionality when getting the URL path
273
         */
274
        public function testUrlPathOverride()
275
        {
276
            $url = new ObjectUrl\TestUrl(self::URL);
277
            $this->assertEquals(
278
                'https://user:[email protected]:443/path/prefix/2015/10/01/36704.event/36704-2?param2=value2#fragment2',
279
                $url->getUrlOverride()
280
            );
281
        }
282
283
        /**
284
         * Test absolute URL
285
         */
286
        public function testUrlAbsolute()
287
        {
288
            $url = new ObjectUrl(self::REMOTE_URL, true);
289
            $this->assertEquals(true, $url->isAbsolute());
290
        }
291
292
        /**
293
         * Test relative URL
294
         */
295
        public function testUrlReative()
296
        {
297
            $url = new ObjectUrl(self::PATH.self::QUERY_FRAGMENT);
298
            $this->assertEquals(false, $url->isAbsolute());
299
        }
300
301
        /**
302
         * Test URL comparison
303
         */
304
        public function testUrlComparison()
305
        {
306
            $this->assertFalse((new Url('http://example.com'))->matches(new Url('https://example.com')));
307
            $this->assertFalse((new Url('http://[email protected]'))->matches(new Url('http://[email protected]')));
308
            $this->assertFalse(
309
                (new Url('http://user:[email protected]'))->matches(new Url('http://user:[email protected]'))
310
            );
311
            $this->assertFalse((new Url('http://example1.com'))->matches(new Url('http://example2.com')));
312
            $this->assertFalse((new Url('http://example.com:80'))->matches(new Url('http://example.com:443')));
313
            $this->assertFalse((new Url('http://example.com/a'))->matches(new Url('http://example.com/b')));
314
            $this->assertFalse((new Url('http://example.com/?a=1'))->matches(new Url('http://example.com/?a=2')));
315
            $this->assertFalse((new Url('http://example.com/#a'))->matches(new Url('http://example.com/#b')));
316
            $this->assertTrue((new Url(self::REMOTE_URL))->matches(new Url(self::REMOTE_URL)));
317
        }
318
319
        /**
320
         * Test object URL comparison
321
         */
322
        public function testObjectUrlComparison()
323
        {
324
            $this->assertFalse(
325
                (
326
                new ObjectUrl(
327
                    'http://example.com/2015/10/01/36704.event/36704-1',
328
                    true
329
                )
330
                )->matches(new ObjectUrl('https://example.com/2015/10/01/36704.event/36704-1', true))
331
            );
332
            $this->assertFalse(
333
                (
334
                new ObjectUrl(
335
                    'http://example.com/2015/10/01/36704.event/36704-1',
336
                    true
337
                )
338
                )->matches(new ObjectUrl('http://example.com/2016/10/01/36704.event/36704-1', true))
339
            );
340
            $this->assertFalse(
341
                (
342
                new ObjectUrl(
343
                    'http://example.com/2015/10/01/36704.event/36704-1',
344
                    true
345
                )
346
                )->matches(new ObjectUrl('http://example.com/2015/10/01/36705.event/36705-1', true))
347
            );
348
            $this->assertFalse(
349
                (
350
                new ObjectUrl(
351
                    'http://example.com/2015/10/01/36704.event/36704-1',
352
                    true
353
                )
354
                )->matches(new ObjectUrl('http://example.com/2015/10/01/36704.article/36704-1', true))
355
            );
356
            $this->assertFalse(
357
                (
358
                new ObjectUrl(
359
                    'http://example.com/2015/10/01/36704.event/36704-1',
360
                    true
361
                )
362
                )->matches(new ObjectUrl('http://example.com/2015/10/01/36704.event/36704-2', true))
363
            );
364
            $this->assertTrue((new ObjectUrl(self::REMOTE_URL, true))->matches(new ObjectUrl(self::REMOTE_URL, true)));
365
        }
366
367
        /**
368
         * Test an invalid apparat URL
369
         *
370
         * @expectedException \Apparat\Object\Domain\Model\Path\InvalidArgumentException
371
         * @expectedExceptionCode 1451435429
372
         */
373
        public function testInvalidApparatUrl()
374
        {
375
            new ApparatUrl(self::REMOTE_URL, true);
376
        }
377
378
        /**
379
         * Test an absolute apparat URL
380
         */
381
        public function testAbsoluteApparatUrl()
382
        {
383
            $apparatUrl = new ApparatUrl(self::APPARAT_URL, true);
384
            $this->assertInstanceOf(ApparatUrl::class, $apparatUrl);
385
        }
386
387
        /**
388
         * Test an unknown relative apparat URL
389
         *
390
         * @expectedException \Apparat\Object\Domain\Model\Path\ApparatInvalidArgumentException
391
         * @expectedExceptionCode 1452695654
392
         */
393
        public function testUnknownRelativeApparatUrl()
394
        {
395
            new ApparatUrl(self::PATH.self::QUERY_FRAGMENT);
396
        }
397
398
        /**
399
         * Test a relative apparat URL
400
         */
401
        public function testRelativeApparatUrl()
402
        {
403
            Repository::register(
404
                self::REPOSITORY_URL,
405
                [
406
                    'type' => FileAdapterStrategy::TYPE,
407
                    'root' => __DIR__,
408
                ]
409
            );
410
            $apparatUrl = new ApparatUrl(self::URL);
411
            $this->assertInstanceOf(ApparatUrl::class, $apparatUrl);
412
        }
413
414
        /**
415
         * Test invalid date precision
416
         *
417
         * @expectedException \Apparat\Object\Domain\Model\Path\InvalidArgumentException
418
         * @expectedExceptionCode 1451514114
419
         */
420
        public function testInvalidDatePrecision()
421
        {
422
            new LocalPath(self::PATH, -1);
423
        }
424
425
        /**
426
         * Test arbitrary date precision
427
         */
428
        public function testArbitraryDatePrecision()
429
        {
430
            $path = new LocalPath(self::PATH, true);
0 ignored issues
show
Documentation introduced by
true is of type boolean, but the function expects a null|object<Apparat\Obje...odel\Path\TRUE>|integer.

It seems like the type of the argument is not accepted by the function/method which you are calling.

In some cases, in particular if PHP’s automatic type-juggling kicks in this might be fine. In other cases, however this might be a bug.

We suggest to add an explicit type cast like in the following example:

function acceptsInteger($int) { }

$x = '123'; // string "123"

// Instead of
acceptsInteger($x);

// we recommend to use
acceptsInteger((integer) $x);
Loading history...
431
            $this->assertInstanceOf(LocalPath::class, $path);
432
        }
433
    }
434
}
435