From 3bf9f7782debd42bc1cd050ea0b51ef14fbf8e17 Mon Sep 17 00:00:00 2001 From: Bernhard Schussek Date: Thu, 27 Jan 2011 15:25:28 +0100 Subject: [PATCH] [DoctrineBundle][Form] Implemented EntityFieldFactoryGuesser --- .../DoctrineBundle/Resources/config/orm.xml | 8 + .../Doctrine/EntityFieldFactoryGuesser.php | 194 ++++++++++++++++++ 2 files changed, 202 insertions(+) create mode 100644 src/Symfony/Component/Form/Extension/Doctrine/EntityFieldFactoryGuesser.php diff --git a/src/Symfony/Bundle/DoctrineBundle/Resources/config/orm.xml b/src/Symfony/Bundle/DoctrineBundle/Resources/config/orm.xml index 3426c686a2..f7661c1573 100644 --- a/src/Symfony/Bundle/DoctrineBundle/Resources/config/orm.xml +++ b/src/Symfony/Bundle/DoctrineBundle/Resources/config/orm.xml @@ -45,6 +45,9 @@ Symfony\Bundle\DoctrineBundle\CacheWarmer\ProxyCacheWarmer + + + Symfony\Component\Form\Extension\Doctrine\EntityFieldFactoryGuesser @@ -62,5 +65,10 @@ + + + + + diff --git a/src/Symfony/Component/Form/Extension/Doctrine/EntityFieldFactoryGuesser.php b/src/Symfony/Component/Form/Extension/Doctrine/EntityFieldFactoryGuesser.php new file mode 100644 index 0000000000..cc24b509a3 --- /dev/null +++ b/src/Symfony/Component/Form/Extension/Doctrine/EntityFieldFactoryGuesser.php @@ -0,0 +1,194 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Component\Form\Extension\Doctrine; + +use Symfony\Component\Form\FieldFactory\FieldFactoryGuesserInterface; +use Symfony\Component\Form\FieldFactory\FieldFactoryGuess; +use Symfony\Component\Form\FieldFactory\FieldFactoryClassGuess; +use Doctrine\ORM\EntityManager; + +/** + * Guesses form fields from the metadata of Doctrine 2 + * + * @author Bernhard Schussek + */ +class EntityFieldFactoryGuesser implements FieldFactoryGuesserInterface +{ + /** + * The Doctrine 2 entity manager + * @var Doctrine\ORM\EntityManager + */ + protected $em = null; + + /** + * Constructor + * + * @param ClassMetadataFactoryInterface $metadataFactory + */ + public function __construct(EntityManager $em) + { + $this->em = $em; + } + + /** + * Returns whether Doctrine 2 metadata exists for that class + * + * @return boolean + */ + protected function isMappedClass($class) + { + return !$this->em->getConfiguration()->getMetadataDriverImpl()->isTransient($class); + } + + /** + * @inheritDoc + */ + public function guessClass($object, $property) + { + $className = get_class($object); + + if ($this->isMappedClass($className)) { + $metadata = $this->em->getClassMetadata($className); + + if ($metadata->hasAssociation($property)) { + $multiple = $metadata->isCollectionValuedAssociation($property); + $mapping = $metadata->getAssociationMapping($property); + + return new FieldFactoryClassGuess( + 'Symfony\Component\Form\Extension\Doctrine\EntityChoiceField', + array( + 'em' => $this->em, + 'class' => $mapping['targetEntity'], + 'multiple' => $multiple, + ), + FieldFactoryGuess::HIGH_CONFIDENCE + ); + } else { + switch ($metadata->getTypeOfField($property)) + { + // case 'array': + // return new FieldFactoryClassGuess( + // 'Symfony\Component\Form\CollectionField', + // array(), + // FieldFactoryGuess::HIGH_CONFIDENCE + // ); + case 'boolean': + return new FieldFactoryClassGuess( + 'Symfony\Component\Form\CheckboxField', + array(), + FieldFactoryGuess::HIGH_CONFIDENCE + ); + case 'datetime': + case 'vardatetime': + case 'datetimetz': + return new FieldFactoryClassGuess( + 'Symfony\Component\Form\DateTimeField', + array(), + FieldFactoryGuess::HIGH_CONFIDENCE + ); + case 'date': + return new FieldFactoryClassGuess( + 'Symfony\Component\Form\DateField', + array(), + FieldFactoryGuess::HIGH_CONFIDENCE + ); + case 'decimal': + case 'float': + return new FieldFactoryClassGuess( + 'Symfony\Component\Form\NumberField', + array(), + FieldFactoryGuess::MEDIUM_CONFIDENCE + ); + case 'integer': + case 'bigint': + case 'smallint': + return new FieldFactoryClassGuess( + 'Symfony\Component\Form\IntegerField', + array(), + FieldFactoryGuess::MEDIUM_CONFIDENCE + ); + case 'string': + return new FieldFactoryClassGuess( + 'Symfony\Component\Form\TextField', + array(), + FieldFactoryGuess::MEDIUM_CONFIDENCE + ); + case 'text': + return new FieldFactoryClassGuess( + 'Symfony\Component\Form\TextareaField', + array(), + FieldFactoryGuess::MEDIUM_CONFIDENCE + ); + case 'time': + return new FieldFactoryClassGuess( + 'Symfony\Component\Form\TimeField', + array(), + FieldFactoryGuess::HIGH_CONFIDENCE + ); + // case 'object': ??? + } + } + } + + return new FieldFactoryClassGuess( + 'Symfony\Component\Form\TextField', + array(), + FieldFactoryGuess::LOW_CONFIDENCE + ); + } + + /** + * @inheritDoc + */ + public function guessRequired($object, $property) + { + if ($this->isMappedClass(get_class($object))) { + $metadata = $this->em->getClassMetadata(get_class($object)); + + if ($metadata->hasField($property)) { + if (!$metadata->isNullable($property)) { + return new FieldFactoryGuess( + true, + FieldFactoryGuess::HIGH_CONFIDENCE + ); + } + + return new FieldFactoryGuess( + false, + FieldFactoryGuess::MEDIUM_CONFIDENCE + ); + } + } + } + + /** + * @inheritDoc + */ + public function guessMaxLength($object, $property) + { + if ($this->isMappedClass(get_class($object))) { + $metadata = $this->em->getClassMetadata(get_class($object)); + + if (!$metadata->hasAssociation($property)) { + $mapping = $metadata->getFieldMapping($property); + + + if (isset($mapping['length'])) { + return new FieldFactoryGuess( + $mapping['length'], + FieldFactoryGuess::HIGH_CONFIDENCE + ); + } + } + } + } +} \ No newline at end of file