@param ClassMetadata $class

@throws InvalidArgumentException
163771
private function verifyClassCanBeProxied(ClassMetadata $class)
    {
        if ($class->getReflectionClass()->isFinal()) {
            throw InvalidArgumentException::classMustNotBeFinal($class->getName());
        }

        if ($class->getReflectionClass()->isAbstract()) {
            throw InvalidArgumentException::classMustNotBeAbstract($class->getName());
        }
    }
946403
private function executeDeletions(ClassMetadata $class, array $options = array())
    {
        $hasPostRemoveLifecycleCallbacks = ! empty($class->lifecycleCallbacks[Events::postRemove]);
        $hasPostRemoveListeners = $this->evm->hasListeners(Events::postRemove);

        $className = $class->name;
        $persister = $this->getDocumentPersister($className);
        $collection = $this->dm->getDocumentCollection($className);
        foreach ($this->documentDeletions as $oid => $document) {
            if (get_class($document) == $className || $document instanceof Proxy && $document instanceof $className) {
                if ( ! $class->isEmbeddedDocument) {
                    $persister->delete($document, $options);
                }
                unset(
                    $this->documentDeletions[$oid],
                    $this->documentIdentifiers[$oid],
                    $this->originalDocumentData[$oid]
                );

                // Clear snapshot information for any referenced PersistentCollection
                // http://www.doctrine-project.org/jira/browse/MODM-95
                foreach ($class->fieldMappings as $fieldMapping) {
                    if (isset($fieldMapping['type']) && $fieldMapping['type'] === 'many') {
                        $value = $class->reflFields[$fieldMapping['fieldName']]->getValue($document);
                        if ($value instanceof PersistentCollection) {
                            $value->clearSnapshot();
                        }
                    }
                }

                // Document with this $oid after deletion treated as NEW, even if the $oid
                // is obtained by a new document because the old one went out of scope.
                $this->documentStates[$oid] = self::STATE_NEW;

                if ($hasPostRemoveLifecycleCallbacks) {
                    $class->invokeLifecycleCallbacks(Events::postRemove, $document);
                }
                if ($hasPostRemoveListeners) {
                    $this->evm->dispatchEvent(Events::postRemove, new LifecycleEventArgs($document, $this->dm));
                }
                $this->cascadePostRemove($class, $document);
            }
        }
    }
479246
public function setIteratorClass($class)
    {
        if (class_exists($class)) {
            $this->iteratorClass = $class;

            return ;
        }

        if (strpos($class, '\\') === 0) {
            $class = '\\' . $class;
            if (class_exists($class)) {
                $this->iteratorClass = $class;

                return ;
            }
        }

        throw new Exception\InvalidArgumentException('The iterator class does not exist');
    }
498604
protected function doLoadMetadata($class, $parent, $rootEntityFound, array $nonSuperclassParents = [])
    {
        /** @var $class ClassMetadata */
        /** @var $parent ClassMetadata */
        if ($parent) {
            $this->addInheritedIndexes($class, $parent);
            $this->addInheritedAttributes($class, $parent);

            $class->setInheritanceType($parent->inheritanceType);
            $class->setDiscriminatorAttribute($parent->discriminatorAttribute);
            $class->setDiscriminatorMap($parent->discriminatorMap);
            $class->setDiscriminatorDefaultValue($parent->discriminatorDefaultValue);
            $class->setVersioned($parent->isVersioned);
            $class->setVersionAttribute($parent->versionAttribute);
            $class->setLifecycleCallbacks($parent->lifecycleCallbacks);
            $class->setAlsoLoadMethods($parent->alsoLoadMethods);
            $class->setChangeTrackingPolicy($parent->changeTrackingPolicy);

            if ($parent->isMappedSuperclass) {
                $class->setCustomRepositoryClass($parent->customRepositoryClassName);
            }
        }

        // Invoke driver
        try {
            $this->driver->loadMetadataForClass($class->getName(), $class);
        } catch (\ReflectionException $e) {
            throw MappingException::reflectionFailure($class->getName(), $e);
        }

        if (!$class->getIndex() && !$class->isMappedSuperclass && !$class->isEmbeddedDocument) {
            throw MappingException::hashKeyRequired($class->name);
        }

        $class->setParentClassNames($nonSuperclassParents);

        if ($parent) {
            if ($parent->isInheritanceTypeSingleTable()) {
                $class->setTable($parent->getTableName());
                $class->setRequireIndexes($parent->requireIndexes);
            } elseif ($class->requireIndexes === null) {
                $class->setRequireIndexes($parent->requireIndexes);
            }
        }

        if ($this->evm->hasListeners(Event::loadClassMetadata)) {
            $eventArgs = new LoadClassMetadataEventArgs($class, $this->dm);
            $this->evm->dispatchEvent(Event::loadClassMetadata, $eventArgs);
        }
    }
