These results are based on our legacy PHP analysis, consider migrating to our new PHP analysis engine instead. Learn more
1 | <?php |
||
2 | |||
3 | declare(strict_types=1); |
||
4 | |||
5 | /* |
||
6 | * This file is part of the Sonata Project package. |
||
7 | * |
||
8 | * (c) Thomas Rabaix <[email protected]> |
||
9 | * |
||
10 | * For the full copyright and license information, please view the LICENSE |
||
11 | * file that was distributed with this source code. |
||
12 | */ |
||
13 | |||
14 | namespace Sonata\AdminBundle\Form\DataTransformer; |
||
15 | |||
16 | use Doctrine\Common\Util\ClassUtils; |
||
17 | use Sonata\AdminBundle\Model\ModelManagerInterface; |
||
18 | use Symfony\Component\Form\DataTransformerInterface; |
||
19 | |||
20 | /** |
||
21 | * Transform object to ID and property label. |
||
22 | * |
||
23 | * @author Andrej Hudec <[email protected]> |
||
24 | */ |
||
25 | class ModelToIdPropertyTransformer implements DataTransformerInterface |
||
26 | { |
||
27 | /** |
||
28 | * @var ModelManagerInterface |
||
29 | */ |
||
30 | protected $modelManager; |
||
31 | |||
32 | /** |
||
33 | * @var string |
||
34 | */ |
||
35 | protected $className; |
||
36 | |||
37 | /** |
||
38 | * @var string |
||
39 | */ |
||
40 | protected $property; |
||
41 | |||
42 | /** |
||
43 | * @var bool |
||
44 | */ |
||
45 | protected $multiple; |
||
46 | |||
47 | /** |
||
48 | * @var callable|null |
||
49 | */ |
||
50 | protected $toStringCallback; |
||
51 | |||
52 | /** |
||
53 | * @param string $className |
||
54 | * @param string $property |
||
55 | * @param bool $multiple |
||
56 | * @param callable|null $toStringCallback |
||
57 | */ |
||
58 | public function __construct( |
||
59 | ModelManagerInterface $modelManager, |
||
60 | $className, |
||
61 | $property, |
||
62 | $multiple = false, |
||
63 | $toStringCallback = null |
||
64 | ) { |
||
65 | $this->modelManager = $modelManager; |
||
66 | $this->className = $className; |
||
67 | $this->property = $property; |
||
68 | $this->multiple = $multiple; |
||
69 | $this->toStringCallback = $toStringCallback; |
||
70 | } |
||
71 | |||
72 | public function reverseTransform($value) |
||
73 | { |
||
74 | $collection = $this->modelManager->getModelCollectionInstance($this->className); |
||
75 | |||
76 | if (empty($value)) { |
||
77 | if ($this->multiple) { |
||
78 | return $collection; |
||
79 | } |
||
80 | |||
81 | return; |
||
82 | } |
||
83 | |||
84 | if (!$this->multiple) { |
||
85 | return $this->modelManager->find($this->className, $value); |
||
86 | } |
||
87 | |||
88 | if (!\is_array($value)) { |
||
89 | throw new \UnexpectedValueException(sprintf('Value should be array, %s given.', \gettype($value))); |
||
90 | } |
||
91 | |||
92 | foreach ($value as $key => $id) { |
||
93 | if ('_labels' === $key) { |
||
94 | continue; |
||
95 | } |
||
96 | |||
97 | $collection[] = $this->modelManager->find($this->className, $id); |
||
98 | } |
||
99 | |||
100 | return $collection; |
||
101 | } |
||
102 | |||
103 | public function transform($entityOrCollection) |
||
104 | { |
||
105 | $result = []; |
||
106 | |||
107 | if (!$entityOrCollection) { |
||
108 | return $result; |
||
109 | } |
||
110 | |||
111 | if ($this->multiple) { |
||
112 | $isArray = \is_array($entityOrCollection); |
||
113 | if (!$isArray && substr(\get_class($entityOrCollection), -1 * \strlen($this->className)) === $this->className) { |
||
114 | throw new \InvalidArgumentException('A multiple selection must be passed a collection not a single value. Make sure that form option "multiple=false" is set for many-to-one relation and "multiple=true" is set for many-to-many or one-to-many relations.'); |
||
115 | } elseif ($isArray || ($entityOrCollection instanceof \ArrayAccess)) { |
||
116 | $collection = $entityOrCollection; |
||
117 | } else { |
||
118 | throw new \InvalidArgumentException('A multiple selection must be passed a collection not a single value. Make sure that form option "multiple=false" is set for many-to-one relation and "multiple=true" is set for many-to-many or one-to-many relations.'); |
||
119 | } |
||
120 | } else { |
||
121 | if (substr(\get_class($entityOrCollection), -1 * \strlen($this->className)) === $this->className) { |
||
122 | $collection = [$entityOrCollection]; |
||
123 | } elseif ($entityOrCollection instanceof \ArrayAccess) { |
||
124 | throw new \InvalidArgumentException('A single selection must be passed a single value not a collection. Make sure that form option "multiple=false" is set for many-to-one relation and "multiple=true" is set for many-to-many or one-to-many relations.'); |
||
125 | } else { |
||
126 | $collection = [$entityOrCollection]; |
||
127 | } |
||
128 | } |
||
129 | |||
130 | if (empty($this->property)) { |
||
131 | throw new \RuntimeException('Please define "property" parameter.'); |
||
132 | } |
||
133 | |||
134 | foreach ($collection as $entity) { |
||
135 | $id = current($this->modelManager->getIdentifierValues($entity)); |
||
136 | |||
137 | if (null !== $this->toStringCallback) { |
||
138 | if (!\is_callable($this->toStringCallback)) { |
||
139 | throw new \RuntimeException('Callback in "to_string_callback" option doesn`t contain callable function.'); |
||
140 | } |
||
141 | |||
142 | $label = \call_user_func($this->toStringCallback, $entity, $this->property); |
||
143 | } else { |
||
144 | try { |
||
145 | $label = (string) $entity; |
||
146 | } catch (\Exception $e) { |
||
0 ignored issues
–
show
|
|||
147 | throw new \RuntimeException(sprintf("Unable to convert the entity %s to String, entity must have a '__toString()' method defined", ClassUtils::getClass($entity)), 0, $e); |
||
148 | } |
||
149 | } |
||
150 | |||
151 | $result[] = $id; |
||
152 | $result['_labels'][] = $label; |
||
153 | } |
||
154 | |||
155 | return $result; |
||
156 | } |
||
157 | } |
||
158 |
This check looks for unreachable code. It uses sophisticated control flow analysis techniques to find statements which will never be executed.
Unreachable code is most often the result of
return
,die
orexit
statements that have been added for debug purposes.In the above example, the last
return false
will never be executed, because a return statement has already been met in every possible execution path.