Issues (201)

Security Analysis    no request data  

This project does not seem to handle request data directly as such no vulnerable execution paths were found.

  Cross-Site Scripting
Cross-Site Scripting enables an attacker to inject code into the response of a web-request that is viewed by other users. It can for example be used to bypass access controls, or even to take over other users' accounts.
  File Exposure
File Exposure allows an attacker to gain access to local files that he should not be able to access. These files can for example include database credentials, or other configuration files.
  File Manipulation
File Manipulation enables an attacker to write custom data to files. This potentially leads to injection of arbitrary code on the server.
  Object Injection
Object Injection enables an attacker to inject an object into PHP code, and can lead to arbitrary code execution, file exposure, or file manipulation attacks.
  Code Injection
Code Injection enables an attacker to execute arbitrary code on the server.
  Response Splitting
Response Splitting can be used to send arbitrary responses.
  File Inclusion
File Inclusion enables an attacker to inject custom files into PHP's file loading mechanism, either explicitly passed to include, or for example via PHP's auto-loading mechanism.
  Command Injection
Command Injection enables an attacker to inject a shell command that is execute with the privileges of the web-server. This can be used to expose sensitive data, or gain access of your server.
  SQL Injection
SQL Injection enables an attacker to execute arbitrary SQL code on your database server gaining access to user data, or manipulating user data.
  XPath Injection
XPath Injection enables an attacker to modify the parts of XML document that are read. If that XML document is for example used for authentication, this can lead to further vulnerabilities similar to SQL Injection.
  LDAP Injection
LDAP Injection enables an attacker to inject LDAP statements potentially granting permission to run unauthorized queries, or modify content inside the LDAP tree.
  Header Injection
  Other Vulnerability
This category comprises other attack vectors such as manipulating the PHP runtime, loading custom extensions, freezing the runtime, or similar.
  Regex Injection
Regex Injection enables an attacker to execute arbitrary code in your PHP process.
  XML Injection
XML Injection enables an attacker to read files on your local filesystem including configuration files, or can be abused to freeze your web-server process.
  Variable Injection
Variable Injection enables an attacker to overwrite program variables with custom data, and can lead to further vulnerabilities.
Unfortunately, the security analysis is currently not available for your project. If you are a non-commercial open-source project, please contact support to gain access.

src/Api/Module/ModuleFile.php (1 issue)

Upgrade to new PHP Analysis Engine

These results are based on our legacy PHP analysis, consider migrating to our new PHP analysis engine instead. Learn more

1
<?php
2
3
/*
4
 * This file is part of the puli/manager package.
5
 *
6
 * (c) Bernhard Schussek <[email protected]>
7
 *
8
 * For the full copyright and license information, please view the LICENSE
9
 * file that was distributed with this source code.
10
 */
11
12
namespace Puli\Manager\Api\Module;
13
14
use InvalidArgumentException;
15
use Puli\Manager\Api\Discovery\BindingDescriptor;
16
use Puli\Manager\Api\Discovery\BindingTypeDescriptor;
17
use Puli\Manager\Api\Discovery\NoSuchBindingException;
18
use Puli\Manager\Api\Repository\NoSuchPathMappingException;
19
use Puli\Manager\Api\Repository\PathMapping;
20
use Puli\Manager\Assert\Assert;
21
use Rhumsaa\Uuid\Uuid;
22
23
/**
24
 * Stores the configuration of a module.
25
 *
26
 * @since  1.0
27
 *
28
 * @author Bernhard Schussek <[email protected]>
29
 */
