Failed Conditions
Pull Request — master (#7095)
by Benjamin
15:14
created

ClassMetadataFactory::doLoadMetadata()   C

Complexity

Conditions 14
Paths 105

Size

Total Lines 65
Code Lines 33

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 32
CRAP Score 14.0054

Importance

Changes 0
Metric Value
cc 14
eloc 33
nc 105
nop 3
dl 0
loc 65
ccs 32
cts 33
cp 0.9697
crap 14.0054
rs 5.8102
c 0
b 0
f 0

How to fix   Long Method    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
declare(strict_types=1);
4
5
namespace Doctrine\ORM\Mapping;
6
7
use Doctrine\Common\EventManager;
8
use Doctrine\DBAL\Platforms;
9
use Doctrine\DBAL\Platforms\AbstractPlatform;
10
use Doctrine\ORM\EntityManagerInterface;
11
use Doctrine\ORM\Event\LoadClassMetadataEventArgs;
12
use Doctrine\ORM\Event\OnClassMetadataNotFoundEventArgs;
13
use Doctrine\ORM\Events;
14
use Doctrine\ORM\ORMException;
15
use Doctrine\ORM\Sequencing;
16
use Doctrine\ORM\Sequencing\Planning\AssociationValueGeneratorExecutor;
17
use Doctrine\ORM\Sequencing\Planning\ColumnValueGeneratorExecutor;
18
use Doctrine\ORM\Sequencing\Planning\CompositeValueGenerationPlan;
19
use Doctrine\ORM\Sequencing\Planning\NoopValueGenerationPlan;
20
use Doctrine\ORM\Sequencing\Planning\SingleValueGenerationPlan;
21
use Doctrine\ORM\Sequencing\Planning\ValueGenerationExecutor;
22
use ReflectionException;
23
use function array_map;
24
use function class_exists;
25
use function count;
26
use function end;
27
use function explode;
28
use function is_subclass_of;
29
use function sprintf;
30
use function strpos;
31
use function strtolower;
32
use function var_export;
33
34
/**
35
 * The ClassMetadataFactory is used to create ClassMetadata objects that contain all the
36
 * metadata mapping information of a class which describes how a class should be mapped
37
 * to a relational database.
38
 */
39
class ClassMetadataFactory extends AbstractClassMetadataFactory
40
{
41
    /**
42
     * @var EntityManagerInterface|null
43
     */
44
    private $em;
45
46
    /**
47
     * @var AbstractPlatform
48
     */
49
    private $targetPlatform;
50
51
    /**
52
     * @var Driver\MappingDriver
53
     */
54
    private $driver;
55
56
    /**
57
     * @var EventManager
58
     */
59
    private $evm;
60
61
    /**
62
     * {@inheritdoc}
63
     */
64 378
    protected function loadMetadata(string $name, ClassMetadataBuildingContext $metadataBuildingContext) : array
65
    {
66 378
        $loaded = parent::loadMetadata($name, $metadataBuildingContext);
67
68 359
        array_map([$this, 'resolveDiscriminatorValue'], $loaded);
69
70 359
        return $loaded;
71
    }
72
73 2251
    public function setEntityManager(EntityManagerInterface $em)
74
    {
75 2251
        $this->em = $em;
76 2251
    }
77
78
    /**
79
     * {@inheritdoc}
80
     *
81
     * @throws ORMException
82
     */
83 444
    protected function initialize() : void
84
    {
85 444
        $this->driver      = $this->em->getConfiguration()->getMetadataDriverImpl();
0 ignored issues
show
Bug introduced by
The method getConfiguration() does not exist on null. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

85
        $this->driver      = $this->em->/** @scrutinizer ignore-call */ getConfiguration()->getMetadataDriverImpl();

This check looks for calls to methods that do not seem to exist on a given type. It looks for the method on the type itself as well as in inherited classes or implemented interfaces.

This is most likely a typographical error or the method has been renamed.

Loading history...
86 444
        $this->evm         = $this->em->getEventManager();
87 444
        $this->initialized = true;
88 444
    }
89
90
    /**
91
     * {@inheritdoc}
92
     */
93 12
    protected function onNotFoundMetadata(
94
        string $className,
95
        ClassMetadataBuildingContext $metadataBuildingContext
96
    ) : ?ClassMetadata {
97 12
        if (! $this->evm->hasListeners(Events::onClassMetadataNotFound)) {
98 10
            return null;
99
        }
100
101 2
        $eventArgs = new OnClassMetadataNotFoundEventArgs($className, $metadataBuildingContext, $this->em);
0 ignored issues
show
Bug introduced by
It seems like $this->em can also be of type null; however, parameter $entityManager of Doctrine\ORM\Event\OnCla...ventArgs::__construct() does only seem to accept Doctrine\ORM\EntityManagerInterface, maybe add an additional type check? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

101
        $eventArgs = new OnClassMetadataNotFoundEventArgs($className, $metadataBuildingContext, /** @scrutinizer ignore-type */ $this->em);
Loading history...
102
103 2
        $this->evm->dispatchEvent(Events::onClassMetadataNotFound, $eventArgs);
104
105 2
        return $eventArgs->getFoundMetadata();
106
    }
107
108
    /**
109
     * {@inheritdoc}
110
     *
111
     * @throws MappingException
112
     * @throws ORMException
113
     */
114 366
    protected function doLoadMetadata(
115
        string $className,
116
        ?ClassMetadata $parent,
117
        ClassMetadataBuildingContext $metadataBuildingContext
118
    ) : ClassMetadata {
119 366
        $classMetadata = new ClassMetadata($className, $metadataBuildingContext);
120
121 366
        if ($parent) {
122 98
            $classMetadata->setParent($parent);
123
124 98
            foreach ($parent->getDeclaredPropertiesIterator() as $fieldName => $property) {
125 97
                $classMetadata->addInheritedProperty($property);
126
            }
127
128 98
            $classMetadata->setInheritanceType($parent->inheritanceType);
0 ignored issues
show
Bug introduced by
$parent->inheritanceType of type string is incompatible with the type integer expected by parameter $type of Doctrine\ORM\Mapping\Cla...a::setInheritanceType(). ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

128
            $classMetadata->setInheritanceType(/** @scrutinizer ignore-type */ $parent->inheritanceType);
Loading history...
129 98
            $classMetadata->setIdentifier($parent->identifier);
130
131 98
            if ($parent->discriminatorColumn) {
132 72
                $classMetadata->setDiscriminatorColumn($parent->discriminatorColumn);
133 72
                $classMetadata->setDiscriminatorMap($parent->discriminatorMap);
134
            }
135
136 98
            $classMetadata->setLifecycleCallbacks($parent->lifecycleCallbacks);
137 98
            $classMetadata->setChangeTrackingPolicy($parent->changeTrackingPolicy);
138
139 98
            if ($parent->isMappedSuperclass) {
140 28
                $classMetadata->setCustomRepositoryClassName($parent->getCustomRepositoryClassName());
141
            }
142
        }
143
144
        // Invoke driver
145
        try {
146 366
            $this->driver->loadMetadataForClass($classMetadata->getClassName(), $classMetadata, $metadataBuildingContext);
147 3
        } catch (ReflectionException $e) {
148
            throw MappingException::reflectionFailure($classMetadata->getClassName(), $e);
149
        }
150
151 363
        $this->completeIdentifierGeneratorMappings($classMetadata);
152
153 363
        if ($parent) {
154 98
            if ($parent->getCache()) {
155 3
                $classMetadata->setCache(clone $parent->getCache());
156
            }
157
158 98
            if (! empty($parent->entityListeners) && empty($classMetadata->entityListeners)) {
159 7
                $classMetadata->entityListeners = $parent->entityListeners;
160
            }
161
        }
162
163 363
        if (! $classMetadata->discriminatorMap && $classMetadata->inheritanceType !== InheritanceType::NONE && $classMetadata->isRootEntity()) {
0 ignored issues
show
Bug Best Practice introduced by
The expression $classMetadata->discriminatorMap of type string[] is implicitly converted to a boolean; are you sure this is intended? If so, consider using empty($expr) instead to make it clear that you intend to check for an array without elements.

This check marks implicit conversions of arrays to boolean values in a comparison. While in PHP an empty array is considered to be equal (but not identical) to false, this is not always apparent.

Consider making the comparison explicit by using empty(..) or ! empty(...) instead.

Loading history...
164 1
            $this->addDefaultDiscriminatorMap($classMetadata);
165
        }
166
167 363
        $this->completeRuntimeMetadata($classMetadata, $parent);
168
169 363
        if ($this->evm->hasListeners(Events::loadClassMetadata)) {
170 6
            $eventArgs = new LoadClassMetadataEventArgs($classMetadata, $this->em);
0 ignored issues
show
Bug introduced by
It seems like $this->em can also be of type null; however, parameter $entityManager of Doctrine\ORM\Event\LoadC...ventArgs::__construct() does only seem to accept Doctrine\ORM\EntityManagerInterface, maybe add an additional type check? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

170
            $eventArgs = new LoadClassMetadataEventArgs($classMetadata, /** @scrutinizer ignore-type */ $this->em);
Loading history...
171
172 6
            $this->evm->dispatchEvent(Events::loadClassMetadata, $eventArgs);
173
        }
174
175 362
        $this->buildValueGenerationPlan($classMetadata);
176 362
        $this->validateRuntimeMetadata($classMetadata, $parent);
177
178 360
        return $classMetadata;
179
    }
180
181 363
    protected function completeRuntimeMetadata(ClassMetadata $class, ?ClassMetadata $parent = null) : void
182
    {
183 363
        if (! $parent || ! $parent->isMappedSuperclass) {
184 363
            return;
185
        }
186
187 28
        if ($class->isMappedSuperclass) {
188 1
            return;
189
        }
190
191 28
        $tableName = $class->getTableName();
192
193
        // Resolve column table names
194 28
        foreach ($class->getDeclaredPropertiesIterator() as $property) {
195 28
            if ($property instanceof FieldMetadata) {
196 28
                $property->setTableName($property->getTableName() ?? $tableName);
197
198 28
                continue;
199
            }
200
201 12
            if (! ($property instanceof ToOneAssociationMetadata)) {
202 12
                continue;
203
            }
204
205
            // Resolve association join column table names
206 9
            foreach ($property->getJoinColumns() as $joinColumn) {
207
                /** @var JoinColumnMetadata $joinColumn */
208 9
                $joinColumn->setTableName($joinColumn->getTableName() ?? $tableName);
209
            }
210
        }
211 28
    }
212
213
    /**
214
     * Validate runtime metadata is correctly defined.
215
     *
216
     * @throws MappingException
217
     */
218 362
    protected function validateRuntimeMetadata(ClassMetadata $class, ?ClassMetadata $parent = null) : void
219
    {
220 362
        if (! $class->getReflectionClass()) {
221
            // only validate if there is a reflection class instance
222
            return;
223
        }
224
225 362
        $class->validateIdentifier();
226 360
        $class->validateAssociations();
227 360
        $class->validateLifecycleCallbacks($this->getReflectionService());
228
229
        // verify inheritance
230 360
        if (! $class->isMappedSuperclass && $class->inheritanceType !== InheritanceType::NONE) {
231 75
            if (! $parent) {
232 74
                if (! $class->discriminatorMap) {
0 ignored issues
show
Bug Best Practice introduced by
The expression $class->discriminatorMap of type string[] is implicitly converted to a boolean; are you sure this is intended? If so, consider using empty($expr) instead to make it clear that you intend to check for an array without elements.

This check marks implicit conversions of arrays to boolean values in a comparison. While in PHP an empty array is considered to be equal (but not identical) to false, this is not always apparent.

Consider making the comparison explicit by using empty(..) or ! empty(...) instead.

Loading history...
233
                    throw MappingException::missingDiscriminatorMap($class->getClassName());
234
                }
235
236 74
                if (! $class->discriminatorColumn) {
237 75
                    throw MappingException::missingDiscriminatorColumn($class->getClassName());
238
                }
239
            }
240 324
        } elseif (($class->discriminatorMap || $class->discriminatorColumn) && $class->isMappedSuperclass && $class->isRootEntity()) {
0 ignored issues
show
Bug Best Practice introduced by
The expression $class->discriminatorMap of type string[] is implicitly converted to a boolean; are you sure this is intended? If so, consider using ! empty($expr) instead to make it clear that you intend to check for an array without elements.

This check marks implicit conversions of arrays to boolean values in a comparison. While in PHP an empty array is considered to be equal (but not identical) to false, this is not always apparent.

Consider making the comparison explicit by using empty(..) or ! empty(...) instead.

Loading history...
241
            // second condition is necessary for mapped superclasses in the middle of an inheritance hierarchy
242
            throw MappingException::noInheritanceOnMappedSuperClass($class->getClassName());
243
        }
244 360
    }
245
246
    /**
247
     * {@inheritdoc}
248
     */
249 1950
    protected function newClassMetadataBuildingContext() : ClassMetadataBuildingContext
250
    {
251 1950
        return new ClassMetadataBuildingContext(
252 1950
            $this,
253 1950
            $this->getReflectionService(),
254 1950
            $this->em->getConfiguration()->getNamingStrategy()
255
        );
256
    }
257
258
    /**
259
     * Populates the discriminator value of the given metadata (if not set) by iterating over discriminator
260
     * map classes and looking for a fitting one.
261
     *
262
     * @throws \InvalidArgumentException
263
     * @throws \ReflectionException
264
     * @throws MappingException
265
     */
266 359
    private function resolveDiscriminatorValue(ClassMetadata $metadata) : void
267
    {
268 359
        if ($metadata->discriminatorValue || ! $metadata->discriminatorMap || $metadata->isMappedSuperclass ||
0 ignored issues
show
Bug Best Practice introduced by
The expression $metadata->discriminatorMap of type string[] is implicitly converted to a boolean; are you sure this is intended? If so, consider using empty($expr) instead to make it clear that you intend to check for an array without elements.

This check marks implicit conversions of arrays to boolean values in a comparison. While in PHP an empty array is considered to be equal (but not identical) to false, this is not always apparent.

Consider making the comparison explicit by using empty(..) or ! empty(...) instead.

Loading history...
269 359
            ! $metadata->getReflectionClass() || $metadata->getReflectionClass()->isAbstract()) {
270 359
            return;
271
        }
272
273
        // minor optimization: avoid loading related metadata when not needed
274 4
        foreach ($metadata->discriminatorMap as $discriminatorValue => $discriminatorClass) {
275 4
            if ($discriminatorClass === $metadata->getClassName()) {
276 3
                $metadata->discriminatorValue = $discriminatorValue;
277
278 4
                return;
279
            }
280
        }
281
282
        // iterate over discriminator mappings and resolve actual referenced classes according to existing metadata
283 1
        foreach ($metadata->discriminatorMap as $discriminatorValue => $discriminatorClass) {
284 1
            if ($metadata->getClassName() === $this->getMetadataFor($discriminatorClass)->getClassName()) {
285
                $metadata->discriminatorValue = $discriminatorValue;
286
287 1
                return;
288
            }
289
        }
290
291 1
        throw MappingException::mappedClassNotPartOfDiscriminatorMap($metadata->getClassName(), $metadata->getRootClassName());
292
    }
293
294
    /**
295
     * Adds a default discriminator map if no one is given
296
     *
297
     * If an entity is of any inheritance type and does not contain a
298
     * discriminator map, then the map is generated automatically. This process
299
     * is expensive computation wise.
300
     *
301
     * The automatically generated discriminator map contains the lowercase short name of
302
     * each class as key.
303
     *
304
     * @throws MappingException
305
     */
306 1
    private function addDefaultDiscriminatorMap(ClassMetadata $class) : void
307
    {
308 1
        $allClasses = $this->driver->getAllClassNames();
309 1
        $fqcn       = $class->getClassName();
310 1
        $map        = [$this->getShortName($fqcn) => $fqcn];
311 1
        $duplicates = [];
312
313 1
        foreach ($allClasses as $subClassCandidate) {
314 1
            if (is_subclass_of($subClassCandidate, $fqcn)) {
315 1
                $shortName = $this->getShortName($subClassCandidate);
316
317 1
                if (isset($map[$shortName])) {
318
                    $duplicates[] = $shortName;
319
                }
320
321 1
                $map[$shortName] = $subClassCandidate;
322
            }
323
        }
324
325 1
        if ($duplicates) {
326
            throw MappingException::duplicateDiscriminatorEntry($class->getClassName(), $duplicates, $map);
327
        }
328
329 1
        $class->setDiscriminatorMap($map);
330 1
    }
331
332
    /**
333
     * Gets the lower-case short name of a class.
334
     *
335
     * @param string $className
336
     */
337 1
    private function getShortName($className) : string
338
    {
339 1
        if (strpos($className, '\\') === false) {
340
            return strtolower($className);
341
        }
342
343 1
        $parts = explode('\\', $className);
344
345 1
        return strtolower(end($parts));
346
    }
347
348
    /**
349
     * Completes the ID generator mapping. If "auto" is specified we choose the generator
350
     * most appropriate for the targeted database platform.
351
     *
352
     * @throws ORMException
353
     */
354 363
    private function completeIdentifierGeneratorMappings(ClassMetadata $class) : void
355
    {
356 363
        foreach ($class->getDeclaredPropertiesIterator() as $property) {
357 361
            if (! $property instanceof FieldMetadata /*&& ! $property instanceof AssocationMetadata*/) {
0 ignored issues
show
Unused Code Comprehensibility introduced by
45% of this comment could be valid code. Did you maybe forget this after debugging?

Sometimes obsolete code just ends up commented out instead of removed. In this case it is better to remove the code once you have checked you do not need it.

The code might also have been commented out for debugging purposes. In this case it is vital that someone uncomments it again or your project may behave in very unexpected ways in production.

This check looks for comments that seem to be mostly valid code and reports them.

Loading history...
358 250
                continue;
359
            }
360
361 359
            $this->completeFieldIdentifierGeneratorMapping($property);
362
        }
363 363
    }
364
365 359
    private function completeFieldIdentifierGeneratorMapping(FieldMetadata $field)
366
    {
367 359
        if (! $field->hasValueGenerator()) {
368 279
            return;
369
        }
370
371 288
        $platform  = $this->getTargetPlatform();
372 288
        $class     = $field->getDeclaringClass();
0 ignored issues
show
Unused Code introduced by
The assignment to $class is dead and can be removed.
Loading history...
373 288
        $generator = $field->getValueGenerator();
374
375 288
        if ($generator->getType() === GeneratorType::AUTO) {
376 278
            $generator = new ValueGeneratorMetadata(
377 278
                $platform->prefersSequences()
378
                    ? GeneratorType::SEQUENCE
379 278
                    : ($platform->prefersIdentityColumns()
380 278
                        ? GeneratorType::IDENTITY
381 278
                        : GeneratorType::TABLE
382
                ),
383 278
                $field->getValueGenerator()->getDefinition()
384
            );
385 278
            $field->setValueGenerator($generator);
386
        }
387
388
        // Validate generator definition and set defaults where needed
389 288
        switch ($generator->getType()) {
390 288
            case GeneratorType::SEQUENCE:
391
                // If there is no sequence definition yet, create a default definition
392 6
                if ($generator->getDefinition()) {
393 6
                    break;
394
                }
395
396
                // @todo guilhermeblanco Move sequence generation to DBAL
397
                $sequencePrefix = $platform->getSequencePrefix($field->getTableName(), $field->getSchemaName());
0 ignored issues
show
Bug introduced by
The method getSchemaName() does not exist on Doctrine\ORM\Mapping\FieldMetadata. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

397
                $sequencePrefix = $platform->getSequencePrefix($field->getTableName(), $field->/** @scrutinizer ignore-call */ getSchemaName());

This check looks for calls to methods that do not seem to exist on a given type. It looks for the method on the type itself as well as in inherited classes or implemented interfaces.

This is most likely a typographical error or the method has been renamed.

Loading history...
398
                $idSequenceName = sprintf('%s_%s_seq', $sequencePrefix, $field->getColumnName());
399
                $sequenceName   = $platform->fixSchemaElementName($idSequenceName);
400
401
                $field->setValueGenerator(
402
                    new ValueGeneratorMetadata(
403
                        $generator->getType(),
404
                        [
405
                            'sequenceName'   => $sequenceName,
406
                            'allocationSize' => 1,
407
                        ]
408
                    )
409
                );
410
411
                break;
412
413 282
            case GeneratorType::TABLE:
414
                throw new ORMException('TableGenerator not yet implemented.');
415
                break;
416
417 282
            case GeneratorType::CUSTOM:
418 1
                $definition = $generator->getDefinition();
419 1
                if (! isset($definition['class'])) {
420
                    throw new ORMException(sprintf('Cannot instantiate custom generator, no class has been defined'));
421
                }
422 1
                if (! class_exists($definition['class'])) {
423
                    throw new ORMException(sprintf('Cannot instantiate custom generator : %s', var_export($definition, true))); //$definition['class']));
0 ignored issues
show
Unused Code Comprehensibility introduced by
100% of this comment could be valid code. Did you maybe forget this after debugging?

Sometimes obsolete code just ends up commented out instead of removed. In this case it is better to remove the code once you have checked you do not need it.

The code might also have been commented out for debugging purposes. In this case it is vital that someone uncomments it again or your project may behave in very unexpected ways in production.

This check looks for comments that seem to be mostly valid code and reports them.

Loading history...
424
                }
425
426 1
                break;
427
428 281
            case GeneratorType::IDENTITY:
429
            case GeneratorType::NONE:
430
            case GeneratorType::UUID:
431 281
                break;
432
433
            default:
434
                throw new ORMException('Unknown generator type: ' . $generator->getType());
435
        }
436 288
    }
437
438
    /**
439
     * {@inheritDoc}
440
     */
441 198
    protected function getDriver() : Driver\MappingDriver
442
    {
443 198
        return $this->driver;
444
    }
445
446
    /**
447
     * {@inheritDoc}
448
     */
449
    protected function isEntity(ClassMetadata $class) : bool
450
    {
451
        return isset($class->isMappedSuperclass) && $class->isMappedSuperclass === false;
452
    }
453
454 288
    private function getTargetPlatform() : Platforms\AbstractPlatform
455
    {
456 288
        if (! $this->targetPlatform) {
457 288
            $this->targetPlatform = $this->em->getConnection()->getDatabasePlatform();
458
        }
459
460 288
        return $this->targetPlatform;
461
    }
462
463 362
    private function buildValueGenerationPlan(ClassMetadata $class) : void
464
    {
465 362
        $executors = $this->buildValueGenerationExecutorList($class);
466
467 362
        switch (count($executors)) {
468 362
            case 0:
469 90
                $class->setValueGenerationPlan(new NoopValueGenerationPlan());
470 90
                break;
471
472 302
            case 1:
473 297
                $class->setValueGenerationPlan(new SingleValueGenerationPlan($class, $executors[0]));
474 297
                break;
475
476
            default:
477 17
                $class->setValueGenerationPlan(new CompositeValueGenerationPlan($class, $executors));
478 17
                break;
479
        }
480 362
    }
481
482
    /**
483
     * @return ValueGenerationExecutor[]
484
     */
485 362
    private function buildValueGenerationExecutorList(ClassMetadata $class) : array
486
    {
487 362
        $executors = [];
488
489 362
        foreach ($class->getDeclaredPropertiesIterator() as $property) {
490 360
            $executor = $this->buildValueGenerationExecutorForProperty($class, $property);
491
492 360
            if ($executor instanceof ValueGenerationExecutor) {
493 360
                $executors[] = $executor;
494
            }
495
        }
496
497 362
        return $executors;
498
    }
499
500 360
    private function buildValueGenerationExecutorForProperty(
501
        ClassMetadata $class,
502
        Property $property
503
    ) : ?ValueGenerationExecutor {
504 360
        if ($property instanceof LocalColumnMetadata && $property->hasValueGenerator()) {
505 287
            return new ColumnValueGeneratorExecutor($property, $this->createPropertyValueGenerator($class, $property));
506
        }
507
508 330
        if ($property instanceof ToOneAssociationMetadata && $property->isPrimaryKey()) {
509 40
            return new AssociationValueGeneratorExecutor();
510
        }
511
512 326
        return null;
513
    }
514
515 287
    private function createPropertyValueGenerator(
516
        ClassMetadata $class,
517
        LocalColumnMetadata $property
518
    ) : Sequencing\Generator {
519 287
        $platform = $this->getTargetPlatform();
520
521 287
        switch ($property->getValueGenerator()->getType()) {
522 287
            case GeneratorType::IDENTITY:
523 280
                $sequenceName = null;
524
525
                // Platforms that do not have native IDENTITY support need a sequence to emulate this behaviour.
526 280
                if ($platform->usesSequenceEmulatedIdentityColumns()) {
527
                    $sequencePrefix = $platform->getSequencePrefix($class->getTableName(), $class->getSchemaName());
528
                    $idSequenceName = $platform->getIdentitySequenceName($sequencePrefix, $property->getColumnName());
529
                    $sequenceName   = $platform->quoteIdentifier($platform->fixSchemaElementName($idSequenceName));
530
                }
531
532 280
                return $property->getTypeName() === 'bigint'
533 1
                    ? new Sequencing\BigIntegerIdentityGenerator($sequenceName)
534 280
                    : new Sequencing\IdentityGenerator($sequenceName);
535
536 7
            case GeneratorType::SEQUENCE:
537 6
                $definition = $property->getValueGenerator()->getDefinition();
538 6
                return new Sequencing\SequenceGenerator(
539 6
                    $platform->quoteIdentifier($definition['sequenceName']),
540 6
                    $definition['allocationSize']
541
                );
542
                break;
0 ignored issues
show
Unused Code introduced by
break is not strictly necessary here and could be removed.

The break statement is not necessary if it is preceded for example by a return statement:

switch ($x) {
    case 1:
        return 'foo';
        break; // This break is not necessary and can be left off.
}

If you would like to keep this construct to be consistent with other case statements, you can safely mark this issue as a false-positive.

Loading history...
543
544 1
            case GeneratorType::UUID:
545
                return new Sequencing\UuidGenerator();
546
                break;
547
548 1
            case GeneratorType::CUSTOM:
549 1
                $class = $property->getValueGenerator()->getDefinition()['class'];
550 1
                return new $class();
551
                break;
552
        }
553
    }
554
}
555