1
|
|
|
<?php |
2
|
|
|
|
3
|
|
|
namespace Bludata\Doctrine\Common\Traits; |
4
|
|
|
|
5
|
|
|
use Bludata\Common\Helpers\FormatHelper; |
6
|
|
|
use Bludata\Doctrine\Common\Annotations\ToObject; |
7
|
|
|
use Doctrine\Common\Annotations\AnnotationReader; |
8
|
|
|
use Doctrine\Common\Collections\ArrayCollection; |
9
|
|
|
use Doctrine\ORM\Mapping\Column; |
10
|
|
|
use Doctrine\ORM\Mapping\ManyToMany; |
11
|
|
|
use Doctrine\ORM\Mapping\ManyToOne; |
12
|
|
|
use Doctrine\ORM\Mapping\OneToMany; |
13
|
|
|
use ReflectionClass; |
14
|
|
|
use ReflectionProperty; |
15
|
|
|
|
16
|
|
|
trait SetPropertiesEntityTrait |
17
|
|
|
{ |
18
|
|
|
public function setPropertiesEntity(array $data) |
19
|
|
|
{ |
20
|
|
|
foreach ($data as $key => $value) { |
21
|
|
|
$set = true; |
22
|
|
|
|
23
|
|
View Code Duplication |
if ( |
|
|
|
|
24
|
|
|
((!isset($data['id']) || !is_numeric($data['id'])) && !in_array($key, $this->getOnlyStore())) |
|
|
|
|
25
|
|
|
|| |
26
|
|
|
(isset($data['id']) && is_numeric($data['id']) && !in_array($key, $this->getOnlyUpdate())) |
|
|
|
|
27
|
|
|
) { |
28
|
|
|
$set = false; |
29
|
|
|
} |
30
|
|
|
|
31
|
|
|
$methodSet = 'set'.ucfirst($key); |
32
|
|
|
$methodGet = 'get'.ucfirst($key); |
33
|
|
|
|
34
|
|
|
if (method_exists($this, $methodSet) && $set) { |
35
|
|
|
/* |
36
|
|
|
* Seta a propriedade com o valor enviado pelo usuário. |
37
|
|
|
*/ |
38
|
|
|
$this->$methodSet(is_string($value) && strlen($value) <= 0 ? null : $value); |
|
|
|
|
39
|
|
|
|
40
|
|
|
/** |
41
|
|
|
* Armazena o valor enviado pelo usuário. |
42
|
|
|
*/ |
43
|
|
|
$valueKey = $this->$methodGet(); |
44
|
|
|
|
45
|
|
|
/** |
46
|
|
|
* Classes utilizadas para buscar os metadados da classe e suas propriedades. |
|
|
|
|
47
|
|
|
*/ |
48
|
|
|
$reflectionClass = new ReflectionClass(get_called_class()); |
|
|
|
|
49
|
|
|
$reflectionProperty = new ReflectionProperty(get_called_class(), $key); |
|
|
|
|
50
|
|
|
$annotationReader = new AnnotationReader(); |
|
|
|
|
51
|
|
|
|
52
|
|
|
$propertyAnnotations = $annotationReader->getPropertyAnnotations($reflectionProperty); |
|
|
|
|
53
|
|
|
|
54
|
|
|
/** |
55
|
|
|
* Busca a anotação Doctrine\ORM\Mapping\Column. |
56
|
|
|
*/ |
57
|
|
|
$column = array_filter($propertyAnnotations, function ($annotation) { |
|
|
|
|
58
|
|
|
return $annotation instanceof Column; |
59
|
|
|
}); |
60
|
|
|
|
61
|
|
|
if ($column) { |
|
|
|
|
62
|
|
|
$column = $column[0]; |
63
|
|
|
} |
64
|
|
|
|
65
|
|
|
/** |
66
|
|
|
* Busca a anotação Bludata\Doctrine\Common\Annotations\ToObject. |
|
|
|
|
67
|
|
|
*/ |
68
|
|
|
$toObject = array_filter($propertyAnnotations, function ($annotation) { |
|
|
|
|
69
|
|
|
return $annotation instanceof ToObject; |
70
|
|
|
}); |
71
|
|
|
|
72
|
|
|
/* |
73
|
|
|
* Verifica se a propriedade está usando a anotação Bludata\Doctrine\Common\Annotations\ToObject. |
|
|
|
|
74
|
|
|
*/ |
75
|
|
|
if ($toObject) { |
|
|
|
|
76
|
|
|
/* |
77
|
|
|
* Caso seja um campo de data, utilizamos o método FormatHelper::parseDate para converter o valor enviado pelo usuário para um objeto DateTime. |
|
|
|
|
78
|
|
|
*/ |
79
|
|
|
if ($column instanceof Column && ($column->type == 'date' || $column->type == 'datetime')) { |
|
|
|
|
80
|
|
|
$this->$methodSet( |
81
|
|
|
FormatHelper::parseDate($valueKey) |
82
|
|
|
); |
83
|
|
|
} else { |
84
|
|
|
/** |
85
|
|
|
* Busca pelas anotações Doctrine\ORM\Mapping\ManyToOne || Doctrine\ORM\Mapping\OneToMany || Doctrine\ORM\Mapping\ManyToMany. |
|
|
|
|
86
|
|
|
*/ |
87
|
|
|
$ormMapping = array_filter($propertyAnnotations, function ($annotation) { |
|
|
|
|
88
|
|
|
return $annotation instanceof ManyToOne |
89
|
|
|
|| |
90
|
|
|
$annotation instanceof OneToMany |
91
|
|
|
|| |
92
|
|
|
$annotation instanceof ManyToMany; |
93
|
|
|
}); |
94
|
|
|
|
95
|
|
|
/* |
96
|
|
|
* Se for encontrado alguma das anotações, iremos realizar o tratamento adequado para a anotação encontrada. |
|
|
|
|
97
|
|
|
*/ |
98
|
|
|
if ($ormMapping) { |
|
|
|
|
99
|
|
|
$ormMapping = $ormMapping[0]; |
100
|
|
|
|
101
|
|
|
$targetEntityName = $reflectionClass->getNamespaceName().'\\'.$ormMapping->targetEntity; |
|
|
|
|
102
|
|
|
$targetEntity = new $targetEntityName(); |
|
|
|
|
103
|
|
|
$repositoryTargetEntity = $targetEntity->getRepository(); |
|
|
|
|
104
|
|
|
|
105
|
|
|
/* |
106
|
|
|
* Se a propriedade estiver utilizando a anotação Doctrine\ORM\Mapping\ManyToOne e o usuário |
|
|
|
|
107
|
|
|
* informou um número, então buscamos o devido objeto pelo seu id. |
|
|
|
|
108
|
|
|
*/ |
109
|
|
|
if ($ormMapping instanceof ManyToOne && is_numeric($valueKey)) { |
|
|
|
|
110
|
|
|
$this->$methodSet( |
111
|
|
|
$repositoryTargetEntity->find($valueKey) |
112
|
|
|
); |
113
|
|
|
} elseif (($ormMapping instanceof OneToMany || $ormMapping instanceof ManyToMany) && is_array($valueKey)) { |
|
|
|
|
114
|
|
|
/** |
115
|
|
|
* Caso a propriedade esteja utilizando as anotações Doctrine\ORM\Mapping\OneToMany || Doctrine\ORM\Mapping\ManyToMany, |
|
|
|
|
116
|
|
|
* então o usuário terá que implementar o método addX?(). |
|
|
|
|
117
|
|
|
* Do contrário será lançada uma BadMethodCallException. |
|
|
|
|
118
|
|
|
*/ |
119
|
|
|
$methodAdd = 'add'.$ormMapping->targetEntity; |
120
|
|
|
if (!method_exists($this, $methodAdd)) { |
121
|
|
|
throw new \BadMethodCallException('Para utilizar Bludata\Doctrine\Common\Annotations\ToObject em '.get_called_class().'::$'.$key.' você precisar declarar o método '.get_called_class().'::'.$methodAdd.'()'); |
|
|
|
|
122
|
|
|
} |
123
|
|
|
|
124
|
|
|
if ( |
125
|
|
|
( |
126
|
|
|
$ormMapping instanceof OneToMany |
127
|
|
|
|| |
128
|
|
|
$ormMapping instanceof ManyToMany |
129
|
|
|
) |
130
|
|
|
&& is_array($valueKey) |
131
|
|
|
) { |
132
|
|
|
$this->$methodSet(new ArrayCollection()); |
133
|
|
|
|
134
|
|
|
foreach ($valueKey as $value) { |
135
|
|
|
$this->$methodAdd( |
136
|
|
|
$ormMapping instanceof OneToMany ? $repositoryTargetEntity->findOrCreate($value) : $repositoryTargetEntity->find($value) |
|
|
|
|
137
|
|
|
); |
138
|
|
|
} |
139
|
|
|
} |
140
|
|
|
} |
141
|
|
|
} |
142
|
|
|
} |
143
|
|
|
} |
144
|
|
|
} |
145
|
|
|
} |
146
|
|
|
|
147
|
|
|
return $this; |
148
|
|
|
} |
149
|
|
|
} |
150
|
|
|
|
Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.
You can also find more detailed suggestions in the “Code” section of your repository.