322020
private function executeUpserts(ClassMetadata $class, array $documents)
    {
        $persister = $this->getDocumentPersister($class->name);

        foreach ($documents as $oid => $document) {
            try {
                $persister->upsert($document);
                $persister->handleCollections($document);

                unset($this->documentUpserts[$oid]);
            } catch (\Aws\DynamoDb\Exception\DynamoDbException $e) {
                unset($this->documentUpserts[$oid]);

                throw $e;
            }

            $this->lifecycleEventManager->postPersist($class, $document);
        }
    }
584462
protected function validateRuntimeMetadata(ClassMetadata $class, ?ClassMetadata $parent = null) : void
    {
        if (! $class->getReflectionClass()) {
            // only validate if there is a reflection class instance
            return;
        }

        $class->validateIdentifier();
        $class->validateAssociations();
        $class->validateLifecycleCallbacks($this->getReflectionService());

        // verify inheritance
        if (! $class->isMappedSuperclass && $class->inheritanceType !== InheritanceType::NONE) {
            if (! $parent) {
                if (! $class->discriminatorMap) {
                    throw MappingException::missingDiscriminatorMap($class->getClassName());
                }

                if (! $class->discriminatorColumn) {
                    throw MappingException::missingDiscriminatorColumn($class->getClassName());
                }
            }
        } elseif (($class->discriminatorMap || $class->discriminatorColumn) && $class->isMappedSuperclass && $class->isRootEntity()) {
            // second condition is necessary for mapped superclasses in the middle of an inheritance hierarchy
            throw MappingException::noInheritanceOnMappedSuperClass($class->getClassName());
        }
    }
1243109
public function preUpdate(ClassMetadata $class, object $document) : void
    {
        if (! empty($class->lifecycleCallbacks[Events::preUpdate])) {
            $class->invokeLifecycleCallbacks(Events::preUpdate, $document, [new PreUpdateEventArgs($document, $this->dm, $this->uow->getDocumentChangeSet($document))]);
            $this->uow->recomputeSingleDocumentChangeSet($class, $document);
        }
        $this->evm->dispatchEvent(Events::preUpdate, new PreUpdateEventArgs($document, $this->dm, $this->uow->getDocumentChangeSet($document)));
        $this->cascadePreUpdate($class, $document);
    }
313891
private function __setCallback($type, $class, array $args)
    {
        if (!is_array($class)) {
            $this->{$type} = [
                [
                    'class' => $class,
                    'args' => $args
                ]
            ];

            return $this;
        } elseif (is_array($class) && count($class) == 2) {
            $className = $class[0];
            $methodName = $class[1];
        } else {
            if (is_array($class)) {
                $class = implode($class);
            }
            throw new \InvalidArgumentException("{$class} is missformated");
        }

        $this->{$type} = [
            [
                'class' => [$className, $methodName],
                'args' => $args
            ]
        ];

        return $this;
    }
1031739
public static function set_class_for_file_extension($exts, $class)
    {
        if (!is_array($exts)) {
            $exts = array($exts);
        }
        foreach ($exts as $ext) {
            if (!is_subclass_of($class, File::class)) {
                throw new InvalidArgumentException(
                    sprintf('Class "%s" (for extension "%s") is not a valid subclass of File', $class, $ext)
                );
            }
            self::config()->merge('class_for_file_extension', [$ext => $class]);
        }
    }
