Ejemplo n.º 1
0
 public function guessColumnFormatters(\Faker\Generator $generator)
 {
     $formatters = array();
     $class = $this->class;
     $nameGuesser = new \Faker\Guesser\Name($generator);
     $columnTypeGuesser = new ColumnTypeGuesser($generator);
     foreach ($this->class->getFieldNames() as $fieldName) {
         if ($this->class->isIdentifier($fieldName) || !$this->class->hasField($fieldName)) {
             continue;
         }
         if ($formatter = $nameGuesser->guessFormat($fieldName)) {
             $formatters[$fieldName] = $formatter;
             continue;
         }
         if ($formatter = $columnTypeGuesser->guessFormat($fieldName, $this->class)) {
             $formatters[$fieldName] = $formatter;
             continue;
         }
     }
     foreach ($this->class->getAssociationNames() as $assocName) {
         if (!$this->class->isIdentifier($assocName) || !$this->class->isCollectionValuedAssociation($assocName)) {
             continue;
         }
         $relatedClass = $this->class->getAssociationTargetClass($assocName);
         $formatters[$assocName] = function ($inserted) use($relatedClass) {
             return isset($inserted[$relatedClass]) ? $inserted[$relatedClass][mt_rand(0, count($inserted[$relatedClass]) - 1)] : null;
         };
     }
     return $formatters;
 }
Ejemplo n.º 2
0
 /**
  * {@inheritDoc}
  */
 public function readExtendedMetadata(ClassMetadata $meta, array &$config)
 {
     $mapping = $this->_getMapping($meta->name);
     if (isset($mapping['gedmo'])) {
         $classMapping = $mapping['gedmo'];
         if (isset($classMapping['loggable'])) {
             $config['loggable'] = true;
             if (isset($classMapping['loggable']['logEntryClass'])) {
                 if (!class_exists($classMapping['loggable']['logEntryClass'])) {
                     throw new InvalidMappingException("LogEntry class: {$classMapping['loggable']['logEntryClass']} does not exist.");
                 }
                 $config['logEntryClass'] = $classMapping['loggable']['logEntryClass'];
             }
         }
     }
     if (isset($mapping['fields'])) {
         foreach ($mapping['fields'] as $field => $fieldMapping) {
             if (isset($fieldMapping['gedmo'])) {
                 if (in_array('versioned', $fieldMapping['gedmo'])) {
                     if ($meta->isCollectionValuedAssociation($field)) {
                         throw new InvalidMappingException("Cannot versioned [{$field}] as it is collection in object - {$meta->name}");
                     }
                     // fields cannot be overrided and throws mapping exception
                     $config['versioned'][] = $field;
                 }
             }
         }
     }
     if (isset($mapping['manyToOne'])) {
         foreach ($mapping['manyToOne'] as $field => $fieldMapping) {
             if (isset($fieldMapping['gedmo'])) {
                 if (in_array('versioned', $fieldMapping['gedmo'])) {
                     if ($meta->isCollectionValuedAssociation($field)) {
                         throw new InvalidMappingException("Cannot versioned [{$field}] as it is collection in object - {$meta->name}");
                     }
                     // fields cannot be overrided and throws mapping exception
                     $config['versioned'][] = $field;
                 }
             }
         }
     }
     if (isset($mapping['oneToOne'])) {
         foreach ($mapping['oneToOne'] as $field => $fieldMapping) {
             if (isset($fieldMapping['gedmo'])) {
                 if (in_array('versioned', $fieldMapping['gedmo'])) {
                     if ($meta->isCollectionValuedAssociation($field)) {
                         throw new InvalidMappingException("Cannot versioned [{$field}] as it is collection in object - {$meta->name}");
                     }
                     // fields cannot be overrided and throws mapping exception
                     $config['versioned'][] = $field;
                 }
             }
         }
     }
 }
