DNSRecordCollection::count()   A
last analyzed

Complexity

Conditions 1
Paths 1

Size

Total Lines 3
Code Lines 1

Duplication

Lines 0
Ratio 0 %

Importance

Changes 1
Bugs 0 Features 0
Metric Value
cc 1
eloc 1
c 1
b 0
f 0
nc 1
nop 0
dl 0
loc 3
rs 10
1
<?php
2
3
namespace RemotelyLiving\PHPDNS\Entities;
4
5
use ArrayAccess;
6
use ArrayIterator;
7
use Countable;
8
use Iterator;
9
use RemotelyLiving\PHPDNS\Entities\Interfaces\Arrayable;
10
use RemotelyLiving\PHPDNS\Entities\Interfaces\DNSRecordInterface;
11
use RemotelyLiving\PHPDNS\Entities\Interfaces\Serializable;
12
use RemotelyLiving\PHPDNS\Exceptions\InvalidArgumentException;
13
14
use function array_filter;
15
use function array_shift;
16
17
final class DNSRecordCollection extends EntityAbstract implements
18
    ArrayAccess,
19
    Iterator,
20
    Countable,
21
    Arrayable,
22
    Serializable
23
{
24
    private ArrayIterator $records;
25
26
    public function __construct(DNSRecordInterface ...$records)
27
    {
28
        $this->records = new ArrayIterator($records);
29
    }
30
31
    public function toArray(): array
32
    {
33
        return $this->records->getArrayCopy();
34
    }
35
36
    public function pickFirst(): ?DNSRecordInterface
37
    {
38
        $copy = $this->records->getArrayCopy();
39
40
        return array_shift($copy);
41
    }
42
43
    public function filteredByType(DNSRecordType $type): self
44
    {
45
        $fn = fn(DNSRecordInterface $record) => $record->getType()->equals($type);
46
        return new self(...array_filter($this->records->getArrayCopy(), $fn));
47
    }
48
49
    public function has(DNSRecordInterface $lookupRecord): bool
50
    {
51
        foreach ($this->records->getArrayCopy() as $record) {
52
            if ($lookupRecord->equals($record)) {
53
                return true;
54
            }
55
        }
56
57
        return false;
58
    }
59
60
    public function current(): ?DNSRecordInterface
61
    {
62
        return $this->records->current();
63
    }
64
65
    public function next(): void
66
    {
67
        $this->records->next();
68
    }
69
70
    public function key(): bool|int|string|null
71
    {
72
        return $this->records->key();
73
    }
74
75
    public function valid(): bool
76
    {
77
        return $this->records->valid();
78
    }
79
80
    public function rewind(): void
81
    {
82
        $this->records->rewind();
83
    }
84
85
    /**
86
     * @param mixed $offset
87
     */
88
    public function offsetExists($offset): bool
89
    {
90
        return $this->records->offsetExists($offset);
91
    }
92
93
    /**
94
     * @param mixed $offset
95
     */
96
    public function offsetGet($offset): DNSRecordInterface
97
    {
98
        return $this->records->offsetGet($offset);
99
    }
100
101
    /**
102
     * @param mixed $offset
103
     * @param mixed $value
104
     * @throws \RemotelyLiving\PHPDNS\Exceptions\InvalidArgumentException
105
     */
106
    public function offsetSet($offset, $value): void
107
    {
108
        if (!$value instanceof DNSRecordInterface) {
109
            throw new InvalidArgumentException('Invalid value');
110
        }
111
112
        $this->records->offsetSet($offset, /** @scrutinizer ignore-type */ $value);
113
    }
114
115
    /**
116
     * @param mixed $offset
117
     */
118
    public function offsetUnset($offset): void
119
    {
120
        $this->records->offsetUnset($offset);
121
    }
122
123
    public function count(): int
124
    {
125
        return $this->records->count();
126
    }
127
128
    public function isEmpty(): bool
129
    {
130
        return $this->count() === 0;
131
    }
132
133
    public function __serialize(): array
134
    {
135
        return $this->records->getArrayCopy();
136
    }
137
138
    public function __unserialize(array $unserialized): void
139
    {
140
        $this->records = new ArrayIterator($unserialized);
141
    }
142
143
    public function jsonSerialize(): array
144
    {
145
        return $this->toArray();
146
    }
147
148
    public function withUniqueValuesExcluded(): self
149
    {
150
        return $this->filterValues(
151
            fn(DNSRecordInterface $candidateRecord, DNSRecordCollection $remaining): bool => $remaining->has(
152
                $candidateRecord
153
            )
154
        )->withUniqueValues();
155
    }
156
157
    public function withUniqueValues(): self
158
    {
159
        return $this->filterValues(
160
            fn(DNSRecordInterface $candidateRecord, DNSRecordCollection $remaining): bool => !$remaining->has(
161
                $candidateRecord
162
            )
163
        );
164
    }
165
166
    private function filterValues(callable $eval): self
167
    {
168
        $filtered = new self();
169
        $records = $this->records->getArrayCopy();
170
171
        while ($record = array_shift($records)) {
172
            if ($eval($record, new self(...$records))) {
173
                $filtered[] = $record;
174
            }
175
        }
176
177
        return $filtered;
178
    }
179
}
180