Completed
Push — master ( 0bf349...523be1 )
by Greg
01:45
created

VersionIdentifiers::getVidPattern()   A

Complexity

Conditions 2
Paths 2

Size

Total Lines 4

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
dl 0
loc 4
rs 10
c 0
b 0
f 0
cc 2
nc 2
nop 0
1
<?php
2
3
namespace Hubph;
4
5
class VersionIdentifiers
6
{
7
    protected $data = [];
8
    protected $vidPattern;
9
    protected $vvalPattern;
10
    protected $preamble = 'Update to ';
11
12
    const DEFAULT_VID = '[A-Za-z_-]+ ?';
13
    const DEFAULT_VVAL = '#.#.#';
14
    const EXTRA = '(?:(stable|beta|b|RC|alpha|a|patch|pl|p)((?:[.-]?\d+)*+)?)?([.-]?dev)?';
15
    const NUMBER = '[0-9]+';
16
17
    /**
18
     * VersionIdentifiers constructor
19
     */
20
    public function __construct()
21
    {
22
        $this->vidPattern = '';
23
        $this->vvalPattern = '';
24
    }
25
26
    public function getPreamble()
27
    {
28
        return $this->preamble;
29
    }
30
31
    public function setPreamble($preamble)
32
    {
33
        $this->preamble = $preamble;
34
    }
35
36
    public function getVidPattern()
37
    {
38
        return empty($this->vidPattern) ? self::DEFAULT_VID : $this->vidPattern;
39
    }
40
41
    public function setVidPattern($vidPattern)
42
    {
43
        $this->vidPattern = $vidPattern;
44
    }
45
46
    public function getVvalPattern()
47
    {
48
        return empty($this->vvalPattern) ? self::DEFAULT_VVAL : $this->vvalPattern;
49
    }
50
51
    public function setVvalPattern($vvalPattern)
52
    {
53
        $this->vvalPattern = $vvalPattern;
54
    }
55
56
    /**
57
     * Multiple provided value with our multiplier
58
     *
59
     * @param $value multiplicand
60
     * @return integer product of multiplier and multiplicand
61
     */
62
    public function add($vid, $vval)
63
    {
64
        $this->data[$vid] = $vval;
65
    }
66
67
    public function pattern()
68
    {
69
        $vidPattern = $this->getVidPattern();
70
        $vvalPattern = $this->getVvalPattern();
71
72
        $vid_vval_regex = "({$vidPattern})({$vvalPattern}[._-]?)" . self::EXTRA;
73
74
        $vid_vval_regex = str_replace('#.', '#\\.', $vid_vval_regex);
75
        $vid_vval_regex = str_replace('#', self::NUMBER, $vid_vval_regex);
76
77
        return $vid_vval_regex;
78
    }
79
80
    /**
81
     * Given a simple message like "Update to WordPress 4.9.8", return the
82
     * correct vid/vval pair. In this case, the vid is "WordPress " and the
83
     * vval is "4.9.8".
84
     *
85
     * @param string $message a commit message
86
     */
87
    public function addVidsFromMessage($message)
88
    {
89
        $vid_vval_regex = $this->pattern();
90
91
        if (!preg_match_all("#$vid_vval_regex#", $message, $matches, PREG_SET_ORDER)) {
92
            throw new \Exception('Message does not contain a semver release identifier, e.g.: Update to myproject-1.2.3');
93
        }
94
        foreach ($matches as $matchset) {
95
            array_shift($matchset);
96
            $vid = array_shift($matchset);
97
            $vval = implode('', $matchset);
98
99
            // Trim trailing punctuation.
100
            $vval = preg_replace('#[^0-9a-zA-Z]*$#', '', $vval);
101
102
            $this->add($vid, $vval);
103
        }
104
    }
105
106
    /**
107
     * Check to see if a list of PR titles collectively contain all of the
108
     * vids with vvals.
109
     *
110
     * @param string[] $titles
111
     */
112
    public function allExist($titles)
113
    {
114
        // If we are empty do we return 'true' or 'false'? Maybe throw.
115
        if ($this->isEmpty()) {
116
            return false;
117
        }
118
119
        foreach ($this->all() as $value) {
120
            if (!$this->someTitleContains($titles, $value)) {
121
                return false;
122
            }
123
        }
124
125
        return true;
126
    }
127
128
    /**
129
     *  foreach ($existingPRs as $pr) {
130
     *    if (strpos($pr['title'], $value) !== false) {
131
     */
132
    protected function someTitleContains($titles, $value)
133
    {
134
        foreach ($titles as $title) {
135
            if (strpos($title, $value) !== false) {
136
                return true;
137
            }
138
        }
139
        return false;
140
    }
141
142
    public function isEmpty()
143
    {
144
        return empty($this->data);
145
    }
146
147
    public function all()
148
    {
149
        $result = [];
150
        foreach ($this->data as $vid => $vval) {
151
            $result[] = "{$vid}{$vval}";
152
        }
153
        return $result;
154
    }
155
156
    public function ids()
157
    {
158
        return array_keys($this->data);
159
    }
160
161
    public function __toString()
162
    {
163
        if ($this->isEmpty()) {
164
            return '';
165
        }
166
167
        $all = $this->all();
168
169
        $last = array_pop($all);
170
171
        if (empty($all)) {
172
            return $last;
173
        }
174
175
        return implode(', ', $all) . ", and $last";
176
    }
177
}
178