Ejemplo n.º 3
0
 /**
  * Hydrate $object with the provided $data.
  *
  * @param  array  $data
  * @param  object $object
  * @throws \Exception
  * @return object
  */
 public function hydrate(array $data, $object)
 {
     $this->metadata = $this->objectManager->getClassMetadata(get_class($object));
     foreach ($data as $field => &$value) {
         if ($this->metadata->hasAssociation($field)) {
             $target = $this->metadata->getAssociationTargetClass($field);
             if ($this->metadata->isSingleValuedAssociation($field)) {
                 $value = $this->toOne($value, $target);
             } elseif ($this->metadata->isCollectionValuedAssociation($field)) {
                 $value = $this->toMany($value, $target);
             }
         }
     }
     return $this->hydrator->hydrate($data, $object);
 }
Ejemplo n.º 4
0
 private function getAssociationString(ClassMetadata $class1, $association)
 {
     $targetClassName = $class1->getAssociationTargetClass($association);
     $class2 = $this->getClassByName($targetClassName);
     $isInverse = $class1->isAssociationInverseSide($association);
     $class1Count = $class1->isCollectionValuedAssociation($association) ? 2 : 1;
     if (null === $class2) {
         return $this->getClassString($class1) . ($isInverse ? '<' : '<>') . '-' . $association . ' ' . ($class1Count > 1 ? '*' : ($class1Count ? '1' : '')) . ($isInverse ? '<>' : '>') . '[' . str_replace('\\', '.', $targetClassName) . ']';
     }
     $class1SideName = $association;
     $class2SideName = '';
     $class2Count = 0;
     $bidirectional = false;
     if ($isInverse) {
         $class2SideName = (string) $class1->getAssociationMappedByTargetField($association);
         if ($class2SideName) {
             $class2Count = $class2->isCollectionValuedAssociation($class2SideName) ? 2 : 1;
             $bidirectional = true;
         }
     } else {
         foreach ($class2->getAssociationNames() as $class2Side) {
             if ($class2->isAssociationInverseSide($class2Side) && $class2->getAssociationMappedByTargetField($class2Side) === $association) {
                 $class2SideName = $class2Side;
                 $class2Count = $class2->isCollectionValuedAssociation($class2SideName) ? 2 : 1;
                 $bidirectional = true;
                 break;
             }
         }
     }
     $this->visitAssociation($targetClassName, $class2SideName);
     return $this->getClassString($class1) . ($bidirectional ? $isInverse ? '<' : '<>' : '') . ($class2SideName ? $class2SideName . ' ' : '') . ($class2Count > 1 ? '*' : ($class2Count ? '1' : '')) . '-' . $class1SideName . ' ' . ($class1Count > 1 ? '*' : ($class1Count ? '1' : '')) . ($bidirectional && $isInverse ? '<>' : '>') . $this->getClassString($class2);
 }
Ejemplo n.º 5
0
 /**
  * {@inheritDoc}
  */
 public function readExtendedMetadata(ClassMetadata $meta, array &$config)
 {
     $class = $meta->getReflectionClass();
     // class annotations
     if ($annot = $this->reader->getClassAnnotation($class, self::LOGGABLE)) {
         $config['loggable'] = true;
         if ($annot->logEntryClass) {
             if (!class_exists($annot->logEntryClass)) {
                 throw new InvalidMappingException("LogEntry class: {$annot->logEntryClass} does not exist.");
             }
             $config['logEntryClass'] = $annot->logEntryClass;
         }
     }
     // property annotations
     foreach ($class->getProperties() as $property) {
         if ($meta->isMappedSuperclass && !$property->isPrivate() || $meta->isInheritedField($property->name) || isset($meta->associationMappings[$property->name]['inherited'])) {
             continue;
         }
         // versioned property
         if ($versioned = $this->reader->getPropertyAnnotation($property, self::VERSIONED)) {
             $field = $property->getName();
             if ($meta->isCollectionValuedAssociation($field)) {
                 throw new InvalidMappingException("Cannot versioned [{$field}] as it is collection in object - {$meta->name}");
             }
             // fields cannot be overrided and throws mapping exception
             $config['versioned'][] = $field;
         }
     }
 }
