/** * @param string $currentClass * * @return array */ private function getChildClasses($currentClass) { $classes = array(); foreach ($this->driver->getAllClassNames() as $className) { if (!ClassType::from($className)->isSubclassOf($currentClass)) { continue; } $classes[] = $className; } return $classes; }
/** * Check if this class is mapped by this EntityManager + ClassMetadata configuration * * @param $class * @return bool */ public function isTransient($class) { if (!$this->initialized) { $this->initialize(); } return $this->driver->isTransient($class); }
/** * Check if this class is mapped by this EntityManager + ClassMetadata configuration * * @param $class * @return bool */ public function isTransient($class) { if (!$this->initialized) { $this->initialize(); } // Check for namespace alias if (strpos($class, ':') !== false) { list($namespaceAlias, $simpleClassName) = explode(':', $class); $class = $this->em->getConfiguration()->getEntityNamespace($namespaceAlias) . '\\' . $simpleClassName; } return $this->driver->isTransient($class); }
/** * Whether the class with the specified name should have its metadata loaded. * * This is only the case for non-transient classes either mapped as an Entity or MappedSuperclass. * * @param string $className * @return boolean */ public function isTransient($className) { foreach ($this->drivers as $namespace => $driver) { if (strpos($className, $namespace) === 0) { return $driver->isTransient($className); } } if ($this->defaultDriver !== null) { return $this->defaultDriver->isTransient($className); } // class isTransient, i.e. not an entity or mapped superclass return true; }
/** * Loads the metadata of the class in question and all it's ancestors whose metadata * is still not loaded. * * @param string $name The name of the class for which the metadata should get loaded. * @param array $tables The metadata collection to which the loaded metadata is added. */ protected function loadMetadata($name) { if (!$this->initialized) { $this->initialize(); } $loaded = array(); $parentClasses = $this->getParentClasses($name); $parentClasses[] = $name; // Move down the hierarchy of parent classes, starting from the topmost class $parent = null; $rootEntityFound = false; $visited = array(); foreach ($parentClasses as $className) { if (isset($this->loadedMetadata[$className])) { $parent = $this->loadedMetadata[$className]; if (!$parent->isMappedSuperclass) { $rootEntityFound = true; array_unshift($visited, $className); } continue; } $class = $this->newClassMetadataInstance($className); if ($parent) { $class->setInheritanceType($parent->inheritanceType); $class->setDiscriminatorColumn($parent->discriminatorColumn); $class->setIdGeneratorType($parent->generatorType); $this->addInheritedFields($class, $parent); $this->addInheritedRelations($class, $parent); $class->setIdentifier($parent->identifier); $class->setVersioned($parent->isVersioned); $class->setVersionField($parent->versionField); $class->setDiscriminatorMap($parent->discriminatorMap); $class->setLifecycleCallbacks($parent->lifecycleCallbacks); $class->setChangeTrackingPolicy($parent->changeTrackingPolicy); } // Invoke driver try { $this->driver->loadMetadataForClass($className, $class); } catch (ReflectionException $e) { throw MappingException::reflectionFailure($className, $e); } // If this class has a parent the id generator strategy is inherited. // However this is only true if the hierachy of parents contains the root entity, // if it consinsts of mapped superclasses these don't necessarily include the id field. if ($parent && $rootEntityFound) { if ($parent->isIdGeneratorSequence()) { $class->setSequenceGeneratorDefinition($parent->sequenceGeneratorDefinition); } else { if ($parent->isIdGeneratorTable()) { $class->getTableGeneratorDefinition($parent->tableGeneratorDefinition); } } if ($parent->generatorType) { $class->setIdGeneratorType($parent->generatorType); } if ($parent->idGenerator) { $class->setIdGenerator($parent->idGenerator); } } else { $this->completeIdGeneratorMapping($class); } if ($parent && $parent->isInheritanceTypeSingleTable()) { $class->setPrimaryTable($parent->table); } $class->setParentClasses($visited); if ($this->evm->hasListeners(Events::loadClassMetadata)) { $eventArgs = new \Doctrine\ORM\Event\LoadClassMetadataEventArgs($class, $this->em); $this->evm->dispatchEvent(Events::loadClassMetadata, $eventArgs); } // Verify & complete identifier mapping if (!$class->identifier && !$class->isMappedSuperclass) { throw MappingException::identifierRequired($className); } // verify inheritance if (!$class->isMappedSuperclass && !$class->isInheritanceTypeNone()) { if (!$parent) { if (count($class->discriminatorMap) == 0) { throw MappingException::missingDiscriminatorMap($class->name); } if (!$class->discriminatorColumn) { throw MappingException::missingDiscriminatorColumn($class->name); } } else { if ($parent && !$class->reflClass->isAbstract() && !in_array($class->name, array_values($class->discriminatorMap))) { // enforce discriminator map for all entities of an inheritance hierachy, otherwise problems will occur. throw MappingException::mappedClassNotPartOfDiscriminatorMap($class->name, $class->rootEntityName); } } } else { if ($class->isMappedSuperclass && $class->name == $class->rootEntityName && (count($class->discriminatorMap) || $class->discriminatorColumn)) { // second condition is necessary for mapped superclasses in the middle of an inheritance hierachy throw MappingException::noInheritanceOnMappedSuperClass($class->name); } } $this->loadedMetadata[$className] = $class; $parent = $class; if (!$class->isMappedSuperclass) { $rootEntityFound = true; array_unshift($visited, $className); } $loaded[] = $className; } return $loaded; }
/** * {@inheritDoc} */ public function isTransient($className) { $this->initialize(); return $this->driver->isTransient($className); }
/** * Loads the metadata of the class in question and all it's ancestors whose metadata * is still not loaded. * * @param string $name The name of the class for which the metadata should get loaded. * @param array $tables The metadata collection to which the loaded metadata is added. */ protected function loadMetadata($name) { if (!$this->initialized) { $this->initialize(); } $loaded = array(); $parentClasses = $this->getParentClasses($name); $parentClasses[] = $name; // Move down the hierarchy of parent classes, starting from the topmost class $parent = null; $visited = array(); foreach ($parentClasses as $className) { if (isset($this->loadedMetadata[$className])) { $parent = $this->loadedMetadata[$className]; if (!$parent->isMappedSuperclass) { array_unshift($visited, $className); } continue; } $class = $this->newClassMetadataInstance($className); if ($parent) { $class->setInheritanceType($parent->inheritanceType); $class->setDiscriminatorColumn($parent->discriminatorColumn); $class->setIdGeneratorType($parent->generatorType); $this->addInheritedFields($class, $parent); $this->addInheritedRelations($class, $parent); $class->setIdentifier($parent->identifier); $class->setVersioned($parent->isVersioned); $class->setVersionField($parent->versionField); $class->setDiscriminatorMap($parent->discriminatorMap); $class->setLifecycleCallbacks($parent->lifecycleCallbacks); $class->setChangeTrackingPolicy($parent->changeTrackingPolicy); } // Invoke driver try { $this->driver->loadMetadataForClass($className, $class); } catch (ReflectionException $e) { throw MappingException::reflectionFailure($className, $e); } // Verify & complete identifier mapping if (!$class->identifier && !$class->isMappedSuperclass) { throw MappingException::identifierRequired($className); } if ($parent && !$parent->isMappedSuperclass) { if ($parent->isIdGeneratorSequence()) { $class->setSequenceGeneratorDefinition($parent->sequenceGeneratorDefinition); } else { if ($parent->isIdGeneratorTable()) { $class->getTableGeneratorDefinition($parent->tableGeneratorDefinition); } } if ($parent->generatorType) { $class->setIdGeneratorType($parent->generatorType); } if ($parent->idGenerator) { $class->setIdGenerator($parent->idGenerator); } } else { $this->completeIdGeneratorMapping($class); } if ($parent && $parent->isInheritanceTypeSingleTable()) { $class->setPrimaryTable($parent->table); } $class->setParentClasses($visited); if ($this->evm->hasListeners(Events::loadClassMetadata)) { $eventArgs = new \Doctrine\ORM\Event\LoadClassMetadataEventArgs($class); $this->evm->dispatchEvent(Events::loadClassMetadata, $eventArgs); } // verify inheritance if (!$parent && !$class->isMappedSuperclass && !$class->isInheritanceTypeNone()) { if (count($class->discriminatorMap) == 0) { throw MappingException::missingDiscriminatorMap($class->name); } if (!$class->discriminatorColumn) { throw MappingException::missingDiscriminatorColumn($class->name); } } $this->loadedMetadata[$className] = $class; $parent = $class; if (!$class->isMappedSuperclass) { array_unshift($visited, $className); } $loaded[] = $className; } return $loaded; }
/** * Get the extended driver instance which will * read the metadata required by extension * * @param ORMDriver $ormDriver * @throws DriverException if driver was not found in extension * @return Gedmo\Mapping\Driver */ private function _getDriver(ORMDriver $ormDriver) { $driver = null; if ($ormDriver instanceof \Doctrine\ORM\Mapping\Driver\DriverChain) { $driver = new Driver\Chain(); foreach ($ormDriver->getDrivers() as $namespace => $nestedOrmDriver) { $driver->addDriver($this->_getDriver($nestedOrmDriver), $namespace); } } else { $className = get_class($ormDriver); $driverName = substr($className, strrpos($className, '\\') + 1); $driverName = substr($driverName, 0, strpos($driverName, 'Driver')); // create driver instance $driverClassName = $this->_extensionNamespace . '\\Mapping\\Driver\\' . $driverName; if (!class_exists($driverClassName)) { throw DriverException::extensionDriverNotSupported($driverClassName, $driverName); } $driver = new $driverClassName(); if ($driver instanceof \Gedmo\Mapping\Driver\File) { $driver->setPaths($ormDriver->getPaths()); } } return $driver; }
/** * Check to see if the given metadata driver is the annotation driver for the * given directory path * * @param Driver $driver * @param string $path * @return boolean */ private function _isAnnotationDriverForPath(Driver $driver, $path) { if (!$driver instanceof AnnotationDriver) { return false; } if (in_array(realpath($path), $driver->getPaths())) { return true; } else { return false; } }