495989
public function scheduleForUpsert(ClassMetadata $class, object $document) : void
    {
        $oid = spl_object_hash($document);

        if ($class->isEmbeddedDocument) {
            throw new InvalidArgumentException('Embedded document can not be scheduled for upsert.');
        }
        if (isset($this->documentUpdates[$oid])) {
            throw new InvalidArgumentException('Dirty document can not be scheduled for upsert.');
        }
        if (isset($this->documentDeletions[$oid])) {
            throw new InvalidArgumentException('Removed document can not be scheduled for upsert.');
        }
        if (isset($this->documentUpserts[$oid])) {
            throw new InvalidArgumentException('Document can not be scheduled for upsert twice.');
        }

        $this->documentUpserts[$oid]     = $document;
        $this->documentIdentifiers[$oid] = $class->getIdentifierValue($document);
        $this->addToIdentityMap($document);
    }
384646
protected function validate(PropertyMetadata $metadata, string $name, & $value)
	{
		if (!$metadata->isValid($value)) {
			$class = get_class($this);
			throw new InvalidArgumentException("Value for {$class}::\${$name} property is invalid.");
		}
	}
1368415
private function validateFieldCriteria(ClassMetadata $class, $fieldName): void
    {
        if (!$class->hasField($fieldName) && !$class->hasAssociation($fieldName)) {
            throw new ConstraintDefinitionException(sprintf("The field '%s' is not mapped by Doctrine, so it cannot be validated for uniqueness.", $fieldName));
        }
    }
476990
private function parseClassMetadata($class)
    {
        $metadata = new ClassMetadata($class);

        //Load up parent and interfaces
        $this->loadParentMetadata($metadata);
        $this->loadInterfaceMetadata($metadata);

        //Load Annotations from Reader
        $this->loader->loadClassMetadata($metadata);

        //Store internally
        $this->setParsedClass($class, $metadata);

        if ($this->cache !== null) {
            $this->cache->save($class, $metadata);
        }

        return $metadata;
    }
