Completed
Push — master ( 7f24e1...cf8767 )
by ignace nyamagana
06:36
created

ImmutableComponentTrait::getReservedRegex()   A

Complexity

Conditions 2
Paths 2

Size

Total Lines 8
Code Lines 5

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 3
CRAP Score 2.5

Importance

Changes 1
Bugs 0 Features 0
Metric Value
c 1
b 0
f 0
dl 0
loc 8
ccs 3
cts 6
cp 0.5
rs 9.4286
cc 2
eloc 5
nc 2
nop 0
crap 2.5
1
<?php
2
/**
3
 * League.Url (http://url.thephpleague.com)
4
 *
5
 * @package   League.url
6
 * @author    Ignace Nyamagana Butera <[email protected]>
7
 * @copyright 2013-2015 Ignace Nyamagana Butera
8
 * @license   https://github.com/thephpleague/uri/blob/master/LICENSE (MIT License)
9
 * @version   4.0.0
10
 * @link      https://github.com/thephpleague/uri/
11
 */
12
namespace League\Uri\Types;
13
14
use InvalidArgumentException;
15
use League\Uri\Interfaces\UriPart;
16
use ReflectionClass;
17
18
/**
19
 * Common methods for Component Value Object
20
 *
21
 * @package League.uri
22
 * @author  Ignace Nyamagana Butera <[email protected]>
23
 * @since   4.0.0
24
 */
25
trait ImmutableComponentTrait
26
{
27
    use ValidatorTrait;
28
29
    /**
30
     * Characters to conform to RFC3986 - http://tools.ietf.org/html/rfc3986#section-2
31
     *
32
     * @var array
33
     */
34
    protected static $characters_set = [
35
        '!', '$', '&', "'", '(', ')', '*', '+', ',', ';', '=', ':',
36
    ];
37
38
    protected static $characters_set_compiled;
39
40
    /**
41
     * Encoded characters to conform to RFC3986 - http://tools.ietf.org/html/rfc3986#section-2
42
     *
43
     * @var array
44
     */
45
    protected static $characters_set_encoded = [
46
        '%21', '%24', '%26', '%27', '%28', '%29', '%2A', '%2B', '%2C', '%3B', '%3D', '%3A',
47
    ];
48
49
    /**
50
     * Invalid Characters list
51
     *
52
     * @var string
53
     */
54
    protected static $invalidCharactersRegex;
55
56
    /**
57
     * Check the string against RFC3986 rules
58
     *
59
     * @param string $str
60
     *
61
     * @throws InvalidArgumentException If the string is invalid
62
     */
63 864
    protected function assertValidComponent($str)
64
    {
65 864
        if (!empty(static::$invalidCharactersRegex) && preg_match(static::$invalidCharactersRegex, $str)) {
66 26
            throw new InvalidArgumentException('The component contains invalid characters');
67
        }
68 838
    }
69
70
    /**
71
     * @inheritdoc
72
     */
73 24
    public function sameValueAs(UriPart $component)
74
    {
75 24
        return $component->getUriComponent() === $this->getUriComponent();
76
    }
77
78
    /**
79
     * @inheritdoc
80
     */
81
    abstract public function getUriComponent();
82
83
    /**
84
     * @inheritdoc
85
     */
86
    abstract public function __toString();
87
88 852
    protected static function getReservedRegex()
89
    {
90 852
        if (!isset(static::$characters_set_compiled)) {
91
            $reserved = preg_quote(implode('', static::$characters_set), '/');
92
            static::$characters_set_compiled = '/(?:[^'.$reserved.']+|%(?![A-Fa-f0-9]{2}))/S';
93
        }
94 852
        return static::$characters_set_compiled;
95
    }
96
97
    /**
98
     * Encoding string according to RFC3986
99
     *
100
     * @param string $value
101
     *
102
     * @return string
103
     */
104 816
    protected static function encode($value)
105
    {
106 816
        $str = preg_replace_callback(
107 816
            self::getReservedRegex(),
108
            function (array $matches) {
109 738
                return rawurlencode($matches[0]);
110 816
            },
111
            $value
112 816
        );
113
114 816
        return preg_replace_callback(',(?<encode>%[0-9a-f]{2}),', function (array $matches) {
115 76
            return strtoupper($matches['encode']);
116 816
        }, $str);
117
    }
118
119
    /**
120
     * @inheritdoc
121
     */
122 356
    public function modify($value)
123
    {
124 356
        if ($value == $this->__toString()) {
125 118
            return $this;
126
        }
127
128 316
        return (new ReflectionClass(get_called_class()))->newInstance($value);
129
    }
130
}
131