Passed
Push — master ( 419cde...d38a64 )
by stéphane
02:51
created

Builder::getChildrenTypes()   A

Complexity

Conditions 2
Paths 2

Size

Total Lines 7
Code Lines 4

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 2
eloc 4
nc 2
nop 1
dl 0
loc 7
rs 10
c 0
b 0
f 0
1
<?php
2
0 ignored issues
show
Coding Style introduced by
Missing file doc comment
Loading history...
3
namespace Dallgoot\Yaml;
4
5
use Dallgoot\Yaml as Y;
6
7
/**
8
 * Constructs the result (YamlObject or array) according to every Node and respecting value
9
 * @category tag in class comment
0 ignored issues
show
Coding Style introduced by
There must be exactly one blank line before the tags in a doc comment
Loading history...
Coding Style introduced by
Category name "tag in class comment" is not valid; consider "Tag_In_Class_Comment" instead
Loading history...
10
 * @package tag in class comment
1 ignored issue
show
Coding Style introduced by
Package name "tag in class comment" is not valid; consider "Tag_In_Class_Comment" instead
Loading history...
Coding Style introduced by
Tag value indented incorrectly; expected 2 spaces but found 1
Loading history...
11
 * @author tag in class comment
1 ignored issue
show
Coding Style introduced by
Content of the @author tag must be in the form "Display Name <[email protected]>"
Loading history...
Coding Style introduced by
Tag value indented incorrectly; expected 3 spaces but found 1
Loading history...
12
 * @license tag in class comment
1 ignored issue
show
Coding Style introduced by
Tag value indented incorrectly; expected 2 spaces but found 1
Loading history...
13
 */