674460
public function loadMetadataForClass($className, ClassMetadata $metadata)
    {
        /**
         * This is the actual type we have at this point, but we cannot change the
         * signature due to inheritance.
         *
         * @var ORM\ClassMetadata $metadata
         */

        try {
            $class = $metadata->getReflectionClass();
            $classSchema = $this->getClassSchema($class->getName());
            $classAnnotations = $this->reader->getClassAnnotations($class);
        } catch (ClassSchemaNotFoundException $exception) {
            throw new ORM\MappingException(sprintf('Failure while fetching class schema class "%s": %s', $metadata->getName(), $exception->getMessage()), 1542792708, $exception);
        }

        // Evaluate Entity annotation
        if (isset($classAnnotations[ORM\MappedSuperclass::class])) {
            $mappedSuperclassAnnotation = $classAnnotations[ORM\MappedSuperclass::class];
            if ($mappedSuperclassAnnotation->repositoryClass !== null) {
                $metadata->setCustomRepositoryClass($mappedSuperclassAnnotation->repositoryClass);
            }
            $metadata->isMappedSuperclass = true;
        } elseif (isset($classAnnotations[Flow\Entity::class]) || isset($classAnnotations[ORM\Entity::class])) {
            $entityAnnotation = isset($classAnnotations[Flow\Entity::class]) ? $classAnnotations[Flow\Entity::class] : $classAnnotations[ORM\Entity::class];
            if ($entityAnnotation->repositoryClass !== null) {
                $metadata->setCustomRepositoryClass($entityAnnotation->repositoryClass);
            } elseif ($classSchema->getRepositoryClassName() !== null) {
                if ($this->reflectionService->isClassImplementationOf($classSchema->getRepositoryClassName(), \Doctrine\ORM\EntityRepository::class)) {
                    $metadata->setCustomRepositoryClass($classSchema->getRepositoryClassName());
                }
            }
            if ($entityAnnotation->readOnly) {
                $metadata->markReadOnly();
            }
        } elseif (isset($classAnnotations[Flow\ValueObject::class])) {
            $valueObjectAnnotation = $classAnnotations[Flow\ValueObject::class];
            if ($valueObjectAnnotation->embedded === true) {
                $metadata->isEmbeddedClass = true;
            } else {
                // also ok... but we make it read-only
                $metadata->markReadOnly();
            }
        } elseif (isset($classAnnotations[ORM\Embeddable::class])) {
            $metadata->isEmbeddedClass = true;
        } else {
            throw ORM\MappingException::classIsNotAValidEntityOrMappedSuperClass($className);
        }

        // Evaluate Table annotation
        $primaryTable = [];
        if (isset($classAnnotations[ORM\Table::class])) {
            $tableAnnotation = $classAnnotations[ORM\Table::class];
            $primaryTable = [
                'name' => $tableAnnotation->name,
                'schema' => $tableAnnotation->schema
            ];

            if ($tableAnnotation->indexes !== null) {
                foreach ($tableAnnotation->indexes as $indexAnnotation) {
                    $index = ['columns' => $indexAnnotation->columns];
                    if (!empty($indexAnnotation->flags)) {
                        $index['flags'] = $indexAnnotation->flags;
                    }
                    if (!empty($indexAnnotation->options)) {
                        $index['options'] = $indexAnnotation->options;
                    }
                    if (!empty($indexAnnotation->name)) {
                        $primaryTable['indexes'][$indexAnnotation->name] = $index;
                    } else {
                        $primaryTable['indexes'][] = $index;
                    }
                }
            }

            if ($tableAnnotation->uniqueConstraints !== null) {
                foreach ($tableAnnotation->uniqueConstraints as $uniqueConstraint) {
                    $uniqueConstraint = ['columns' => $uniqueConstraint->columns];
                    if (!empty($uniqueConstraint->options)) {
                        $uniqueConstraint['options'] = $uniqueConstraint->options;
                    }
                    if (!empty($uniqueConstraint->name)) {
                        $primaryTable['uniqueConstraints'][$uniqueConstraint->name] = $uniqueConstraint;
                    } else {
                        $primaryTable['uniqueConstraints'][] = $uniqueConstraint;
                    }
                }
            }

            if ($tableAnnotation->options !== null) {
                $primaryTable['options'] = $tableAnnotation->options;
            }
        }
        if (!isset($classAnnotations[ORM\Embeddable::class])
            && !isset($primaryTable['name'])) {
            $className = $classSchema->getClassName();
            $primaryTable['name'] = $this->inferTableNameFromClassName($className);
        }

        // Evaluate @Cache annotation
        if (isset($classAnnotations[ORM\Cache::class])) {
            $cacheAnnotation = $classAnnotations[ORM\Cache::class];
            $cacheMap   = [
                'region' => $cacheAnnotation->region,
                'usage'  => constant('Doctrine\ORM\Mapping\ClassMetadata::CACHE_USAGE_' . $cacheAnnotation->usage),
            ];

            $metadata->enableCache($cacheMap);
        }

        // Evaluate NamedNativeQueries annotation
        if (isset($classAnnotations[ORM\NamedNativeQueries::class])) {
            $namedNativeQueriesAnnotation = $classAnnotations[ORM\NamedNativeQueries::class];

            foreach ($namedNativeQueriesAnnotation->value as $namedNativeQuery) {
                $metadata->addNamedNativeQuery([
                    'name' => $namedNativeQuery->name,
                    'query' => $namedNativeQuery->query,
                    'resultClass' => $namedNativeQuery->resultClass,
                    'resultSetMapping' => $namedNativeQuery->resultSetMapping,
                ]);
            }
        }

        // Evaluate SqlResultSetMappings annotation
        if (isset($classAnnotations[ORM\SqlResultSetMappings::class])) {
            $sqlResultSetMappingsAnnotation = $classAnnotations[ORM\SqlResultSetMappings::class];

            foreach ($sqlResultSetMappingsAnnotation->value as $resultSetMapping) {
                $entities = [];
                $columns = [];
                foreach ($resultSetMapping->entities as $entityResultAnnotation) {
                    $entityResult = [
                        'fields' => [],
                        'entityClass' => $entityResultAnnotation->entityClass,
                        'discriminatorColumn' => $entityResultAnnotation->discriminatorColumn,
                    ];

                    foreach ($entityResultAnnotation->fields as $fieldResultAnnotation) {
                        $entityResult['fields'][] = [
                            'name' => $fieldResultAnnotation->name,
                            'column' => $fieldResultAnnotation->column
                        ];
                    }

                    $entities[] = $entityResult;
                }

                foreach ($resultSetMapping->columns as $columnResultAnnotation) {
                    $columns[] = [
                        'name' => $columnResultAnnotation->name,
                    ];
                }

                $metadata->addSqlResultSetMapping([
                    'name' => $resultSetMapping->name,
                    'entities' => $entities,
                    'columns' => $columns
                ]);
            }
        }

        // Evaluate NamedQueries annotation
        if (isset($classAnnotations[ORM\NamedQueries::class])) {
            $namedQueriesAnnotation = $classAnnotations[ORM\NamedQueries::class];

            if (!is_array($namedQueriesAnnotation->value)) {
                throw new \UnexpectedValueException('@ORM\NamedQueries should contain an array of @ORM\NamedQuery annotations.');
            }

            foreach ($namedQueriesAnnotation->value as $namedQuery) {
                if (!($namedQuery instanceof ORM\NamedQuery)) {
                    throw new \UnexpectedValueException('@ORM\NamedQueries should contain an array of @ORM\NamedQuery annotations.');
                }
                $metadata->addNamedQuery([
                    'name' => $namedQuery->name,
                    'query' => $namedQuery->query
                ]);
            }
        }

        // Evaluate InheritanceType annotation
        if (isset($classAnnotations[ORM\InheritanceType::class])) {
            $inheritanceTypeAnnotation = $classAnnotations[ORM\InheritanceType::class];
            $inheritanceType = constant('Doctrine\ORM\Mapping\ClassMetadata::INHERITANCE_TYPE_' . strtoupper($inheritanceTypeAnnotation->value));

            if ($inheritanceType !== ORM\ClassMetadata::INHERITANCE_TYPE_NONE) {

                // Evaluate DiscriminatorColumn annotation
                if (isset($classAnnotations[ORM\DiscriminatorColumn::class])) {
                    $discriminatorColumnAnnotation = $classAnnotations[ORM\DiscriminatorColumn::class];
                    $discriminatorColumn = [
                        'name' => $discriminatorColumnAnnotation->name,
                        'type' => $discriminatorColumnAnnotation->type,
                        'length' => $discriminatorColumnAnnotation->length,
                        'columnDefinition' => $discriminatorColumnAnnotation->columnDefinition
                    ];
                } else {
                    $discriminatorColumn = [
                        'name' => 'dtype', 'type' => 'string', 'length' => 255
                    ];
                }

                // Evaluate DiscriminatorMap annotation
                if (isset($classAnnotations[ORM\DiscriminatorMap::class])) {
                    $discriminatorMapAnnotation = $classAnnotations[ORM\DiscriminatorMap::class];
                    $discriminatorMap = $discriminatorMapAnnotation->value;
                } else {
                    $discriminatorMap = [];
                    $subclassNames = $this->reflectionService->getAllSubClassNamesForClass($className);
                    if (!$this->reflectionService->isClassAbstract($className)) {
                        $mappedClassName = strtolower(str_replace('Domain_Model_', '', str_replace('\\', '_', $className)));
                        $discriminatorMap[$mappedClassName] = $className;
                    }
                    foreach ($subclassNames as $subclassName) {
                        $mappedSubclassName = strtolower(str_replace('Domain_Model_', '', str_replace('\\', '_', $subclassName)));
                        $discriminatorMap[$mappedSubclassName] = $subclassName;
                    }
                }

                if ($discriminatorMap !== []) {
                    $metadata->setDiscriminatorColumn($discriminatorColumn);
                    $metadata->setDiscriminatorMap($discriminatorMap);
                } else {
                    $inheritanceType = ORM\ClassMetadata::INHERITANCE_TYPE_NONE;
                }
            }

            $metadata->setInheritanceType($inheritanceType);
        }

        // Evaluate DoctrineChangeTrackingPolicy annotation
        if (isset($classAnnotations[ORM\ChangeTrackingPolicy::class])) {
            $changeTrackingAnnotation = $classAnnotations[ORM\ChangeTrackingPolicy::class];
            $metadata->setChangeTrackingPolicy(constant('Doctrine\ORM\Mapping\ClassMetadata::CHANGETRACKING_' . strtoupper($changeTrackingAnnotation->value)));
        } else {
            $metadata->setChangeTrackingPolicy(ORM\ClassMetadata::CHANGETRACKING_DEFERRED_EXPLICIT);
        }

        // Evaluate annotations on properties/fields
        try {
            $this->evaluatePropertyAnnotations($metadata);
        } catch (ORM\MappingException $exception) {
            throw new ORM\MappingException(sprintf('Failure while evaluating property annotations for class "%s": %s', $metadata->getName(), $exception->getMessage()), 1382003497, $exception);
        }

        // build unique index for table
        if (!isset($classAnnotations[ORM\Embeddable::class])
            && !isset($primaryTable['uniqueConstraints'])) {
            $idProperties = array_keys($classSchema->getIdentityProperties());
            if (array_diff($idProperties, $metadata->getIdentifierFieldNames()) !== []) {
                $uniqueIndexName = $this->truncateIdentifier('flow_identity_' . $primaryTable['name']);
                foreach ($idProperties as $idProperty) {
                    $primaryTable['uniqueConstraints'][$uniqueIndexName]['columns'][] = isset($metadata->columnNames[$idProperty]) ? $metadata->columnNames[$idProperty] : strtolower($idProperty);
                }
            }
        }

        $metadata->setPrimaryTable($primaryTable);

        // Evaluate AssociationOverrides annotation
        $this->evaluateOverridesAnnotations($classAnnotations, $metadata);

        // Evaluate EntityListeners annotation
        $this->evaluateEntityListenersAnnotation($class, $metadata, $classAnnotations);

        // Evaluate @HasLifecycleCallbacks annotation
        $this->evaluateLifeCycleAnnotations($class, $metadata);
    }
