-
-
Notifications
You must be signed in to change notification settings - Fork 312
/
Copy pathQueryResult.php
112 lines (87 loc) · 2.52 KB
/
QueryResult.php
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
<?php
declare(strict_types = 1);
namespace Embed;
use Closure;
use DOMElement;
use DOMNodeList;
use Psr\Http\Message\UriInterface;
use Throwable;
class QueryResult
{
private Extractor $extractor;
private array $nodes = [];
public function __construct(DOMNodeList $result, Extractor $extractor)
{
$this->nodes = iterator_to_array($result, false);
$this->extractor = $extractor;
}
public function node(): ?DOMElement
{
return $this->nodes[0] ?? null;
}
public function nodes(): array
{
return $this->nodes;
}
public function filter(Closure $callback): self
{
$this->nodes = array_filter($this->nodes, $callback);
return $this;
}
public function get(?string $attribute = null)
{
$node = $this->node();
if (!$node) {
return null;
}
return $attribute ? self::getAttribute($node, $attribute) : $node->nodeValue;
}
public function getAll(?string $attribute = null): array
{
$nodes = $this->nodes();
return array_filter(
array_map(
fn ($node) => $attribute ? self::getAttribute($node, $attribute) : $node->nodeValue,
$nodes
)
);
}
public function str(?string $attribute = null): ?string
{
$value = $this->get($attribute);
return $value ? clean($value) : null;
}
public function strAll(?string $attribute = null): array
{
return array_filter(array_map(fn ($value) => clean($value), $this->getAll($attribute)));
}
public function int(?string $attribute = null): ?int
{
$value = $this->get($attribute);
return $value ? (int) $value : null;
}
public function url(?string $attribute = null): ?UriInterface
{
$value = $this->get($attribute);
if (!$value) {
return null;
}
try {
return $this->extractor->resolveUri($value);
} catch (Throwable $error) {
return null;
}
}
private static function getAttribute(DOMElement $node, string $name): ?string
{
//Don't use $node->getAttribute() because it does not work with namespaces (ex: xml:lang)
$attributes = $node->attributes;
for ($i = 0; $i < $attributes->length; ++$i) {
$attribute = $attributes->item($i);
if ($attribute->name === $name) {
return $attribute->nodeValue;
}
}
return null;
}
}