Passed
Push — master ( d1d055...513454 )
by Andreas
14:02
created

dbobject::__set()   D

Complexity

Conditions 19
Paths 26

Size

Total Lines 47
Code Lines 33

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 32
CRAP Score 19.01

Importance

Changes 1
Bugs 0 Features 0
Metric Value
cc 19
eloc 33
c 1
b 0
f 0
nc 26
nop 2
dl 0
loc 47
ccs 32
cts 33
cp 0.9697
crap 19.01
rs 4.5166

How to fix   Complexity   

Long Method

Small methods make your code easier to understand, in particular if combined with a good name. Besides, if your method is small, finding a good name is usually much easier.

For example, if you find yourself adding comments to a method's body, this is usually a good sign to extract the commented part to a new method, and use the comment as a starting point when coming up with a good name for this new method.

Commonly applied refactorings include:

1
<?php
2
/**
3
 * @author CONTENT CONTROL http://www.contentcontrol-berlin.de/
4
 * @copyright CONTENT CONTROL http://www.contentcontrol-berlin.de/
5
 * @license http://www.gnu.org/licenses/gpl.html GNU General Public License
6
 */
7
namespace midgard\portable\api;
8
9
use midgard\portable\storage\connection;
10
use Doctrine\Persistence\ObjectManager;
11
use Doctrine\Persistence\Mapping\ClassMetadata;
12
use midgard_datetime;
13
14
abstract class dbobject
15
{
16
    protected string $guid = '';
17
18
    /**
19
     * @var \midgard\portable\mapping\classmetadata
20
     */
21
    protected $cm;
22
23
    /**
24
     * Simple map of association fields changed during the object's lifetime
25
     *
26
     * We need this for some workarounds for proxy-related problems during changeset calculation
27
     */
28
    protected array $changed_associations = [];
29
30
    /**
31
     * {@inheritDoc}
32
     */
33 82
    public function injectObjectManager(ObjectManager $objectmanager, ClassMetadata $classmetadata)
34
    {
35 82
        if ($objectmanager !== connection::get_em()) {
0 ignored issues
show
introduced by
The condition $objectmanager !== midga...ge\connection::get_em() is always true.
Loading history...
36
            throw new \RuntimeException("Trying to use midgard_dbobject with different ObjectManager instances");
37
        }
38
39 82
        $this->cm = $classmetadata;
40
    }
41
42 27
    public function __get_changed_associations() : array
43
    {
44 27
        return $this->changed_associations;
45
    }
46
47
    /**
48
     * Filter out internal stuff for var_dump
49
     *
50
     * This is not 100% accurate right now (e.g. metadata is not handled totally correctly), but at least it
51
     * prevents killing the server by dumping recursively linked EntityManagers and the like
52
     *
53
     * @return array
54
     */
55 1
    public function __debugInfo()
56
    {
57 1
        $this->initialize();
58 1
        $properties = array_merge($this->cm->getFieldNames(), $this->cm->getAssociationNames(), array_keys($this->cm->midgard['field_aliases']));
59 1
        $properties = array_filter($properties, function ($input) {
60 1
            return !str_contains($input, 'metadata_');
61 1
        });
62 1
        $ret = [];
63 1
        foreach ($properties as $property) {
64 1
            $ret[$property] = $this->__get($property);
65
        }
66
67 1
        return $ret;
68
    }
69
70 126
    public function __set($field, $value)
71
    {
72 126
        $this->initialize();
73
74 126
        if (   !$this->cm->hasField($field)
75 126
            && isset($this->cm->midgard['field_aliases'][$field])) {
76
            $field = $this->cm->midgard['field_aliases'][$field];
77
        }
78 126
        if ($this->cm->isSingleValuedAssociation($field)) {
79
            // mgd api only allows setting links identifiers, doctrine wants objects,
80
            // so it seems we need an expensive and pretty useless conversion..
81 57
            if (empty($value)) {
82 37
                $value = null;
83
            } else {
84 36
                if (   !\is_object($this->$field)
85 36
                    || $this->$field->id != $value) {
86 36
                    $this->changed_associations[$field] = true;
87
                }
88 36
                $classname = $this->cm->getAssociationTargetClass($field);
89 57
                $value = connection::get_em()->getReference($classname, $value);
90
            }
91 126
        } elseif ($this->cm->hasField($field)) {
92 125
            $mapping = $this->cm->getFieldMapping($field);
93
94 125
            if (   $mapping['type'] === 'string'
95 125
                || $mapping['type'] == 'text') {
96 124
                $value = (string) $value;
97 120
            } elseif ($mapping['type'] === 'integer') {
98 120
                $value = (int) $value;
99 120
                if ($value === 0 && $this->cm->isIdentifier($field)) {
100 120
                    $value = null;
101
                }
102 101
            } elseif ($mapping['type'] === 'boolean') {
103 42
                $value = (boolean) $value;
104 101
            } elseif ($mapping['type'] === 'float') {
105 8
                $value = (float) $value;
106 101
            } elseif (in_array($mapping['type'], ['datetime', 'date'])) {
107 101
                if (   \is_string($value)
108 101
                    && $value !== '0000-00-00 00:00:00') {
109 7
                    $value = new midgard_datetime($value);
110 100
                } elseif (!($value instanceof midgard_datetime)) {
111 1
                    $value = new midgard_datetime('0001-01-01 00:00:00');
112
                }
113
            }
114
        }
115
116 126
        $this->$field = $value;
117
    }
118
119 137
    public function __get($field)
120
    {
121 137
        $this->initialize();
122
123 137
        if (   !$this->cm->hasField($field)
124 137
            && isset($this->cm->midgard['field_aliases'][$field])) {
125
            $field = $this->cm->midgard['field_aliases'][$field];
126
        }
127
128 137
        if ($this->cm->isSingleValuedAssociation($field)) {
129
            // mgd api only allows returning link identifiers, doctrine has objects,
130
            // so it seems we need a pretty useless conversion..
131 108
            if (is_object($this->$field)) {
132 36
                return (int) $this->$field->id;
133
            }
134 108
            return 0;
135
        }
136 136
        if (   $this->$field === null
137 136
            && $this->cm->isIdentifier($field)) {
138 103
            return 0;
139
        }
140 134
        if (   $this->$field instanceof midgard_datetime
141 134
            && $this->$field->format('U') == -62169984000) {
142
            //This is mainly needed for working with converted Legacy databases. Midgard2 somehow handles this internally
143
            //@todo Find a nicer solution and research how QB handles this
144 1
            $this->$field->setDate(1, 1, 1);
145
        }
146
147 134
        return $this->$field;
148
    }
149
150 123
    public function __isset($field)
151
    {
152 123
        return property_exists($this, $field);
153
    }
154
155 54
    protected function populate_from_entity(dbobject $entity)
156
    {
157 54
        $this->initialize();
158 54
        foreach ($this->cm->reflFields as $name => $field) {
159 54
            $this->$name = $entity->$name;
160
        }
161
    }
162
163 143
    protected function initialize()
164
    {
165 143
        $this->cm ??= connection::get_em()->getClassMetadata(get_class($this));
166
    }
167
}
168