Completed
Push — master ( faa599...1fb1b7 )
by
unknown
24:44
created

GeneratorProxyTrait::__invoke()   A

Complexity

Conditions 2
Paths 2

Size

Total Lines 8
Code Lines 4

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 2
eloc 4
nc 2
nop 1
dl 0
loc 8
rs 9.4285
c 0
b 0
f 0
1
<?php
2
3
/**
4
 * This file is part of the eZ Publish Kernel package.
5
 *
6
 * @copyright Copyright (C) eZ Systems AS. All rights reserved.
7
 * @license For full copyright and license information view LICENSE file distributed with this source code.
8
 */
9
namespace eZ\Publish\Core\Repository\Values;
10
11
use Generator;
12
13
/**
14
 * Trait for proxies, covers all relevant magic methods and exposes private method to load object.
15
 *
16
 * Uses generator internally to be able to cleanly execute object load async on-demand.
17
 *
18
 * @internal Meant for internal use by Repository!
19
 */
20
trait GeneratorProxyTrait
21
{
22
    /**
23
     * Overload this for correct type hint on object type.
24
     *
25
     * @var object|null
26
     */
27
    protected $object;
28
29
    /**
30
     * Needs to be protected as value objects often define this as well.
31
     *
32
     * @var mixed
33
     */
34
    protected $id;
35
36
    /**
37
     * @var Generator|null
38
     */
39
    private $generator;
40
41
    /**
42
     * GeneratorProxyTrait constructor.
43
     *
44
     * @param Generator $generator
45
     * @param mixed $id Object id to use for loading the object on demand.
46
     */
47
    public function __construct(Generator $generator, $id)
48
    {
49
        $this->generator = $generator;
50
        $this->id = $id;
51
    }
52
53
    public function __call($name, $arguments)
54
    {
55
        if ($this->object === null) {
56
            $this->loadObject();
57
        }
58
59
        return $this->object->$name(...$arguments);
60
    }
61
62
    public function __invoke(...$args)
63
    {
64
        if ($this->object === null) {
65
            $this->loadObject();
66
        }
67
68
        return ($this->object)(...$args);
69
    }
70
71 View Code Duplication
    public function __get($name)
72
    {
73
        if ($name === 'id') {
74
            return $this->id;
75
        }
76
77
        if ($this->object === null) {
78
            $this->loadObject();
79
        }
80
81
        return $this->object->$name;
82
    }
83
84 View Code Duplication
    public function __isset($name)
85
    {
86
        if ($name === 'id') {
87
            return true;
88
        }
89
90
        if ($this->object === null) {
91
            $this->loadObject();
92
        }
93
94
        return isset($this->object->$name);
95
    }
96
97
    public function __unset($name)
98
    {
99
        if ($this->object === null) {
100
            $this->loadObject();
101
        }
102
103
        unset($this->object->$name);
104
    }
105
106
    public function __set($name, $value)
107
    {
108
        if ($this->object === null) {
109
            $this->loadObject();
110
        }
111
112
        $this->object->$name = $value;
113
    }
114
115
    public function __toString()
116
    {
117
        if ($this->object === null) {
118
            $this->loadObject();
119
        }
120
121
        return (string)$this->object;
122
    }
123
124
    public function __sleep()
125
    {
126
        if ($this->object === null) {
127
            $this->loadObject();
128
        }
129
130
        return ['object', 'id'];
131
    }
132
133
    public function __debugInfo()
134
    {
135
        if ($this->object === null) {
136
            $this->loadObject();
137
        }
138
139
        return [
140
            'object' => $this->object,
141
            'id' => $this->id,
142
        ];
143
    }
144
145
    /**
146
     * Loads the generator to object value and unset's generator.
147
     *
148
     * Can only be called once, so check presence of $this->object before using it.
149
     *
150
     * This assumes generator is made to support bulk loading of several objects, and thus takes object id as input
151
     * in order to return right object at a time, and thus performs two yields per item.
152
     * -> See PR that came with this trait for example generators.
153
     */
154
    protected function loadObject()
155
    {
156
        $this->object = $this->generator->send($this->id);
157
        $this->generator->next();
158
        unset($this->generator);
159
    }
160
}
161