1296358
private function generateMagicIsset(ClassMetadata $class)
    {
        $lazyPublicProperties = array_keys($this->getLazyLoadedPublicProperties($class));
        $hasParentIsset       = $class->getReflectionClass()->hasMethod('__isset');

        if (empty($lazyPublicProperties) && ! $hasParentIsset) {
            return '';
        }

        $inheritDoc = $hasParentIsset ? '{@inheritDoc}' : '';
        $magicIsset = <<<EOT
    /**
     * $inheritDoc
     * @param  string \$name
     * @return boolean
     */
    public function __isset(\$name)
    {

EOT;

        if ( ! empty($lazyPublicProperties)) {
            $magicIsset .= <<<'EOT'
        if (array_key_exists($name, $this->__getLazyProperties())) {
            $this->__initializer__ && $this->__initializer__->__invoke($this, '__isset', [$name]);

            return isset($this->$name);
        }


EOT;
        }

        if ($hasParentIsset) {
            $magicIsset .= <<<'EOT'
        $this->__initializer__ && $this->__initializer__->__invoke($this, '__isset', [$name]);

        return parent::__isset($name);

EOT;
        } else {
            $magicIsset .= "        return false;";
        }

        return $magicIsset . "\n    }";
    }
1004612
public function loadMetadataForClass(\ReflectionClass $class)
    {
        $classMetadata = new ClassMetadata($class->name);
        $classMetadata->fileResources[] = $class->getFilename();

        foreach ($this->reader->getClassAnnotations($class) as $annotation) {
            if ($annotation instanceOf Schema) {
                $classMetadata->schema = $annotation->name;
            }
            if ($annotation instanceOf Inherit) {
                $classMetadata->inherit = $annotation->name;
            }
        }

        if (null !== $classMetadata->schema) {
            return $classMetadata;
        }

        return null;
    }
408765
public function loadMetadataForClass($className, CommonClassMetadata $metadata)
    {
        /** @var \Doctrine\KeyValueStore\Mapping\ClassMetadata $metadata */
        try {
            $element = $this->getElement($className);
        } catch (MappingException $exception) {
            throw new \InvalidArgumentException($metadata->name . ' is not a valid key-value-store entity.');
        }

        $class = new \ReflectionClass($className);

        if (isset($element['storageName'])) {
            $metadata->storageName = $element['storageName'];
        }

        $ids = [];
        if (isset($element['id'])) {
            $ids = $element['id'];
        }

        $transients = [];
        if (isset($element['transient'])) {
            $transients = $element['transient'];
        }

        foreach ($class->getProperties() as $property) {
            if (in_array($property->getName(), $ids)) {
                $metadata->mapIdentifier($property->getName());

                continue;
            }

            if (in_array($property->getName(), $transients)) {
                $metadata->skipTransientField($property->getName());

                continue;
            }

            $metadata->mapField([
                'fieldName' => $property->getName(),
            ]);
        }
    }