Ejemplo n.º 6
0
    /**
     * Prepare strategies before the hydrator is used
     *
     * @throws \InvalidArgumentException
     * @return void
     */
    protected function prepareStrategies()
    {
        $associations = $this->metadata->getAssociationNames();

        foreach ($associations as $association) {
            if ($this->metadata->isCollectionValuedAssociation($association)) {
                // Add a strategy if the association has none set by user
                if (!$this->hasStrategy($association)) {
                    if ($this->byValue) {
                        $this->addStrategy($association, new Strategy\AllowRemoveByValue());
                    } else {
                        $this->addStrategy($association, new Strategy\AllowRemoveByReference());
                    }
                }

                $strategy = $this->getStrategy($association);

                if (!$strategy instanceof Strategy\AbstractCollectionStrategy) {
                    throw new InvalidArgumentException(
                        sprintf(
                            'Strategies used for collections valued associations must inherit from '
                            . 'Strategy\AbstractCollectionStrategy, %s given',
                            get_class($strategy)
                        )
                    );
                }

                $strategy->setCollectionName($association)
                         ->setClassMetadata($this->metadata);
            }
        }
    }
Ejemplo n.º 7
0
 /**
  * Hydrate $object with the provided $data.
  *
  * @param  array  $data
  * @param  object $object
  * @throws \Exception
  * @return object
  */
 public function hydrate(array $data, $object)
 {
     $this->metadata = $this->objectManager->getClassMetadata(get_class($object));
     $object = $this->tryConvertArrayToObject($data, $object);
     foreach ($data as $field => &$value) {
         $value = $this->hydrateValue($field, $value);
         if ($value === null) {
             continue;
         }
         // @todo DateTime (and other types) conversion should be handled by doctrine itself in future
         if (in_array($this->metadata->getTypeOfField($field), array('datetime', 'time', 'date'))) {
             if (is_int($value)) {
                 $dt = new DateTime();
                 $dt->setTimestamp($value);
                 $value = $dt;
             } elseif (is_string($value)) {
                 $value = new DateTime($value);
             }
         }
         if ($this->metadata->hasAssociation($field)) {
             $target = $this->metadata->getAssociationTargetClass($field);
             if ($this->metadata->isSingleValuedAssociation($field)) {
                 $value = $this->toOne($value, $target);
             } elseif ($this->metadata->isCollectionValuedAssociation($field)) {
                 $value = $this->toMany($value, $target);
                 // Automatically merge collections using helper utility
                 $propertyRefl = $this->metadata->getReflectionClass()->getProperty($field);
                 $propertyRefl->setAccessible(true);
                 $previousValue = $propertyRefl->getValue($object);
                 $value = CollectionUtils::intersectUnion($previousValue, $value);
             }
         }
     }
     return $this->hydrator->hydrate($data, $object);
 }
