AttributesTrait   A
last analyzed

Complexity

Total Complexity 8

Size/Duplication

Total Lines 81
Duplicated Lines 0 %

Importance

Changes 2
Bugs 0 Features 0
Metric Value
eloc 17
c 2
b 0
f 0
dl 0
loc 81
rs 10
wmc 8

6 Methods

Rating   Name   Duplication   Size   Complexity  
A offsetUnset() 0 3 1
A offsetSet() 0 15 3
A offsetExists() 0 3 1
A offsetGet() 0 3 1
A setAttributes() 0 4 1
A getAttributes() 0 3 1
1
<?php
2
3
namespace Helix\DB;
4
5
/**
6
 * Forwards `ArrayAccess` to an EAV array property named `$attributes`.
7
 *
8
 * `ArrayAccess` must be implemented by the class using this trait.
9
 * The `$attributes` property must also be defined in the class,
10
 * and annotated with `@eav <TABLE>`.
11
 *
12
 * The instance must have its attributes loaded before use as an array,
13
 * otherwise existing EAV data may be lost when the instance is saved.
14
 * Attribute loading is done automatically by {@link Record}.
15
 *
16
 * @see Record::load()
17
 */
18
trait AttributesTrait
19
{
20
21
    /**
22
     * Override this property with your own annotation.
23
     *
24
     * This is nullable, and must remain null until it's used.
25
     * Once this is an array, {@link Record::save()} will delete any attributes not in the array.
26
     * So for example, this must not default to an empty array during construction.
27
     *
28
     * All of the {@link Record} methods that return/fetch entities will automatically preload these.
29
     *
30
     * @eav table_name_here
31
     * @var string[] This can be changed to other scalar-typed arrays.
32
     */
33
    protected ?array $attributes;
34
35
    /**
36
     * @return scalar[]
37
     */
38
    public function getAttributes(): array
39
    {
40
        return $this->attributes ?? [];
41
    }
42
43
    /**
44
     * @param mixed $attr
45
     * @return bool
46
     */
47
    public function offsetExists($attr): bool
48
    {
49
        return isset($this->attributes[$attr]);
50
    }
51
52
    /**
53
     * @param mixed $attr
54
     * @return null|scalar
55
     */
56
    public function offsetGet($attr)
57
    {
58
        return $this->attributes[$attr] ?? null;
59
    }
60
61
    /**
62
     * @param mixed $attr
63
     * @param null|scalar $value
64
     */
65
    public function offsetSet($attr, $value): void
66
    {
67
        if (isset($attr)) {
68
            if (isset($value)) {
69
                assert(is_scalar($value));
70
                $this->attributes[$attr] = $value;
71
            } else {
72
                $this->offsetUnset($attr);
73
            }
74
        } else {
75
            // appending must not be null.
76
            // even though missing numeric offsets would yield null when fetched individually,
77
            // getAttributes() would not have them.
78
            assert(isset($value));
79
            $this->attributes[] = $value;
80
        }
81
    }
82
83
    /**
84
     * @param mixed $attr
85
     */
86
    public function offsetUnset($attr): void
87
    {
88
        unset($this->attributes[$attr]);
89
    }
90
91
    /**
92
     * @param scalar[] $attributes
93
     * @return $this
94
     */
95
    public function setAttributes(array $attributes)
96
    {
97
        $this->attributes = array_filter($attributes, 'is_scalar');
98
        return $this;
99
    }
100
}
101