DataMutator   A
last analyzed

Complexity

Total Complexity 15

Size/Duplication

Total Lines 85
Duplicated Lines 0 %

Importance

Changes 1
Bugs 0 Features 0
Metric Value
wmc 15
eloc 37
c 1
b 0
f 0
dl 0
loc 85
rs 10

3 Methods

Rating   Name   Duplication   Size   Complexity  
A addNewEntry() 0 13 3
B setIndexed() 0 37 10
A setByPath() 0 14 2
1
<?php
2
3
declare(strict_types=1);
4
5
namespace Communibase\DataBag;
6
7
final class DataMutator
8
{
9
    /**
10
     * @var array<string,array>
11
     */
12
    private $data;
13
14
    /**
15
     * @param array<string,mixed> $data
16
     * @param mixed $value
17
     */
18
    public function setByPath(array &$data, string $path, $value): void
19
    {
20
        $this->data = &$data;
21
22
        [$entityType, $path] = explode('.', $path, 2);
23
24
        // Direct property
25
        if (strpos($path, '.') === false) {
26
            $data[$entityType][$path] = $value;
27
            return;
28
        }
29
30
        // Indexed
31
        $this->setIndexed($entityType, $path, $value);
32
    }
33
34
    /**
35
     * @param mixed $value
36
     */
37
    private function setIndexed(string $entityType, string $path, $value): void
38
    {
39
        [$path, $index] = explode('.', $path, 2);
40
41
        $field = null;
42
        if (strpos($index, '.') > 0) {
43
            [$index, $field] = explode('.', $index, 2);
44
        }
45
46
        $target = $index;
47
        if (!is_numeric($index)) {
48
            if (\is_array($value)) {
49
                $value['type'] = $index;
50
            }
51
            $index = null;
52
            if (isset($this->data[$entityType][$path])) {
53
                foreach ((array)$this->data[$entityType][$path] as $nodeIndex => $node) {
54
                    if (isset($node['type']) && $node['type'] === $target) {
55
                        $index = $nodeIndex;
56
                        break;
57
                    }
58
                }
59
            }
60
        }
61
62
        // No index found, new entry
63
        if ($index === null) {
64
            $this->addNewEntry($entityType, $path, $field, $target, $value);
65
            return;
66
        }
67
68
        // Use found index
69
        if ($field === null) {
70
            $this->data[$entityType][$path][$index] = $value;
71
            return;
72
        }
73
        $this->data[$entityType][$path][$index][$field] = $value;
74
    }
75
76
    /**
77
     * @param mixed $value
78
     */
79
    private function addNewEntry(string $entityType, string $path, ?string $field, string $target, $value): void
80
    {
81
        if ($field === null) {
82
            $this->data[$entityType][$path][] = $value;
83
            return;
84
        }
85
        $value = [
86
            $field => $value
87
        ];
88
        if (!is_numeric($target)) {
89
            $value['type'] = $target;
90
        }
91
        $this->data[$entityType][$path][] = $value;
92
    }
93
}
94