Ejemplo n.º 8
0
 /**
  * Adds an object to a collection.
  *
  * @param string $field
  * @param array  $args
  *
  * @return void
  *
  * @throws \BadMethodCallException
  * @throws \InvalidArgumentException
  */
 private function add($field, $args)
 {
     $this->initializeDoctrine();
     if ($this->cm->hasAssociation($field) && $this->cm->isCollectionValuedAssociation($field)) {
         $targetClass = $this->cm->getAssociationTargetClass($field);
         if (!$args[0] instanceof $targetClass) {
             throw new \InvalidArgumentException("Expected persistent object of type '" . $targetClass . "'");
         }
         if (!$this->{$field} instanceof Collection) {
             $this->{$field} = new ArrayCollection($this->{$field} ?: []);
         }
         $this->{$field}->add($args[0]);
         $this->completeOwningSide($field, $targetClass, $args[0]);
     } else {
         throw new \BadMethodCallException("There is no method add" . $field . "() on " . $this->cm->getName());
     }
 }
 /**
  * {@inheritDoc}
  */
 protected function validateExtendedMetadata(ClassMetadata $baseClassMetadata, ClassMetadataInterface $extendedClassMetadata)
 {
     if ($extendedClassMetadata->hasTranslatableProperties()) {
         if (!isset($extendedClassMetadata->localeProperty)) {
             throw new Exception\MappingException('Entity \'' . $baseClassMetadata->name . '\' has translatable properties so it must have property marked with @Translatable\\Language annotation');
         }
         $translatableProperties = $extendedClassMetadata->getTranslatableProperties();
         foreach ($translatableProperties as $translation => $properties) {
             if (!$baseClassMetadata->hasAssociation($translation) || !$baseClassMetadata->isCollectionValuedAssociation($translation)) {
                 throw new Exception\MappingException('Field \'' . $translation . '\' in entity \'' . $baseClassMetadata->name . '\' has to be a OneToMany association');
             }
         }
     }
     if (isset($extendedClassMetadata->localeProperty)) {
         if ($extendedClassMetadata->hasTranslatableProperties() && ($baseClassMetadata->hasField($extendedClassMetadata->localeProperty) || $baseClassMetadata->hasAssociation($extendedClassMetadata->localeProperty))) {
             throw new Exception\MappingException('Entity \'' . $baseClassMetadata->name . '\' seems to be a translatable entity so its \'' . $extendedClassMetadata->localeProperty . '\' field must not be persistent');
         } else {
             if (!$extendedClassMetadata->hasTranslatableProperties() && !$baseClassMetadata->hasField($extendedClassMetadata->localeProperty) && !$baseClassMetadata->hasAssociation($extendedClassMetadata->localeProperty)) {
                 throw new Exception\MappingException('Entity \'' . $baseClassMetadata->name . '\' seems to be a translation entity so its \'' . $extendedClassMetadata->localeProperty . '\' field must be persistent');
             }
         }
     }
 }
Ejemplo n.º 10
0
 /**
  * @param ClassMetadata $meta
  * @param string        $field
  *
  * @return bool
  */
 protected function isMappingValid(ClassMetadata $meta, $field)
 {
     return $meta->isCollectionValuedAssociation($field) == false;
 }
 /**
  * @param \Doctrine\Common\Persistence\Mapping\ClassMetadata $baseClassMetadata
  * @param \FSi\DoctrineExtensions\Translatable\Mapping\ClassMetadata $translatableClassMetadata
  * @throws \FSi\DoctrineExtensions\Translatable\Exception\MappingException
  */
 private function validateTranslatableProperties(ClassMetadata $baseClassMetadata, TranslatableClassMetadata $translatableClassMetadata)
 {
     $translatableProperties = $translatableClassMetadata->getTranslatableProperties();
     foreach ($translatableProperties as $translation => $properties) {
         if (!$baseClassMetadata->hasAssociation($translation) || !$baseClassMetadata->isCollectionValuedAssociation($translation)) {
             throw new Exception\MappingException(sprintf("Field '%s' in entity '%s' has to be a OneToMany association", $translation, $baseClassMetadata->getName()));
         }
     }
 }
 /**
  * Производит простой перебор ассоциаций, взятых из метаданных и на каждую ассоциацию вызывает callback
  *
  * @param ClassMetadata $metadata мета данные сущности
  * @param callable $callback метод, который будет вызван для каждой найденной ассоциации
  */
 private function bypassAssociationsOfClass(ClassMetadata $metadata, \Closure $callback)
 {
     foreach ($metadata->getAssociationNames() as $assocName) {
         if (!$metadata->isCollectionValuedAssociation($assocName)) {
             $callback($assocName);
         }
     }
 }