30
class ModuleFile
31
{
32
    /**
33
     * @var string
34
     */
35
    private $version;
36
37
    /**
38
     * @var string|null
39
     */
40
    private $moduleName;
41
42
    /**
43
     * @var string|null
44
     */
45
    private $path;
46
47
    /**
48
     * @var PathMapping[]
49
     */
50
    private $pathMappings = array();
51
52
    /**
53
     * @var BindingDescriptor[]
54
     */
55
    private $bindingDescriptors = array();
56
57
    /**
58
     * @var BindingTypeDescriptor[]
59
     */
60
    private $typeDescriptors = array();
61
62
    /**
63
     * @var bool[]
64
     */
65
    private $dependencies = array();
66
67
    /**
68
     * @var array
69
     */
70
    private $extra = array();
71
72
    /**
73
     * Creates a new module file.
74
     *
75
     * @param string|null $moduleName The module name. Optional.
76
     * @param string|null $path       The path where the file is stored or
77
     *                                `null` if this configuration is not
78
     *                                stored on the file system.
79
     *
80
     * @throws InvalidArgumentException If the name/path is not a string or empty.
81
     */
82 626
    public function __construct($moduleName = null, $path = null)
83
    {
84 626
        Assert::nullOrModuleName($moduleName);
85 624
        Assert::nullOrAbsoluteSystemPath($path);
86
87 622
        $this->path = $path;
88 622
        $this->moduleName = $moduleName;
89 622
    }
90
91
    /**
92
     * Returns the version of the module file.
93
     *
94
     * @return string The module file version.
95
     */
96 13
    public function getVersion()
97
    {
98 13
        return $this->version;
99
    }
100
101
    /**
102
     * Sets the version of the module file.
103
     *
104
     * @param string $version The module file version.
105
     */
106 47
    public function setVersion($version)
107
    {
108 47
        Assert::string($version, 'The module file version must be a string. Got: %s');
109 47
        Assert::regex($version, '~^\d\.\d$~', 'The module file version must have the format "<digit>.<digit>". Got: %s</digit>');
110
111 47
        $this->version = $version;
112 47
    }
113
114
    /**
115
     * Returns the module name.
116
     *
117
     * @return string|null The module name or `null` if none is set.
118
     */
119 453
    public function getModuleName()
120
    {
121 453
        return $this->moduleName;
122
    }
123
124
    /**
125
     * Sets the module name.
126
     *
127
     * @param string|null $moduleName The module name or `null` to unset.
128
     *
129
     * @throws InvalidArgumentException If the name is not a string or empty.
130
     */
131 42
    public function setModuleName($moduleName)
132
    {
133 42
        Assert::nullOrModuleName($moduleName);
134
135 40
        $this->moduleName = $moduleName;
136 40
    }
137
138
    /**
139
     * Returns the path to the module file.
140
     *
141
     * @return string|null The path or `null` if this file is not stored on the
142
     *                     file system.
143
     */
144 25
    public function getPath()
145
    {
146 25
        return $this->path;
147
    }
148
149
    /**
150
     * Sets the names of the modules this module depends on.
151
     *
152
     * @param string[] $moduleNames The names of the modules.
153
     */
154 52
    public function setDependencies(array $moduleNames)
155
    {
156 52
        $this->dependencies = array();
157
158 52
        foreach ($moduleNames as $moduleName) {
159 52
            $this->dependencies[$moduleName] = true;
160
        }
161 52
    }
162
163
    /**
164
     * Adds a dependency to a module.
165
     *
166
     * @param string $moduleName The name of the module.
167
     */
168 10
    public function addDependency($moduleName)
169
    {
170 10
        $this->dependencies[$moduleName] = true;
171 10
    }
172
173
    /**
174
     * Adds a dependency to a module.
175
     *
176
     * @param string $moduleName The name of the module.
177
     */
178 2
    public function removeDependency($moduleName)
179
    {
180 2
        unset($this->dependencies[$moduleName]);
181 2
    }
182
183
    /**
184
     * Removes all dependencies.
185
     */
186
    public function clearDependencies()
187
    {
188
        $this->dependencies = array();
189
    }
190
191
    /**
192
     * Returns the names of the modules this module overrides.
193
     *
194
     * @return string[] The names of the overridden modules.
0 ignored issues
show
Should the return type not be integer[]?

This check compares the return type specified in the @return annotation of a function or method doc comment with the types returned by the function and raises an issue if they mismatch.

Loading history...
195
     */
196 120
    public function getDependencies()
197
    {
198 120
        return array_keys($this->dependencies);
199
    }
200
201
    /**
202
     * Returns whether the module depends on a given module.
203
     *
204
     * @param string $moduleName The name of the module.
205
     *
206
     * @return bool Returns `true` if the module depends on the given module.
207
     */
208 7
    public function hasDependency($moduleName)
209
    {
210 7
        return isset($this->dependencies[$moduleName]);
211
    }
212
213
    /**
214
     * Returns whether the module has dependencies on other modules.
215
     *
216
     * @return bool Returns `true` if the module depends on other modules and
217
     *              `false` otherwise.
218
     */
219
    public function hasDependencies()
220
    {
221
        return count($this->dependencies) > 0;
222
    }
223
224
    /**
225
     * Returns the path mappings.
226
     *
227
     * @return PathMapping[] The path mappings.
228
     */
229 89
    public function getPathMappings()
230
    {
231 89
        return $this->pathMappings;
232
    }
233
234
    /**
235
     * Returns the path mapping for a repository path.
236
     *
237
     * @param string $repositoryPath The repository path.
238
     *
239
     * @return PathMapping The corresponding path mapping.
240
     *
241
     * @throws NoSuchPathMappingException If the repository path is not mapped.
242
     */
243 15
    public function getPathMapping($repositoryPath)
244
    {
245 15
        if (!isset($this->pathMappings[$repositoryPath])) {
246 1
            throw NoSuchPathMappingException::forRepositoryPath($repositoryPath);
247
        }
248
249 14
        return $this->pathMappings[$repositoryPath];
250
    }
251
252
    /**
253
     * Returns whether the file contains a path mapping for a repository path.
254
     *
255
     * @param string $repositoryPath The repository path.
256
     *
257
     * @return bool Returns `true` if the file contains a mapping for the path.
258
     */
259 30
    public function hasPathMapping($repositoryPath)
260
    {
261 30
        return isset($this->pathMappings[$repositoryPath]);
262
    }
263
264
    /**
265
     * Returns whether the file contains any path mappings.
266
     *
267
     * @return bool Returns `true` if the file contains path mappings and
268
     *              `false` otherwise.
269
     */
270 1
    public function hasPathMappings()
271
    {
272 1
        return count($this->pathMappings) > 0;
273
    }
274
275
    /**
276
     * Adds a path mapping.
277
     *
278
     * @param PathMapping $mapping The path mapping.
279
     */
280 67
    public function addPathMapping(PathMapping $mapping)
281
    {
282 67
        $this->pathMappings[$mapping->getRepositoryPath()] = $mapping;
283
284 67
        ksort($this->pathMappings);
285 67
    }
286
287
    /**
288
     * Removes the path mapping for a repository path.
289
     *
290
     * @param string $repositoryPath The repository path.
291
     */
292 16
    public function removePathMapping($repositoryPath)
293
    {
294 16
        unset($this->pathMappings[$repositoryPath]);
295 16
    }
296
297
    /**
298
     * Removes all path mappings.
299
     */
300
    public function clearPathMappings()
301
    {
302
        $this->pathMappings = array();
303
    }
304
305
    /**
306
     * Returns the binding descriptors.
307
     *
308
     * @return BindingDescriptor[] The binding descriptors.
309
     */
310 123
    public function getBindingDescriptors()
311
    {
312 123
        return array_values($this->bindingDescriptors);
313
    }
314
315
    /**
316
     * Returns the binding descriptor with the given UUID.
317
     *
318
     * @param Uuid $uuid The UUID of the binding descriptor.
319
     *
320
     * @return BindingDescriptor The binding descriptor.
321
     *
322
     * @throws NoSuchBindingException If the UUID was not found.
323
     */
324 10
    public function getBindingDescriptor(Uuid $uuid)
325
    {
326 10
        $uuidString = $uuid->toString();
327
328 10
        if (!isset($this->bindingDescriptors[$uuidString])) {
329 1
            throw NoSuchBindingException::forUuid($uuid);
330
        }
331
332 9
        return $this->bindingDescriptors[$uuidString];
333
    }
334
335
    /**
336
     * Adds a binding descriptor.
337
     *
338
     * @param BindingDescriptor $descriptor The binding descriptor to add.
339
     */
340 66
    public function addBindingDescriptor(BindingDescriptor $descriptor)
341
    {
342 66
        $this->bindingDescriptors[$descriptor->getUuid()->toString()] = $descriptor;
343 66
    }
344
345
    /**
346
     * Removes a binding descriptor.
347
     *
348
     * @param Uuid $uuid The UUID of the binding descriptor to remove.
349
     */
350 9
    public function removeBindingDescriptor(Uuid $uuid)
351
    {
352 9
        unset($this->bindingDescriptors[$uuid->toString()]);
353 9
    }
354
355
    /**
356
     * Removes all binding descriptors.
357
     */
358
    public function clearBindingDescriptors()
359
    {
360
        $this->bindingDescriptors = array();
361
    }
362
363
    /**
364
     * Returns whether the binding descriptor exists in this file.
365
     *
366
     * @param Uuid $uuid The UUID of the binding descriptor.
367
     *
368
     * @return bool Whether the file contains the binding descriptor.
369
     */
370 13
    public function hasBindingDescriptor(Uuid $uuid)
371
    {
372 13
        return isset($this->bindingDescriptors[$uuid->toString()]);
373
    }
374
375
    /**
376
     * Returns whether the file contains any binding descriptors.
377
     *
378
     * @return bool Returns `true` if the file contains binding descriptors and
379
     *              `false` otherwise.
380
     */
381 1
    public function hasBindingDescriptors()
382
    {
383 1
        return count($this->bindingDescriptors) > 0;
384
    }
385
386
    /**
387
     * Adds a type descriptor.
388
     *
389
     * @param BindingTypeDescriptor $descriptor The type descriptor.
390
     */
391 85
    public function addTypeDescriptor(BindingTypeDescriptor $descriptor)
392
    {
393 85
        $this->typeDescriptors[$descriptor->getTypeName()] = $descriptor;
394 85
    }
395
396
    /**
397
     * Removes a type descriptor.
398
     *
399
     * @param string $typeName The type name.
400
     */
401 14
    public function removeTypeDescriptor($typeName)
402
    {
403 14
        unset($this->typeDescriptors[$typeName]);
404 14
    }
405
406
    /**
407
     * Removes all type descriptors.
408
     */
409
    public function clearTypeDescriptors()
410
    {
411
        $this->typeDescriptors = array();
412
    }
413
414
    /**
415
     * Returns the type descriptor with the given name.
416
     *
417
     * @param string $typeName The type name.
418
     *
419
     * @return BindingTypeDescriptor The type descriptor.
420
     */
421 13
    public function getTypeDescriptor($typeName)
422
    {
423 13
        return $this->typeDescriptors[$typeName];
424
    }
425
426
    /**
427
     * Returns the type descriptors.
428
     *
429
     * @return BindingTypeDescriptor[] The type descriptors.
430
     */
431 116
    public function getTypeDescriptors()
432
    {
433
        // Names as keys are for internal use only
434 116
        return array_values($this->typeDescriptors);
435
    }
436
437
    /**
438
     * Returns whether a type is defined in this file.
439
     *
440
     * @param string $typeName The type name.
441
     *
442
     * @return bool Whether the type is defined in the file.
443
     */
444 17
    public function hasTypeDescriptor($typeName)
445
    {
446 17
        return isset($this->typeDescriptors[$typeName]);
447
    }
448
449
    /**
450
     * Returns whether the file contains any type descriptors.
451
     *
452
     * @return bool Returns `true` if the file contains type descriptors and
453
     *              `false` otherwise.
454
     */
455 2
    public function hasTypeDescriptors()
456
    {
457 2
        return count($this->typeDescriptors) > 0;
458
    }
459
460
    /**
461
     * Sets an extra key in the module file.
462
     *
463
     * Extra keys can be freely set by the user. They are stored in a separate
464
     * area of the module file and not validated in any way.
465
     *
466
     * @param string $key   The name of the key.
467
     * @param mixed  $value The value to store.
468
     */
469 85
    public function setExtraKey($key, $value)
470
    {
471 85
        $this->extra[$key] = $value;
472 85
    }
473
474
    /**
475
     * Sets multiple extra keys at once.
476
     *
477
     * Existing extra keys are overridden.
478
     *
479
     * @param array $values The values indexed by their key names.
480
     *
481
     * @see setExtraKey()
482
     */
483 9
    public function setExtraKeys(array $values)
484
    {
485 9
        $this->extra = array();
486
487 9
        foreach ($values as $key => $value) {
488 9
            $this->setExtraKey($key, $value);
489
        }
490 9
    }
491
492
    /**
493
     * Sets multiple extra keys at once.
494
     *
495
     * Existing extra keys are preserved.
496
     *
497
     * @param array $values The values indexed by their key names.
498
     *
499
     * @see setExtraKey()
500
     */
501 1
    public function addExtraKeys(array $values)
502
    {
503 1
        foreach ($values as $key => $value) {
504 1
            $this->setExtraKey($key, $value);
505
        }
506 1
    }
507
508
    /**
509
     * Removes an extra key.
510
     *
511
     * @param string $key The name of the key.
512
     *
513
     * @see setExtraKey()
514
     */
515 7
    public function removeExtraKey($key)
516
    {
517 7
        unset($this->extra[$key]);
518 7
    }
519
520
    /**
521
     * Removes all extra keys.
522
     *
523
     * @see setExtraKey()
524
     */
525 4
    public function clearExtraKeys()
526
    {
527 4
        $this->extra = array();
528 4
    }
529
530
    /**
531
     * Returns the value of an extra key.
532
     *
533
     * @param string $key     The name of the key.
534
     * @param mixed  $default The value to return if the key was not set.
535
     *
536
     * @return mixed The value stored for the key.
537
     *
538
     * @see setExtraKey()
539
     */
540 96
    public function getExtraKey($key, $default = null)
541
    {
542 96
        return array_key_exists($key, $this->extra) ? $this->extra[$key] : $default;
543
    }
544
545
    /**
546
     * Returns all stored extra keys.
547
     *
548
     * @return array The stored values indexed by their key names.
549
     *
550
     * @see setExtraKey()
551
     */
552 38
    public function getExtraKeys()
553
    {
554 38
        return $this->extra;
555
    }
556
557
    /**
558
     * Returns whether the given extra key exists.
559
     *
560
     * @param string $key The name of the key.
561
     *
562
     * @return bool Returns `true` if the given extra key exists and `false`
563
     *              otherwise.
564
     *
565
     * @see setExtraKey()
566
     */
567 14
    public function hasExtraKey($key)
568
    {
569 14
        return array_key_exists($key, $this->extra);
570
    }
571
572
    /**
573
     * Returns whether the file contains any extra keys.
574
     *
575
     * @return bool Returns `true` if the file contains extra keys and `false`
576
     *              otherwise.
577
     *
578
     * @see setExtraKey()
579
     */
580 2
    public function hasExtraKeys()
581
    {
582 2
        return count($this->extra) > 0;
583
    }
584
}
585