Failed Conditions
Push — master ( ffa886...8c8aba )
by Vladimir
16:14
created

NodeList   A

Complexity

Total Complexity 16

Size/Duplication

Total Lines 130
Duplicated Lines 0 %

Test Coverage

Coverage 71.05%

Importance

Changes 1
Bugs 0 Features 0
Metric Value
wmc 16
eloc 25
c 1
b 0
f 0
dl 0
loc 130
ccs 27
cts 38
cp 0.7105
rs 10

10 Methods

Rating   Name   Duplication   Size   Complexity  
A offsetExists() 0 3 1
A __construct() 0 3 1
A create() 0 3 1
A getIterator() 0 4 2
A offsetSet() 0 17 3
A splice() 0 3 1
A count() 0 3 1
A offsetUnset() 0 3 1
A merge() 0 7 2
A offsetGet() 0 11 3
1
<?php
2
3
declare(strict_types=1);
4
5
namespace GraphQL\Language\AST;
6
7
use ArrayAccess;
8
use Countable;
9
use GraphQL\Utils\AST;
10
use InvalidArgumentException;
11
use IteratorAggregate;
12
use Traversable;
13
use function array_merge;
14
use function array_splice;
15
use function count;
16
use function is_array;
17
18
/**
19
 * @template T of Node
20
 * @phpstan-implements ArrayAccess<int|string, T>
21
 * @phpstan-implements IteratorAggregate<T>
22
 */
23
class NodeList implements ArrayAccess, IteratorAggregate, Countable
24
{
25
    /**
26
     * @var Node[]
27
     * @phpstan-var array<T>
28
     */
29
    private $nodes;
30
31
    /**
32
     * @param Node[] $nodes
33
     *
34
     * @phpstan-param array<T> $nodes
35
     * @phpstan-return self<T>
36
     */
37 1
    public static function create(array $nodes) : self
38
    {
39 1
        return new static($nodes);
40
    }
41
42
    /**
43
     * @param Node[] $nodes
44
     *
45
     * @phpstan-param array<T> $nodes
46
     */
47 1003
    public function __construct(array $nodes)
48
    {
49 1003
        $this->nodes = $nodes;
50 1003
    }
51
52
    /**
53
     * @param int|string $offset
54
     */
55
    public function offsetExists($offset) : bool
56
    {
57
        return isset($this->nodes[$offset]);
58
    }
59
60
    /**
61
     * TODO enable strict typing by changing how the Visitor deals with NodeList.
62
     * Ideally, this function should always return a Node instance.
63
     * However, the Visitor currently allows mutation of the NodeList
64
     * and puts arbitrary values in the NodeList, such as strings.
65
     * We will have to switch to using an array or a less strict
66
     * type instead so we can enable strict typing in this class.
67
     *
68
     * @param int|string $offset
69
     *
70
     * @phpstan-return T
71
     */
72 968
    public function offsetGet($offset)// : Node
73
    {
74 968
        $item = $this->nodes[$offset];
75
76 968
        if (is_array($item) && isset($item['kind'])) {
0 ignored issues
show
introduced by
The condition is_array($item) is always false.
Loading history...
77
            /** @phpstan-var T $node */
78 2
            $node                 = AST::fromArray($item);
79 2
            $this->nodes[$offset] = $node;
80
        }
81
82 968
        return $this->nodes[$offset];
83
    }
84
85
    /**
86
     * @param int|string   $offset
87
     * @param Node|mixed[] $value
88
     *
89
     * @phpstan-param T|mixed[] $value
90
     */
91 138
    public function offsetSet($offset, $value) : void
92
    {
93 138
        if (is_array($value)) {
94
            if (isset($value['kind'])) {
95
                /** @phpstan-var T $node */
96
                $node                 = AST::fromArray($value);
97
                $this->nodes[$offset] = $node;
98
99
                return;
100
            }
101
102
            throw new InvalidArgumentException(
103
                'Expected array value to be valid node data structure, missing key "kind"'
104
            );
105
        }
106
107 138
        $this->nodes[$offset] = $value;
108 138
    }
109
110
    /**
111
     * @param int|string $offset
112
     */
113
    public function offsetUnset($offset) : void
114
    {
115
        unset($this->nodes[$offset]);
116
    }
117
118
    /**
119
     * @param mixed $replacement
120
     *
121
     * @phpstan-return NodeList<T>
122
     */
123 4
    public function splice(int $offset, int $length, $replacement = null) : NodeList
124
    {
125 4
        return new NodeList(array_splice($this->nodes, $offset, $length, $replacement));
126
    }
127
128
    /**
129
     * @param NodeList|Node[] $list
130
     *
131
     * @phpstan-param NodeList<T>|array<T> $list
132
     * @phpstan-return NodeList<T>
133
     */
134 60
    public function merge($list) : NodeList
135
    {
136 60
        if ($list instanceof self) {
137 60
            $list = $list->nodes;
138
        }
139
140 60
        return new NodeList(array_merge($this->nodes, $list));
141
    }
142
143 790
    public function getIterator() : Traversable
144
    {
145 790
        foreach ($this->nodes as $key => $_) {
146 754
            yield $this->offsetGet($key);
147
        }
148 788
    }
149
150 768
    public function count() : int
151
    {
152 768
        return count($this->nodes);
153
    }
154
}
155