Ejemplo n.º 13
0
 /**
  * Builds the association value.
  *
  * @param ClassMetadata $metadata
  * @param string        $propertyPath
  * @param string        $value
  *
  * @return array|object
  * @throws \Exception
  */
 private function buildAssociationValue(ClassMetadata $metadata, $propertyPath, $value)
 {
     $childMetadata = $this->manager->getClassMetadata($metadata->getAssociationTargetClass($propertyPath));
     // Single association
     if ($metadata->isSingleValuedAssociation($propertyPath)) {
         if (is_string($value) && '#' === substr($value, 0, 1)) {
             return $this->getReference(substr($value, 1));
         } elseif (is_array($value)) {
             return $this->buildEntity($childMetadata, $value);
         }
         throw new \Exception("Unexpected value for single association '{$propertyPath}'.");
         // Collection association
     } elseif ($metadata->isCollectionValuedAssociation($propertyPath)) {
         if (!is_array($value)) {
             throw new \Exception('Expected array.');
         }
         $builtValue = [];
         foreach ($value as $childData) {
             if (is_string($childData) && '#' === substr($childData, 0, 1)) {
                 array_push($builtValue, $this->getReference(substr($childData, 1)));
             } elseif (is_array($value)) {
                 array_push($builtValue, $this->buildEntity($childMetadata, $childData));
             } else {
                 throw new \Exception("Unexpected value for association '{$propertyPath}'.");
             }
         }
         return $builtValue;
     }
     throw new \Exception("Unexpected association path '{$propertyPath}'.");
 }
Ejemplo n.º 14
0
 /**
  * @param \Faker\Generator $generator
  * @return array
  */
 public function guessColumnFormatters(\Faker\Generator $generator)
 {
     $formatters = array();
     $nameGuesser = new \Faker\Guesser\Name($generator);
     $columnTypeGuesser = new ColumnTypeGuesser($generator);
     foreach ($this->class->getFieldNames() as $fieldName) {
         if ($this->class->isIdentifier($fieldName) || !$this->class->hasField($fieldName)) {
             continue;
         }
         $size = isset($this->class->fieldMappings[$fieldName]['length']) ? $this->class->fieldMappings[$fieldName]['length'] : null;
         if ($formatter = $nameGuesser->guessFormat($fieldName, $size)) {
             $formatters[$fieldName] = $formatter;
             continue;
         }
         if ($formatter = $columnTypeGuesser->guessFormat($fieldName, $this->class)) {
             $formatters[$fieldName] = $formatter;
             continue;
         }
     }
     foreach ($this->class->getAssociationNames() as $assocName) {
         if ($this->class->isCollectionValuedAssociation($assocName)) {
             continue;
         }
         $relatedClass = $this->class->getAssociationTargetClass($assocName);
         $unique = $optional = false;
         if ($this->class instanceof \Doctrine\ORM\Mapping\ClassMetadata) {
             $mappings = $this->class->getAssociationMappings();
             foreach ($mappings as $mapping) {
                 if ($mapping['targetEntity'] == $relatedClass) {
                     if ($mapping['type'] == \Doctrine\ORM\Mapping\ClassMetadata::ONE_TO_ONE) {
                         $unique = true;
                         $optional = isset($mapping['joinColumns'][0]['nullable']) ? $mapping['joinColumns'][0]['nullable'] : false;
                         break;
                     }
                 }
             }
         } elseif ($this->class instanceof \Doctrine\ODM\MongoDB\Mapping\ClassMetadata) {
             $mappings = $this->class->associationMappings;
             foreach ($mappings as $mapping) {
                 if ($mapping['targetDocument'] == $relatedClass) {
                     if ($mapping['type'] == \Doctrine\ODM\MongoDB\Mapping\ClassMetadata::ONE && $mapping['association'] == \Doctrine\ODM\MongoDB\Mapping\ClassMetadata::REFERENCE_ONE) {
                         $unique = true;
                         $optional = isset($mapping['nullable']) ? $mapping['nullable'] : false;
                         break;
                     }
                 }
             }
         }
         $index = 0;
         $formatters[$assocName] = function ($inserted) use($relatedClass, &$index, $unique, $optional) {
             if (isset($inserted[$relatedClass])) {
                 if ($unique) {
                     $related = null;
                     if (isset($inserted[$relatedClass][$index]) || !$optional) {
                         $related = $inserted[$relatedClass][$index];
                     }
                     $index++;
                     return $related;
                 }
                 return $inserted[$relatedClass][mt_rand(0, count($inserted[$relatedClass]) - 1)];
             }
             return null;
         };
     }
     return $formatters;
 }