Completed
Push — 1.1 ( 17428c...7dea68 )
by David
10:20
created

DiscoveryFileLoader::loadDiscoveryFile()   C

Complexity

Conditions 7
Paths 7

Size

Total Lines 25
Code Lines 15

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
dl 0
loc 25
rs 6.7272
c 0
b 0
f 0
cc 7
eloc 15
nc 7
nop 3
1
<?php
2
3
4
namespace TheCodingMachine\Discovery;
5
6
use Seld\JsonLint\JsonParser;
7
use Seld\JsonLint\ParsingException;
8
use TheCodingMachine\Discovery\Utils\IOException;
9
use TheCodingMachine\Discovery\Utils\JsonException;
10
11
/**
12
 * Class in charge of loading a discovery.json file.
13
 */
14
class DiscoveryFileLoader
15
{
16
    /**
17
     * Returns an array of array of asset operations indexed by asset type.
18
     *
19
     * @param \SplFileInfo $file
20
     * @return AssetOperation[][]
21
     * @throws JsonException
22
     */
23
    public function loadDiscoveryFile(\SplFileInfo $file, string $package, string $packageDir) : array
24
    {
25
        $jsonParser = new JsonParser();
26
        try {
27
            $result = $jsonParser->parse($this->getContents($file), JsonParser::PARSE_TO_ASSOC);
28
        } catch (ParsingException $e) {
29
            throw new JsonException(sprintf('Invalid JSON in file "%s": %s', $file->getPath(), $e->getMessage()), 0, $e);
30
        }
31
32
        if (!is_array($result) || !$this->isAssoc($result)) {
33
            throw new JsonException(sprintf('File "%s" should contain a JSON object.', $file->getPath()));
34
        }
35
36
        $assetTypes = [];
37
38
        foreach ($result as $type => $array) {
39
            if (!is_array($array)) {
40
                $array = [$array];
41
            }
42
            foreach ($array as $value) {
43
                $assetTypes[$type][] = $this->toAssetOperation($value, $package, $packageDir);
44
            }
45
        }
46
        return $assetTypes;
47
    }
48
49
    /**
50
     * Returns false if the array is numerically indexed, starting at 0.
51
     *
52
     * @param array $arr
53
     * @return bool
54
     */
55
    private function isAssoc(array $arr)
56
    {
57
        if (array() === $arr) {
58
            return true;
59
        }
60
        return array_keys($arr) !== range(0, count($arr) - 1);
61
    }
62
63
    /**
64
     * Returns the contents of the file.
65
     *
66
     * @param \SplFileInfo $file
67
     * @return string the contents of the file
68
     *
69
     */
70
    private function getContents(\SplFileInfo $file)
71
    {
72
        $level = error_reporting(0);
73
        $content = file_get_contents($file->getPathname());
74
        error_reporting($level);
75
        if (false === $content) {
76
            $error = error_get_last();
77
            throw new IOException($error['message']);
78
        }
79
        return $content;
80
    }
81
82
    /**
83
     * Transforms a value string into a value array.
84
     * Also, if a value array is passed, checks it contains valid data.
85
     *
86
     * @param mixed $value
87
     * @return AssetOperation
88
     */
89
    private function toAssetOperation($value, string $package, string $packageDir) : AssetOperation
90
    {
91
        if (is_array($value)) {
92
            return AssetOperation::buildFromArray($value, $package, $packageDir);
93
        } else {
94
            return AssetOperation::buildFromString((string) $value, $package, $packageDir);
95
        }
96
    }
97
}
98