0 ignored issues
show
Coding Style introduced by
Missing @link tag in class comment
Loading history...
14
final class Builder
15
{
16
    private static $_root;
17
    private static $_debug;
18
19
    const ERROR_NO_KEYNAME = self::class.": key has NO IDENTIFIER on line %d";
20
    const INVALID_DOCUMENT = self::class.": DOCUMENT %d can NOT be a mapping AND a sequence";
21
22
23
    private static function build(object $node, &$parent = null)
0 ignored issues
show
Coding Style introduced by
Missing function doc comment
Loading history...
24
    {
25
        if ($node instanceof NodeList) return self::buildNodeList($node, $parent);
26
        return self::buildNode($node, $parent);
27
    }
28
29
    private static function buildNodeList(NodeList $node, &$parent)
0 ignored issues
show
Coding Style introduced by
Private method name "Builder::buildNodeList" must be prefixed with an underscore
Loading history...
Coding Style introduced by
Missing function doc comment
Loading history...
30
    {
31
        $type = &$node->type;
32
        if ($type & (Y\RAW | Y\LITTERALS)) {
0 ignored issues
show
Bug introduced by
The constant Dallgoot\Yaml\Y\RAW was not found. Maybe you did not declare it correctly or list all dependencies?
Loading history...
33
            return self::litteral($node, $type);
34
        }
35
        $p = $parent;
36
        switch ($type) {
37
            case Y\MAPPING: //fall through
1 ignored issue
show
Bug introduced by
The constant Dallgoot\Yaml\Y\MAPPING was not found. Maybe you did not declare it correctly or list all dependencies?
Loading history...
Coding Style introduced by
Line indented incorrectly; expected 8 spaces, found 12
Loading history...
38
            case Y\SET:      $p = new \StdClass; break;
1 ignored issue
show
Bug introduced by
The constant Dallgoot\Yaml\Y\SET was not found. Maybe you did not declare it correctly or list all dependencies?
Loading history...
Coding Style introduced by
Line indented incorrectly; expected 8 spaces, found 12
Loading history...
Coding Style introduced by
Closing brace must be on a line by itself
Loading history...
39
            case Y\SEQUENCE: $p = []; break;
1 ignored issue
show
Bug introduced by
The constant Dallgoot\Yaml\Y\SEQUENCE was not found. Maybe you did not declare it correctly or list all dependencies?
Loading history...
Coding Style introduced by
Line indented incorrectly; expected 8 spaces, found 12
Loading history...
Coding Style introduced by
Closing brace must be on a line by itself
Loading history...
40
            // case Y\KEY: $p = $parent;break;
41
        }
42
        $out = null;
43
        foreach ($node as $child) {
44
            $result = self::build($child, $p);
45
            if (!is_null($result)) {
46
                if (is_string($result)) {
47
                    $out .= $result.' ';
48
                } else {
49
                    return $result;
50
                }
51
            }
52
        }
53
        return is_null($out) ? $p : rtrim($out);
54
    }
55
56
    private static function buildNode(Node $node, &$parent)
0 ignored issues
show
Coding Style introduced by
Private method name "Builder::buildNode" must be prefixed with an underscore
Loading history...
Coding Style introduced by
Missing function doc comment
Loading history...
57
    {
58
        extract((array) $node, EXTR_REFS);
59
        switch ($type) {
60
            case Y\COMMENT: self::$_root->addComment($line, $value); return;
1 ignored issue
show
Bug introduced by
The constant Dallgoot\Yaml\Y\COMMENT was not found. Maybe you did not declare it correctly or list all dependencies?
Loading history...
Coding Style introduced by
Line indented incorrectly; expected 8 spaces, found 12
Loading history...
Coding Style introduced by
Closing brace must be on a line by itself
Loading history...
61
            case Y\DIRECTIVE: return; //TODO
1 ignored issue
show
Bug introduced by
The constant Dallgoot\Yaml\Y\DIRECTIVE was not found. Maybe you did not declare it correctly or list all dependencies?
Loading history...
Coding Style introduced by
Line indented incorrectly; expected 8 spaces, found 12
Loading history...
Coding Style introduced by
Closing brace must be on a line by itself
Loading history...
62
            case Y\ITEM: self::buildItem($value, $parent); return;
1 ignored issue
show
Bug introduced by
The constant Dallgoot\Yaml\Y\ITEM was not found. Maybe you did not declare it correctly or list all dependencies?
Loading history...
Coding Style introduced by
Line indented incorrectly; expected 8 spaces, found 12
Loading history...
Coding Style introduced by
Closing brace must be on a line by itself
Loading history...
63
            case Y\KEY:  self::buildKey($node, $parent); return;
1 ignored issue
show
Coding Style introduced by
Line indented incorrectly; expected 8 spaces, found 12
Loading history...
Coding Style introduced by
Closing brace must be on a line by itself
Loading history...
64
            case Y\REF_DEF: //fall through
1 ignored issue
show
Bug introduced by
The constant Dallgoot\Yaml\Y\REF_DEF was not found. Maybe you did not declare it correctly or list all dependencies?
Loading history...
Coding Style introduced by
Line indented incorrectly; expected 8 spaces, found 12
Loading history...
65
            case Y\REF_CALL://TODO: self::build returns what ?
1 ignored issue
show
Bug introduced by
The constant Dallgoot\Yaml\Y\REF_CALL was not found. Maybe you did not declare it correctly or list all dependencies?
Loading history...
Coding Style introduced by
Line indented incorrectly; expected 8 spaces, found 12
Loading history...
66
                if (is_object($value)) {
1 ignored issue
show
Coding Style introduced by
Line indented incorrectly; expected 12 spaces, found 16
Loading history...
67
                    $result = self::build($value, $parent);
68
                    if (is_null($result)) {
1 ignored issue
show
Coding Style introduced by
Line indented incorrectly; expected 16 spaces, found 20
Loading history...
69
                        $tmp = $parent;
70
                    } else {
1 ignored issue
show
Coding Style introduced by
Line indented incorrectly; expected 16 spaces, found 20
Loading history...
71
                        $tmp = $result;
72
                    }
1 ignored issue
show
Coding Style introduced by
Line indented incorrectly; expected 16 spaces, found 20
Loading history...
73
                } else {
1 ignored issue
show
Coding Style introduced by
Line indented incorrectly; expected 12 spaces, found 16
Loading history...
74
                    $tmp = $node->getPhpValue();
75
                }
1 ignored issue
show
Coding Style introduced by
Line indented incorrectly; expected 12 spaces, found 16
Loading history...
76
                // $tmp = is_object($value) ? self::build($value, $parent) : $node->getPhpValue();
77
                if ($type === Y\REF_DEF) self::$_root->addReference($identifier, $tmp);
78
                return self::$_root->getReference($identifier);
79
            case Y\SET_KEY:
1 ignored issue
show
Bug introduced by
The constant Dallgoot\Yaml\Y\SET_KEY was not found. Maybe you did not declare it correctly or list all dependencies?
Loading history...
Coding Style introduced by
Line indented incorrectly; expected 8 spaces, found 12
Loading history...
80
                $key = json_encode(self::build($value, $parent), JSON_PARTIAL_OUTPUT_ON_ERROR|JSON_UNESCAPED_SLASHES);
81
                if (empty($key))
82
                    throw new \Exception("Cant serialize complex key: ".var_export($value, true), 1);
83
                $parent->{$key} = null;
84
                return;
85
            case Y\SET_VALUE:
1 ignored issue
show
Bug introduced by
The constant Dallgoot\Yaml\Y\SET_VALUE was not found. Maybe you did not declare it correctly or list all dependencies?
Loading history...
Coding Style introduced by
Line indented incorrectly; expected 8 spaces, found 12
Loading history...
86
                $prop = array_keys(get_object_vars($parent));
87
                $key = end($prop);
88
                if (property_exists($value, "type") && ($value->type & (Y\ITEM|Y\MAPPING))) {
1 ignored issue
show
Bug introduced by
The constant Dallgoot\Yaml\Y\MAPPING was not found. Maybe you did not declare it correctly or list all dependencies?
Loading history...
Coding Style introduced by
Line indented incorrectly; expected 12 spaces, found 16
Loading history...
89
                    $p = $value->type === Y\ITEM ? [] : new \StdClass;
90
                    self::build($value, $p);
91
                } else {
1 ignored issue
show
Coding Style introduced by
Line indented incorrectly; expected 12 spaces, found 16
Loading history...
92
                    $p = self::build($value, $parent->{$key});
93
                }
1 ignored issue
show
Coding Style introduced by
Line indented incorrectly; expected 12 spaces, found 16
Loading history...
94
                $parent->{$key} = $p;
95
                return;
96
            case Y\TAG:
1 ignored issue
show
Bug introduced by
The constant Dallgoot\Yaml\Y\TAG was not found. Maybe you did not declare it correctly or list all dependencies?
Loading history...
Coding Style introduced by
Line indented incorrectly; expected 8 spaces, found 12
Loading history...
97
                if ($parent === self::$_root) {
1 ignored issue
show
Coding Style introduced by
Line indented incorrectly; expected 12 spaces, found 16
Loading history...
98
                    $parent->addTag($identifier); return;
99
                } else {//TODO: have somewhere a list of common tags and their treatment
1 ignored issue
show
Coding Style introduced by
Line indented incorrectly; expected 12 spaces, found 16
Loading history...
100
                    if (in_array($identifier, ['!binary', '!str'])) {
1 ignored issue
show
Coding Style introduced by
Line indented incorrectly; expected 16 spaces, found 20
Loading history...
101
                        if ($value->value instanceof NodeList) $value->value->type = Y\RAW;
0 ignored issues
show
Bug introduced by
The constant Dallgoot\Yaml\Y\RAW was not found. Maybe you did not declare it correctly or list all dependencies?
Loading history...
102
                        else $value->type = Y\RAW;
1 ignored issue
show
Coding Style introduced by
Line indented incorrectly; expected 20 spaces, found 24
Loading history...
103
                    }
1 ignored issue
show
Coding Style introduced by
Line indented incorrectly; expected 16 spaces, found 20
Loading history...
104
                    $val = is_null($value) ? null : self::build(/** @scrutinizer ignore-type */ $value, $node);
2 ignored issues
show
Coding Style introduced by
The open comment tag must be the only content on the line
Loading history...
Coding Style introduced by
Missing short description in doc comment
Loading history...
Coding Style introduced by
The close comment tag must be the only content on the line
Loading history...
105
                    return new Tag($identifier, $val);
106
                }
1 ignored issue
show
Coding Style introduced by
Line indented incorrectly; expected 12 spaces, found 16
Loading history...
107
            default:
1 ignored issue
show
Coding Style introduced by
Line indented incorrectly; expected 8 spaces, found 12
Loading history...
108
                return is_object($value) ? self::build($value, $parent) : $node->getPhpValue();
109
        }
110
    }
111
112
    /**
113
     * Builds a key and set the property + value to the given parent
114
     *
115
     * @param Node $node       The node
2 ignored issues
show
Coding Style introduced by
Expected 9 spaces after parameter type; 1 found
Loading history...
Coding Style introduced by
Expected 3 spaces after parameter name; 7 found
Loading history...
116
     * @param object|array $parent       The parent
1 ignored issue
show
Coding Style introduced by
Expected 1 spaces after parameter name; 7 found
Loading history...
117
     *
118
     * @throws \ParseError if Key has no name(identifier)
119
     * @return null
120
     */
121
    private static function buildKey($node, &$parent):void
0 ignored issues
show
Coding Style introduced by
Private method name "Builder::buildKey" must be prefixed with an underscore
Loading history...
122
    {
123
        extract((array) $node, EXTR_REFS);
124
        if (is_null($identifier)) {
125
            throw new \ParseError(sprintf(self::ERROR_NO_KEYNAME, $line));
126
        } else {
127
            if ($value instanceof Node && ($value->type & (Y\KEY|Y\ITEM))) {
0 ignored issues
show
Bug introduced by
The constant Dallgoot\Yaml\Y\ITEM was not found. Maybe you did not declare it correctly or list all dependencies?
Loading history...
128
                $parent->{$identifier} = $value->type & Y\KEY ? new \StdClass : [];
129
                self::build($value, $parent->{$identifier});
130
            } elseif (is_object($value)) {
131
                $parent->{$identifier} = self::build($value, $parent->{$identifier});
132
            } else {
133
                $parent->{$identifier} = $node->getPhpValue();
134
            }
135
        }
136
    }
137
138
    private static function buildItem($value, &$parent):void
0 ignored issues
show
Coding Style introduced by
Private method name "Builder::buildItem" must be prefixed with an underscore
Loading history...
Coding Style introduced by
Missing function doc comment
Loading history...
139
    {
140
        if (!is_array($parent) && !($parent instanceof \ArrayIterator)) {
141
            throw new \Exception("parent must be an Iterable not ".(is_object($parent) ? get_class($parent) : gettype($parent)), 1);
142
        }
143
        if ($value instanceof Node && $value->type === Y\KEY) {
144
            $parent[$value->identifier] = self::build($value->value, $parent[$value->identifier]);
0 ignored issues
show
Bug introduced by
It seems like $value->value can also be of type null and string; however, parameter $node of Dallgoot\Yaml\Builder::build() does only seem to accept object, maybe add an additional type check? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

144
            $parent[$value->identifier] = self::build(/** @scrutinizer ignore-type */ $value->value, $parent[$value->identifier]);
Loading history...
145
        } else {
146
            $index = count($parent);
147
            $parent[$index] = self::build($value, $parent[$index]);
148
        }
149
    }
150
151
    /**
152
     * Builds a file.  check multiple documents & split if more than one documents
153
     *
154
     * @param   Node   $_root      The root node
3 ignored issues
show
Coding Style introduced by
Expected 1 spaces after parameter type; 3 found
Loading history...
Coding Style introduced by
Expected 2 spaces after parameter name; 6 found
Loading history...
Coding Style introduced by
Tag value indented incorrectly; expected 1 spaces but found 3
Loading history...
155
     * @param   int   $_debug      the level of debugging requested
3 ignored issues
show
Coding Style introduced by
Expected 2 spaces after parameter type; 3 found
Loading history...
Coding Style introduced by
Expected 1 spaces after parameter name; 6 found
Loading history...
Coding Style introduced by
Tag value indented incorrectly; expected 1 spaces but found 3
Loading history...
156
     *
157
     * @return array|YamlObject      list of documents or juste one.
158
     */
159
    public static function buildContent(Node $_root, int $_debug)
160
    {
161
        self::$_debug = $_debug;
162
        $totalDocStart = 0;
163
        $documents = [];
164
        if ($_root->value instanceof Node) {
165
            $q = new NodeList;
166
            $q->push($_root->value);
167
            return self::buildDocument($q, 0);
168
        }
169
        $_root->value->setIteratorMode(NodeList::IT_MODE_DELETE);
0 ignored issues
show
Bug introduced by
The method setIteratorMode() does not exist on null. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

169
        $_root->value->/** @scrutinizer ignore-call */ 
170
                       setIteratorMode(NodeList::IT_MODE_DELETE);

This check looks for calls to methods that do not seem to exist on a given type. It looks for the method on the type itself as well as in inherited classes or implemented interfaces.

This is most likely a typographical error or the method has been renamed.

Loading history...
170
        foreach ($_root->value as $child) {
171
            if ($child->type & Y\DOC_START) $totalDocStart++;
0 ignored issues
show
Bug introduced by
The constant Dallgoot\Yaml\Y\DOC_START was not found. Maybe you did not declare it correctly or list all dependencies?
Loading history...
172
            //if 0 or 1 DOC_START = we are still in first document
173
            $currentDoc = $totalDocStart > 1 ? $totalDocStart - 1 : 0;
174
            if (!isset($documents[$currentDoc])) $documents[$currentDoc] = new NodeList();
175
            $documents[$currentDoc]->push($child);
176
        }
177
        $content = array_map([self::class, 'buildDocument'], $documents, array_keys($documents));
178
        return count($content) === 1 ? $content[0] : $content;
179
    }
180
181
    private static function buildDocument(NodeList $list, int $key):YamlObject
0 ignored issues
show
Coding Style introduced by
Private method name "Builder::buildDocument" must be prefixed with an underscore
Loading history...
Coding Style introduced by
Missing function doc comment
Loading history...
182
    {
183
        self::$_root = new YamlObject();
184
        $childTypes = $list->getTypes();
185
        $isMapping  = (Y\KEY | Y\MAPPING) & $childTypes;
0 ignored issues
show
Bug introduced by
The constant Dallgoot\Yaml\Y\MAPPING was not found. Maybe you did not declare it correctly or list all dependencies?
Loading history...
186
        $isSequence = Y\ITEM & $childTypes;
0 ignored issues
show
Bug introduced by
The constant Dallgoot\Yaml\Y\ITEM was not found. Maybe you did not declare it correctly or list all dependencies?
Loading history...
187
        $isSet      = Y\SET_VALUE & $childTypes;
0 ignored issues
show
Bug introduced by
The constant Dallgoot\Yaml\Y\SET_VALUE was not found. Maybe you did not declare it correctly or list all dependencies?
Loading history...
188
        if ($isMapping && $isSequence) {
189
            throw new \ParseError(sprintf(self::INVALID_DOCUMENT, $key));
190
        } else {
191
            switch (true) {
0 ignored issues
show
Bug Best Practice introduced by
It seems like you are loosely comparing $isSequence of type integer to the boolean true. If you are specifically checking for non-zero, consider using something more explicit like > 0 or !== 0 instead.
Loading history...
Bug Best Practice introduced by
It seems like you are loosely comparing $isSet of type integer to the boolean true. If you are specifically checking for non-zero, consider using something more explicit like > 0 or !== 0 instead.
Loading history...
192
                case $isSequence: $list->type = Y\SEQUENCE;break;
1 ignored issue
show
Bug introduced by
The constant Dallgoot\Yaml\Y\SEQUENCE was not found. Maybe you did not declare it correctly or list all dependencies?
Loading history...
Coding Style introduced by
Line indented incorrectly; expected 12 spaces, found 16
Loading history...
Coding Style introduced by
Closing brace must be on a line by itself
Loading history...
193
                case $isSet:      $list->type = Y\SET;break;
1 ignored issue
show
Bug introduced by
The constant Dallgoot\Yaml\Y\SET was not found. Maybe you did not declare it correctly or list all dependencies?
Loading history...
Coding Style introduced by
Line indented incorrectly; expected 12 spaces, found 16
Loading history...
Coding Style introduced by
Closing brace must be on a line by itself
Loading history...
194
                default:          $list->type = Y\MAPPING;
1 ignored issue
show
Coding Style introduced by
Line indented incorrectly; expected 12 spaces, found 16
Loading history...
195
            }
196
        }
197
        $string = '';
198
        foreach ($list as $child) {
199
            $result = self::build($child, self::$_root);
200
            if (is_string($result)) {
201
                $string .= $result.' ';
202
            }
203
        }
204
        if (!empty($string)) {
205
            self::$_root->setText(rtrim($string));
206
        }
207
        return self::$_root;
208
    }
209
210
    private static function litteral(NodeList $children, $type):string
0 ignored issues
show
Coding Style introduced by
Private method name "Builder::litteral" must be prefixed with an underscore
Loading history...
Coding Style introduced by
Missing function doc comment
Loading history...
211
    {
212
        $children->rewind();
213
        $refIndent = $children->current()->indent;
214
        $separator = $type === Y\RAW ? '' : "\n";
0 ignored issues
show
Bug introduced by
The constant Dallgoot\Yaml\Y\RAW was not found. Maybe you did not declare it correctly or list all dependencies?
Loading history...
215
        $action = function ($c) { return $c->value; };
0 ignored issues
show
Coding Style introduced by
Opening brace must be the last content on the line
Loading history...
Coding Style introduced by
Closing brace must be on a line by itself
Loading history...
216
        if ($type & Y\LITT_FOLDED) {
0 ignored issues
show
Bug introduced by
The constant Dallgoot\Yaml\Y\LITT_FOLDED was not found. Maybe you did not declare it correctly or list all dependencies?
Loading history...
217
            $separator = ' ';
218
            $action = function ($c) use ($refIndent) {
219
                return $c->indent > $refIndent || ($c->type & Y\BLANK) ? "\n".$c->value : $c->value;
220
            };
221
        }
222
        $tmp = [];
223
        $children->rewind();
224
        foreach ($children as $child) {
225
            $tmp[] = $child->value instanceof NodeList ? self::litteral($child->value, $type) : $action($child);
226
        }
227
        return implode($separator, $tmp);
228
    }
229
}
230