Completed
Push — master ( d76cf7...55ae92 )
by Nikola
02:19
created

Version   B

Complexity

Total Complexity 39

Size/Duplication

Total Lines 270
Duplicated Lines 0 %

Coupling/Cohesion

Components 1
Dependencies 7

Test Coverage

Coverage 100%

Importance

Changes 4
Bugs 0 Features 0
Metric Value
wmc 39
lcom 1
cbo 7
dl 0
loc 270
ccs 93
cts 93
cp 1
rs 8.2857
c 4
b 0
f 0

29 Methods

Rating   Name   Duplication   Size   Complexity  
A __construct() 0 12 1
A validateNumber() 0 6 2
A fromParts() 0 4 1
A fromString() 0 21 4
A getMajor() 0 4 1
A getMinor() 0 4 1
A getPatch() 0 4 1
A getPreRelease() 0 4 1
A getBuild() 0 4 1
A isPreRelease() 0 4 1
A isBuild() 0 4 1
A isEqualTo() 0 4 1
A isNotEqualTo() 0 4 1
A isGreaterThan() 0 4 1
A isGreaterOrEqualTo() 0 4 1
A isLessThan() 0 4 1
A isLessOrEqualTo() 0 4 1
A compareTo() 0 8 2
A incrementMajor() 0 4 1
A incrementMinor() 0 4 1
A incrementPatch() 0 4 1
A withPreRelease() 0 8 2
A withBuild() 0 8 2
A matches() 0 4 1
A getVersionString() 0 10 3
A __toString() 0 4 1
A jsonSerialize() 0 4 1
A toArray() 0 10 1
A getComparator() 0 10 2
1
<?php
2
3
declare(strict_types=1);
4
5
namespace Version;
6
7
use JsonSerializable;
8
use Version\Extension\Build;
9
use Version\Extension\NoBuild;
10
use Version\Extension\NoPreRelease;
11
use Version\Exception\InvalidVersionException;
12
use Version\Exception\InvalidVersionStringException;
13
use Version\Comparator\ComparatorInterface;
14
use Version\Comparator\SemverComparator;
15
use Version\Constraint\ConstraintInterface;
16
use Version\Extension\PreRelease;
17
18
/**
19
 * @author Nikola Posa <[email protected]>
20
 */
