Completed
Pull Request — master (#1)
by Greg
65:22 queued 63:19
created

SiteAliasName::location()   A

Complexity

Conditions 1
Paths 1

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 1
nc 1
nop 0
1
<?php
2
namespace Consolidation\SiteAlias;
3
4
/**
5
 * Parse a string that contains a site alias name, and provide convenience
6
 * methods to access the parts.
7
 *
8
 * When provided by users, aliases must be in one of the following forms:
9
 *
10
 *   - @sitename.env: List only sitename and environment.
11
 *
12
 *   - @location.sitename.env: List only sitename and environment. Search
13
 *       only those paths where the basename matches 'location'. Location terms
14
 *       may only be used when both the sitename and env are also provided.
15
 *
16
 *   - @env: Look up a named environment in instances where the site root
17
 *       is known (e.g. via cwd). In this form, there is an implicit sitename
18
 *       'self' which is replaced by the actual site alias name once known.
19
 *
20
 *   - @sitename: Provides only the sitename; uses the 'default' environment,
21
 *       or 'dev' if there is no 'default' (or whatever is there if there is
22
 *       only one). With this form, the site alias name has no environment
23
 *       until the appropriate default environment is looked up. This form
24
 *       is checked only after `@env` returns no matches. This form can NOT
25
 *       be filtered with a `location.` term.
26
 *
27
 * There are also two special aliases that are recognized:
28
 *
29
 *   - @self: The current bootstrapped site.
30
 *
31
 *   - @none: No alias ('root' and 'uri' unset).
32
 *
33
 * The special alias forms have no environment component.
34
 *
35
 * When provided to an API, the '@' is optional.
36
 *
37
 * Note that @sitename and @env are ambiguous. Aliases in this form
38
 * (that are not one of the special aliases) will first be assumed
39
 * to be @env, and may be converted to @sitename later.
40
 *
41
 * Note that:
42
 *
43
 * - 'sitename' and 'env' MUST NOT contain a '.' (unlike previous
44
 *     versions of Drush).
45
 * - Users SHOULD NOT create any environments that have the same name
46
 *     as any site name (and visa-versa).
47
 * - All environments in one site record SHOULD be different versions
48
 *     of the same site (e.g. dev / test / live).
49
 */
50
class SiteAliasName
51
{
52
    protected $location;
53
    protected $sitename;
54
    protected $env;
55
56
    /**
57
     * Match the parts of a regex name.
58
     */
59
    const ALIAS_NAME_REGEX = '%^@?([a-zA-Z0-9_-]+)(\.[a-zA-Z0-9_-]+)?(\.[a-zA-Z0-9_-]+)?$%';
60
61
    /**
62
     * Create a new site alias name
63
     *
64
     * @param string $item
65
     * @return SiteAliasName
66
     */
67
    public static function parse($item)
68
    {
69
        $aliasName = new self();
70
        $aliasName->doParse($item);
71
        return $aliasName;
72
    }
73
74
    /**
75
     * Creae a SiteAliasName object from an alias name string.
76
     *
77
     * @param string $sitename The alias name for the site.
78
     * @param string $env The name for the site's environment.
79
     */
80
    public function __construct($sitename = null, $env = null)
81
    {
82
        $this->location = null;
83
        $this->sitename = $sitename;
84
        $this->env = $env;
85
    }
86
87
    /**
88
     * Convert an alias name back to a string.
89
     *
90
     * @return string
91
     */
92
    public function __toString()
93
    {
94
        $parts = [ $this->sitename() ];
95
        if ($this->hasLocation()) {
96
            array_unshift($parts, $this->location());
97
        }
98
        if ($this->hasEnv()) {
99
            $parts[] = $this->env();
100
        }
101
        return '@' . implode('.', $parts);
102
    }
103
104
    /**
105
     * Determine whether or not the provided name is an alias name.
106
     *
107
     * @param string $aliasName
108
     * @return bool
109
     */
110
    public static function isAliasName($aliasName)
111
    {
112
        // Alias names provided by users must begin with '@'
113
        if (empty($aliasName) || ($aliasName[0] != '@')) {
114
            return false;
115
        }
116
        return preg_match(self::ALIAS_NAME_REGEX, $aliasName);
117
    }
118
119
    /**
120
     * Return the sitename portion of the alias name. By definition,
121
     * every alias must have a sitename. If the site name is implicit,
122
     * then 'self' is assumed.
123
     *
124
     * @return string
125
     */
126
    public function sitename()
127
    {
128
        return empty($this->sitename) ? 'self' : $this->sitename;
129
    }
130
131
    /**
132
     * Set the sitename portion of the alias name
133
     *
134
     * @param string $sitename
135
     */
136
    public function setSitename($sitename)
137
    {
138
        $this->sitename = $sitename;
139
        return $this;
140
    }
141
142
    /**
143
     * In general, all aliases have a sitename. The time when one will not
144
     * is when an environment name `@env` is used as a shortcut for `@self.env`
145
     *
146
     * @return bool
147
     */
148
    public function hasSitename()
149
    {
150
        return !empty($this->sitename);
151
    }
152
153
    /**
154
     * Return true if this alias name contains an 'env' portion.
155
     *
156
     * @return bool
157
     */
158
    public function hasEnv()
159
    {
160
        return !empty($this->env);
161
    }
162
163
    /**
164
     * Set the environment portion of the alias name.
165
     *
166
     * @param string
167
     */
168
    public function setEnv($env)
169
    {
170
        $this->env = $env;
171
        return $this;
172
    }
173
174
    /**
175
     * Return the 'env' portion of the alias name.
176
     *
177
     * @return string
178
     */
179
    public function env()
180
    {
181
        return $this->env;
182
    }
183
184
    /**
185
     * Return true if this alias name contains a 'location' portion
186
     * @return bool
187
     */
188
    public function hasLocation()
189
    {
190
        return !empty($this->location);
191
    }
192
193
    /**
194
     * Set the 'loation' portion of the alias name.
195
     * @param string $location
196
     */
197
    public function setLocation($location)
198
    {
199
        $this->location = $location;
200
        return $this;
201
    }
202
203
    /**
204
     * Return the 'location' portion of the alias name.
205
     *
206
     * @param string
207
     */
208
    public function location()
209
    {
210
        return $this->location;
211
    }
212
213
    /**
214
     * Return true if this alias name is the 'self' alias.
215
     *
216
     * @return bool
217
     */
218
    public function isSelf()
219
    {
220
        return ($this->sitename == 'self') && !isset($this->env);
221
    }
222
223
    /**
224
     * Return true if this alias name is the 'none' alias.
225
     */
226
    public function isNone()
227
    {
228
        return ($this->sitename == 'none') && !isset($this->env);
229
    }
230
231
    /**
232
     * Convert the parts of an alias name to its various component parts.
233
     *
234
     * @param string $aliasName a string representation of an alias name.
235
     */
236
    protected function doParse($aliasName)
237
    {
238
        // Example contents of $matches:
239
        //
240
        // - a.b:
241
        //     [
242
        //       0 => 'a.b',
0 ignored issues
show
Unused Code Comprehensibility introduced by
58% of this comment could be valid code. Did you maybe forget this after debugging?

Sometimes obsolete code just ends up commented out instead of removed. In this case it is better to remove the code once you have checked you do not need it.

The code might also have been commented out for debugging purposes. In this case it is vital that someone uncomments it again or your project may behave in very unexpected ways in production.

This check looks for comments that seem to be mostly valid code and reports them.

Loading history...
243
        //       1 => 'a',
0 ignored issues
show
Unused Code Comprehensibility introduced by
58% of this comment could be valid code. Did you maybe forget this after debugging?

Sometimes obsolete code just ends up commented out instead of removed. In this case it is better to remove the code once you have checked you do not need it.

The code might also have been commented out for debugging purposes. In this case it is vital that someone uncomments it again or your project may behave in very unexpected ways in production.

This check looks for comments that seem to be mostly valid code and reports them.

Loading history...
244
        //       2 => '.b',
0 ignored issues
show
Unused Code Comprehensibility introduced by
58% of this comment could be valid code. Did you maybe forget this after debugging?

Sometimes obsolete code just ends up commented out instead of removed. In this case it is better to remove the code once you have checked you do not need it.

The code might also have been commented out for debugging purposes. In this case it is vital that someone uncomments it again or your project may behave in very unexpected ways in production.

This check looks for comments that seem to be mostly valid code and reports them.

Loading history...
245
        //     ]
246
        //
247
        // - a:
248
        //     [
249
        //       0 => 'a',
0 ignored issues
show
Unused Code Comprehensibility introduced by
58% of this comment could be valid code. Did you maybe forget this after debugging?

Sometimes obsolete code just ends up commented out instead of removed. In this case it is better to remove the code once you have checked you do not need it.

The code might also have been commented out for debugging purposes. In this case it is vital that someone uncomments it again or your project may behave in very unexpected ways in production.

This check looks for comments that seem to be mostly valid code and reports them.

Loading history...
250
        //       1 => 'a',
0 ignored issues
show
Unused Code Comprehensibility introduced by
58% of this comment could be valid code. Did you maybe forget this after debugging?

Sometimes obsolete code just ends up commented out instead of removed. In this case it is better to remove the code once you have checked you do not need it.

The code might also have been commented out for debugging purposes. In this case it is vital that someone uncomments it again or your project may behave in very unexpected ways in production.

This check looks for comments that seem to be mostly valid code and reports them.

Loading history...
251
        //     ]
252
        if (!preg_match(self::ALIAS_NAME_REGEX, $aliasName, $matches)) {
253
            return false;
254
        }
255
256
        // Get rid of $matches[0]
0 ignored issues
show
Unused Code Comprehensibility introduced by
37% of this comment could be valid code. Did you maybe forget this after debugging?

Sometimes obsolete code just ends up commented out instead of removed. In this case it is better to remove the code once you have checked you do not need it.

The code might also have been commented out for debugging purposes. In this case it is vital that someone uncomments it again or your project may behave in very unexpected ways in production.

This check looks for comments that seem to be mostly valid code and reports them.

Loading history...
257
        array_shift($matches);
258
259
        // If $matches contains only one item1, then assume the alias name
260
        // contains only the environment.
261
        if (count($matches) == 1) {
262
            return $this->processSingleItem($matches[0]);
263
        }
264
265
        // If there are three items, then the first is the location.
266
        if (count($matches) == 3) {
267
            $this->location = trim(array_shift($matches), '.');
268
        }
269
270
        // The sitename and env follow the location.
271
        $this->sitename = trim(array_shift($matches), '.');
272
        $this->env = trim(array_shift($matches), '.');
273
        return true;
274
    }
275
276
    /**
277
     * Process an alias name provided as '@sitename'.
278
     *
279
     * @param string $sitename
0 ignored issues
show
Bug introduced by
There is no parameter named $sitename. Was it maybe removed?

This check looks for PHPDoc comments describing methods or function parameters that do not exist on the corresponding method or function.

Consider the following example. The parameter $italy is not defined by the method finale(...).

/**
 * @param array $germany
 * @param array $island
 * @param array $italy
 */
function finale($germany, $island) {
    return "2:1";
}

The most likely cause is that the parameter was removed, but the annotation was not.

Loading history...
280
     * @return true
281
     */
282
    protected function processSingleItem($item)
283
    {
284
        if ($this->isSpecialAliasName($item)) {
285
            $this->setSitename($item);
286
            return true;
287
        }
288
        $this->sitename = '';
289
        $this->env = $item;
290
        return true;
291
    }
292
293
    /**
294
     * Determine whether the requested name is a special alias name.
295
     *
296
     * @param string $item
297
     * @return boolean
298
     */
299
    protected function isSpecialAliasName($item)
300
    {
301
        return ($item == 'self') || ($item == 'none');
302
    }
303
}
304