Test Failed
Branch master (bee4a6)
by stéphane
14:37
created

YamlObject   A

Complexity

Total Complexity 20

Size/Duplication

Total Lines 180
Duplicated Lines 0 %

Importance

Changes 0
Metric Value
wmc 20
eloc 41
dl 0
loc 180
rs 10
c 0
b 0
f 0

14 Methods

Rating   Name   Duplication   Size   Complexity  
A __construct() 0 4 1
A jsonSerialize() 0 7 3
A getOptions() 0 3 1
A addReference() 0 8 2
A getReference() 0 10 2
A getComment() 0 6 2
A setText() 0 4 1
A setDocStart() 0 3 1
A getAllReferences() 0 3 1
A __toString() 0 3 1
A addComment() 0 3 1
A addTag() 0 7 2
A isTagged() 0 3 1
A hasDocStart() 0 3 1
1
<?php
2
3
namespace Dallgoot\Yaml\Types;
4
5
use Dallgoot\Yaml\YamlProperties;
6
7
/**
8
 *  The returned object representing a YAML document
9
 *
10
 * @author  Stéphane Rebai <[email protected]>
11
 * @license Apache 2.0
12
 * @link    https://github.com/dallgoot/yaml
13
 */
14
class YamlObject extends \ArrayIterator implements \JsonSerializable
15
{
16
    private YamlProperties $__yaml__object__api;
17
18
    const UNDEFINED_METHOD = self::class . ": undefined method '%s', valid methods are (addReference,getReference,getAllReferences,addComment,getComment,setText,addTag,hasDocStart,isTagged)";
19
    const UNKNOWN_REFERENCE = "no reference named: '%s', known are : (%s)";
20
    const UNAMED_REFERENCE  = "reference MUST have a name";
21
    const TAGHANDLE_DUPLICATE = "Tag handle '%s' already declared before, handle must be unique";
22
23
    /**
24
     * Construct the YamlObject making sure the indices can be accessed directly
25
     * and creates the API object with a reference to this YamlObject.
26
     * @todo check indices access outside of foreach loop
27
     */
28
    public function __construct($buildingOptions)
29
    {
30
        parent::__construct([], 1); //1 = Array indices can be accessed as properties in read/write.
31
        $this->__yaml__object__api = new YamlProperties($buildingOptions);
32
    }
33
34
    /**
35
     * Returns a string representation of the YamlObject when
36
     * it has NO property NOR keys ie. is only a LITTERAL
37
     *
38
     * @return string String representation of the object.
39
     */
40
    public function __toString(): string
41
    {
42
        return $this->__yaml__object__api->value ?? serialize($this);
43
    }
44
45
    public function getOptions()
46
    {
47
        return $this->__yaml__object__api->_options;
48
    }
49
    /**
50
     * Adds a reference.
51
     *
52
     * @param mixed  $value The reference value
53
     *
54
     * @throws \UnexpectedValueException  (description)
55
     * @return mixed
56
     */
57
    public function &addReference(string $name, $value)
58
    {
59
        if (empty($name)) {
60
            throw new \UnexpectedValueException(self::UNAMED_REFERENCE);
61
        }
62
        // var_dump("DEBUG: '$name' added as reference");
63
        $this->__yaml__object__api->_anchors[$name] = $value;
64
        return $this->__yaml__object__api->_anchors[$name];
65
    }
66
67
    /**
68
     * Return the reference saved by $name
69
     *
70
     * @return mixed Value of the reference
71
     * @throws \UnexpectedValueException    if there's no reference by that $name
72
     */
73
    public function &getReference(string $name)
74
    {
75
        if (array_key_exists($name, $this->__yaml__object__api->_anchors)) {
76
            return $this->__yaml__object__api->_anchors[$name];
77
        }
78
        throw new \UnexpectedValueException(
79
            sprintf(
80
                self::UNKNOWN_REFERENCE,
81
                $name,
82
                implode(',', array_keys($this->__yaml__object__api->_anchors))
83
            )
84
        );
85
    }
86
87
    /**
88
     * Return array with all references as Keys and their values, declared for this YamlObject
89
     *
90
     * @return array
91
     */
92
    public function getAllReferences(): array
93
    {
94
        return $this->__yaml__object__api->_anchors;
95
    }
96
97
    /**
98
     * Adds a comment.
99
     *
100
     * @param int    $lineNumber The line number at which the comment should appear
101
     * @param string $value      The comment
102
     *
103
     * @return null
104
     */
105
    public function addComment(int $lineNumber, string $value): void
106
    {
107
        $this->__yaml__object__api->_comments[$lineNumber] = $value;
108
    }
109
110
    /**
111
     * Gets the comment at $lineNumber
112
     *
113
     * @return string|array<int,string> The comment at $lineNumber OR all comments.
114
     */
115
    public function getComment(?int $lineNumber = 0)
116
    {
117
        if (array_key_exists((string) $lineNumber, $this->__yaml__object__api->_comments)) {
118
            return $this->__yaml__object__api->_comments[$lineNumber];
119
        }
120
        return $this->__yaml__object__api->_comments;
121
    }
122
123
    /**
124
     * Sets the text when the content is *only* a literal
125
     */
126
    public function setText(string $value): YamlObject
127
    {
128
        $this->__yaml__object__api->value .= ltrim($value);
129
        return $this;
130
    }
131
132
    /**
133
     * TODO:  what to do with these tags ???
134
     * Adds a tag.
135
     *
136
     * @param string $handle The handle declared for the tag
137
     * @param string $prefix The prefix/namespace/schema that defines the tag
138
     *
139
     * @return null
140
     */
141
    public function addTag(string $handle, string $prefix)
142
    {
143
        //  It is an error to specify more than one “TAG” directive for the same handle in the same document, even if both occurrences give the same prefix.
144
        if (array_key_exists($handle, $this->__yaml__object__api->_tags)) {
145
            throw new \Exception(sprintf(self::TAGHANDLE_DUPLICATE, $handle), 1);
146
        }
147
        $this->__yaml__object__api->_tags[$handle] = $prefix;
148
    }
149
150
    /**
151
     * Determines if it has YAML document start string => '---'.
152
     *
153
     * @return boolean  True if document has start, False otherwise.
154
     */
155
    public function hasDocStart(): bool
156
    {
157
        return is_bool($this->__yaml__object__api->_hasDocStart);
158
    }
159
160
    /**
161
     * Sets the document start.
162
     *
163
     * @param null|bool $value The value : null = no docstart, true = docstart before document comments, false = docstart after document comments
164
     *
165
     * @return null
166
     */
167
    public function setDocStart($value)
168
    {
169
        $this->__yaml__object__api->_hasDocStart = $value;
170
    }
171
172
    /**
173
     * Is the whole YAML document (YamlObject) tagged ?
174
     *
175
     * @return bool
176
     */
177
    public function isTagged()
178
    {
179
        return !empty($this->__yaml__object__api->_tags);
180
    }
181
182
    /**
183
     * Filters unwanted property for JSON serialization
184
     *
185
     * @return mixed Array (of object properties or keys) OR string if YAML object only contains LITTERAL (in self::value)
186
     */
187
    public function jsonSerialize()
188
    {
189
        $prop = get_object_vars($this);
190
        unset($prop["__yaml__object__api"]);
191
        if (count($prop) > 0) return $prop;
192
        if (count($this) > 0) return iterator_to_array($this);
193
        return $this->__yaml__object__api->value ?? "_Empty YamlObject_";
194
    }
195
}
196