21
class Version implements JsonSerializable
22
{
23
    /**
24
     * @var int
25
     */
26
    protected $major;
27
28
    /**
29
     * @var int
30
     */
31
    protected $minor;
32
33
    /**
34
     * @var int
35
     */
36
    protected $patch;
37
38
    /**
39
     * @var PreRelease
40
     */
41
    protected $preRelease;
42
43
    /**
44
     * @var Build
45
     */
46
    protected $build;
47
48 72
    protected function __construct(int $major, int $minor, int $patch, PreRelease $preRelease, Build $build)
49
    {
50 72
        $this->validateNumber('major', $major);
51 71
        $this->validateNumber('minor', $minor);
52 70
        $this->validateNumber('patch', $patch);
53
54 69
        $this->major = $major;
55 69
        $this->minor = $minor;
56 69
        $this->patch = $patch;
57 69
        $this->preRelease = $preRelease;
58 69
        $this->build = $build;
59 69
    }
60
61 72
    protected function validateNumber(string $name, int $value) : void
62
    {
63 72
        if ($value < 0) {
64 3
            throw InvalidVersionException::forNumber($name, $value);
65
        }
66 71
    }
67
68 72
    public static function fromParts(int $major, int $minor = 0, int $patch = 0, PreRelease $preRelease = null, Build $build = null) : Version
69
    {
70 72
        return new static($major, $minor, $patch, $preRelease ?? new NoPreRelease(), $build ?? new NoBuild());
71
    }
72
73
    /**
74
     * @param string $versionString
75
     * @return Version
76
     * @throws InvalidVersionStringException
77
     */
78 70
    public static function fromString(string $versionString) : Version
79
    {
80 70
        if (!preg_match(
81
            '#^'
82
            . 'v?'
83
            . '(?P<core>(?:[0-9]|[1-9][0-9]+)(?:\.(?:[0-9]|[1-9][0-9]+)){2})'
84
            . '(?:\-(?P<preRelease>[0-9A-Za-z\-\.]+))?'
85
            . '(?:\+(?P<build>[0-9A-Za-z\-\.]+))?'
86 70
            . '$#',
87 70
            $versionString,
88 70
            $parts
89
        )) {
90 4
            throw InvalidVersionStringException::forVersionString($versionString);
91
        }
92
93 66
        [$major, $minor, $patch] = explode('.', $parts['core']);
0 ignored issues
show
Bug introduced by
The variable $major does not exist. Did you forget to declare it?

This check marks access to variables or properties that have not been declared yet. While PHP has no explicit notion of declaring a variable, accessing it before a value is assigned to it is most likely a bug.

Loading history...
Bug introduced by
The variable $minor does not exist. Did you forget to declare it?

This check marks access to variables or properties that have not been declared yet. While PHP has no explicit notion of declaring a variable, accessing it before a value is assigned to it is most likely a bug.

Loading history...
Bug introduced by
The variable $patch does not exist. Did you forget to declare it?

This check marks access to variables or properties that have not been declared yet. While PHP has no explicit notion of declaring a variable, accessing it before a value is assigned to it is most likely a bug.

Loading history...
94 66
        $preRelease = !empty($parts['preRelease']) ? PreRelease::fromIdentifiersString($parts['preRelease']) : new NoPreRelease();
95 66
        $build = !empty($parts['build']) ? Build::fromIdentifiersString($parts['build']) : new NoBuild();
96
97 66
        return static::fromParts((int) $major, (int) $minor, (int) $patch, $preRelease, $build);
98
    }
99
100 49
    public function getMajor() : int
101
    {
102 49
        return $this->major;
103
    }
104
105 45
    public function getMinor() : int
106
    {
107 45
        return $this->minor;
108
    }
109
110 42
    public function getPatch() : int
111
    {
112 42
        return $this->patch;
113
    }
114
115 37
    public function getPreRelease() : PreRelease
116
    {
117 37
        return $this->preRelease;
118
    }
119
120 17
    public function getBuild() : Build
121
    {
122 17
        return $this->build;
123
    }
124
125 36
    public function isPreRelease() : bool
126
    {
127 36
        return !$this->preRelease->isEmpty();
128
    }
129
130 14
    public function isBuild() : bool
131
    {
132 14
        return !$this->build->isEmpty();
133
    }
134
135
    /**
136
     * @param Version|string $version
137
     * @return bool
138
     */
139 5
    public function isEqualTo($version) : bool
140
    {
141 5
        return $this->compareTo($version) === 0;
142
    }
143
144
    /**
145
     * @param Version|string $version
146
     * @return bool
147
     */
148 1
    public function isNotEqualTo($version) : bool
149
    {
150 1
        return !$this->isEqualTo($version);
151
    }
152
153
    /**
154
     * @param Version|string $version
155
     * @return bool
156
     */
157 3
    public function isGreaterThan($version) : bool
158
    {
159 3
        return $this->compareTo($version) > 0;
160
    }
161
162
    /**
163
     * @param Version|string $version
164
     * @return bool
165
     */
166 4
    public function isGreaterOrEqualTo($version) : bool
167
    {
168 4
        return $this->compareTo($version) >= 0;
169
    }
170
171
    /**
172
     * @param Version|string $version
173
     * @return bool
174
     */
175 3
    public function isLessThan($version) : bool
176
    {
177 3
        return $this->compareTo($version) < 0;
178
    }
179
180
    /**
181
     * @param Version|string $version
182
     * @return bool
183
     */
184 2
    public function isLessOrEqualTo($version) : bool
185
    {
186 2
        return $this->compareTo($version) <= 0;
187
    }
188
189
    /**
190
     * @param Version|string $version
191
     * @return int (1 if $this > $version, -1 if $this < $version, 0 if equal)
192
     */
193 20
    public function compareTo($version) : int
194
    {
195 20
        if (is_string($version)) {
196 7
            $version = static::fromString($version);
197
        }
198
199 20
        return $this->getComparator()->compare($this, $version);
200
    }
201
202 1
    public function incrementMajor() : Version
203
    {
204 1
        return static::fromParts($this->major + 1, 0, 0, new NoPreRelease(), new NoBuild());
205
    }
206
207 2
    public function incrementMinor() : Version
208
    {
209 2
        return static::fromParts($this->major, $this->minor + 1, 0, new NoPreRelease(), new NoBuild());
210
    }
211
212 1
    public function incrementPatch() : Version
213
    {
214 1
        return static::fromParts($this->major, $this->minor, $this->patch + 1, new NoPreRelease(), new NoBuild());
215
    }
216
217
    /**
218
     * @param PreRelease|string $preRelease
219
     * @return Version
220
     */
221 2
    public function withPreRelease($preRelease) : Version
222
    {
223 2
        if (is_string($preRelease)) {
224 2
            $preRelease = PreRelease::fromIdentifiersString($preRelease);
225
        }
226
227 2
        return static::fromParts($this->major, $this->minor, $this->patch, $preRelease, new NoBuild());
228
    }
229
230
    /**
231
     * @param Build|string $build
232
     * @return Version
233
     */
234 1
    public function withBuild($build) : Version
235
    {
236 1
        if (is_string($build)) {
237 1
            $build = Build::fromIdentifiersString($build);
238
        }
239
240 1
        return static::fromParts($this->major, $this->minor, $this->patch, $this->preRelease, $build);
241
    }
242
243 2
    public function matches(ConstraintInterface $constraint) : bool
244
    {
245 2
        return $constraint->assert($this);
246
    }
247
248 14
    public function getVersionString() : string
249
    {
250
        return
251 14
            $this->major
252 14
            . '.' . $this->minor
253 14
            . '.' . $this->patch
254 14
            . ($this->isPreRelease() ? '-' . (string) $this->preRelease : '')
255 14
            . ($this->isBuild() ? '+' . (string) $this->build : '')
256
        ;
257
    }
258
259 10
    public function __toString() : string
260
    {
261 10
        return $this->getVersionString();
262
    }
263
264 4
    public function jsonSerialize() : string
265
    {
266 4
        return $this->getVersionString();
267
    }
268
269 4
    public function toArray() : array
270
    {
271
        return [
272 4
            'major' => $this->major,
273 4
            'minor' => $this->minor,
274 4
            'patch' => $this->patch,
275 4
            'preRelease' => $this->preRelease->getIdentifiers(),
276 4
            'build' => $this->build->getIdentifiers(),
277
        ];
278
    }
279
280 20
    protected function getComparator() : ComparatorInterface
281
    {
282 20
        static $comparator = null;
283
284 20
        if (null === $comparator) {
285 1
            $comparator = new SemverComparator();
286
        }
287
288 20
        return $comparator;
289
    }
290
}
291