bug #18209 [PropertyInfo] Support Doctrine custom mapping type in DoctrineExtractor (teohhanhui)
This PR was submitted for the master branch but it was merged into the 2.8 branch instead (closes #18209).
Discussion
----------
[PropertyInfo] Support Doctrine custom mapping type in DoctrineExtractor
| Q | A
| ------------- | ---
| Branch? | 2.8
| Bug fix? | yes
| New feature? | no
| BC breaks? | no
| Deprecations? | no
| Tests pass? | yes
| Fixed tickets | N/A
| License | MIT
| Doc PR | N/A
Also use Doctrine\DBAL\Types\Type class constants
Commits
-------
b50360f
[PropertyInfo] Support Doctrine custom mapping type in DoctrineExtractor
This commit is contained in:
commit
0c01903559
@ -13,6 +13,7 @@ namespace Symfony\Bridge\Doctrine\PropertyInfo;
|
|||||||
|
|
||||||
use Doctrine\Common\Persistence\Mapping\ClassMetadataFactory;
|
use Doctrine\Common\Persistence\Mapping\ClassMetadataFactory;
|
||||||
use Doctrine\Common\Persistence\Mapping\MappingException;
|
use Doctrine\Common\Persistence\Mapping\MappingException;
|
||||||
|
use Doctrine\DBAL\Types\Type as DBALType;
|
||||||
use Doctrine\ORM\Mapping\ClassMetadataInfo;
|
use Doctrine\ORM\Mapping\ClassMetadataInfo;
|
||||||
use Doctrine\ORM\Mapping\MappingException as OrmMappingException;
|
use Doctrine\ORM\Mapping\MappingException as OrmMappingException;
|
||||||
use Symfony\Component\PropertyInfo\PropertyListExtractorInterface;
|
use Symfony\Component\PropertyInfo\PropertyListExtractorInterface;
|
||||||
@ -93,23 +94,26 @@ class DoctrineExtractor implements PropertyListExtractorInterface, PropertyTypeE
|
|||||||
$nullable = $metadata instanceof ClassMetadataInfo && $metadata->isNullable($property);
|
$nullable = $metadata instanceof ClassMetadataInfo && $metadata->isNullable($property);
|
||||||
|
|
||||||
switch ($typeOfField) {
|
switch ($typeOfField) {
|
||||||
case 'date':
|
case DBALType::DATE:
|
||||||
case 'datetime':
|
case DBALType::DATETIME:
|
||||||
case 'datetimetz':
|
case DBALType::DATETIMETZ:
|
||||||
case 'time':
|
case 'vardatetime':
|
||||||
|
case DBALType::TIME:
|
||||||
return array(new Type(Type::BUILTIN_TYPE_OBJECT, $nullable, 'DateTime'));
|
return array(new Type(Type::BUILTIN_TYPE_OBJECT, $nullable, 'DateTime'));
|
||||||
|
|
||||||
case 'array':
|
case DBALType::TARRAY:
|
||||||
return array(new Type(Type::BUILTIN_TYPE_ARRAY, $nullable, null, true));
|
return array(new Type(Type::BUILTIN_TYPE_ARRAY, $nullable, null, true));
|
||||||
|
|
||||||
case 'simple_array':
|
case DBALType::SIMPLE_ARRAY:
|
||||||
return array(new Type(Type::BUILTIN_TYPE_ARRAY, $nullable, null, true, new Type(Type::BUILTIN_TYPE_INT), new Type(Type::BUILTIN_TYPE_STRING)));
|
return array(new Type(Type::BUILTIN_TYPE_ARRAY, $nullable, null, true, new Type(Type::BUILTIN_TYPE_INT), new Type(Type::BUILTIN_TYPE_STRING)));
|
||||||
|
|
||||||
case 'json_array':
|
case DBALType::JSON_ARRAY:
|
||||||
return array(new Type(Type::BUILTIN_TYPE_ARRAY, $nullable, null, true));
|
return array(new Type(Type::BUILTIN_TYPE_ARRAY, $nullable, null, true));
|
||||||
|
|
||||||
default:
|
default:
|
||||||
return array(new Type($this->getPhpType($typeOfField), $nullable));
|
$builtinType = $this->getPhpType($typeOfField);
|
||||||
|
|
||||||
|
return $builtinType ? array(new Type($builtinType, $nullable)) : null;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -119,36 +123,37 @@ class DoctrineExtractor implements PropertyListExtractorInterface, PropertyTypeE
|
|||||||
*
|
*
|
||||||
* @param string $doctrineType
|
* @param string $doctrineType
|
||||||
*
|
*
|
||||||
* @return string
|
* @return string|null
|
||||||
*/
|
*/
|
||||||
private function getPhpType($doctrineType)
|
private function getPhpType($doctrineType)
|
||||||
{
|
{
|
||||||
switch ($doctrineType) {
|
switch ($doctrineType) {
|
||||||
case 'smallint':
|
case DBALType::SMALLINT:
|
||||||
// No break
|
case DBALType::BIGINT:
|
||||||
case 'bigint':
|
case DBALType::INTEGER:
|
||||||
// No break
|
|
||||||
case 'integer':
|
|
||||||
return Type::BUILTIN_TYPE_INT;
|
return Type::BUILTIN_TYPE_INT;
|
||||||
|
|
||||||
case 'decimal':
|
case DBALType::FLOAT:
|
||||||
|
case DBALType::DECIMAL:
|
||||||
return Type::BUILTIN_TYPE_FLOAT;
|
return Type::BUILTIN_TYPE_FLOAT;
|
||||||
|
|
||||||
case 'text':
|
case DBALType::STRING:
|
||||||
// No break
|
case DBALType::TEXT:
|
||||||
case 'guid':
|
case DBALType::GUID:
|
||||||
return Type::BUILTIN_TYPE_STRING;
|
return Type::BUILTIN_TYPE_STRING;
|
||||||
|
|
||||||
case 'boolean':
|
case DBALType::BOOLEAN:
|
||||||
return Type::BUILTIN_TYPE_BOOL;
|
return Type::BUILTIN_TYPE_BOOL;
|
||||||
|
|
||||||
case 'blob':
|
case DBALType::BLOB:
|
||||||
// No break
|
|
||||||
case 'binary':
|
case 'binary':
|
||||||
return Type::BUILTIN_TYPE_RESOURCE;
|
return Type::BUILTIN_TYPE_RESOURCE;
|
||||||
|
|
||||||
|
case DBALType::OBJECT:
|
||||||
|
return Type::BUILTIN_TYPE_OBJECT;
|
||||||
|
|
||||||
default:
|
default:
|
||||||
return $doctrineType;
|
return;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -11,6 +11,7 @@
|
|||||||
|
|
||||||
namespace Symfony\Bridge\Doctrine\PropertyInfo\Tests;
|
namespace Symfony\Bridge\Doctrine\PropertyInfo\Tests;
|
||||||
|
|
||||||
|
use Doctrine\DBAL\Types\Type as DBALType;
|
||||||
use Doctrine\ORM\EntityManager;
|
use Doctrine\ORM\EntityManager;
|
||||||
use Doctrine\ORM\Tools\Setup;
|
use Doctrine\ORM\Tools\Setup;
|
||||||
use Symfony\Bridge\Doctrine\PropertyInfo\DoctrineExtractor;
|
use Symfony\Bridge\Doctrine\PropertyInfo\DoctrineExtractor;
|
||||||
@ -31,6 +32,11 @@ class DoctrineExtractorTest extends \PHPUnit_Framework_TestCase
|
|||||||
$config = Setup::createAnnotationMetadataConfiguration(array(__DIR__.DIRECTORY_SEPARATOR.'Fixtures'), true);
|
$config = Setup::createAnnotationMetadataConfiguration(array(__DIR__.DIRECTORY_SEPARATOR.'Fixtures'), true);
|
||||||
$entityManager = EntityManager::create(array('driver' => 'pdo_sqlite'), $config);
|
$entityManager = EntityManager::create(array('driver' => 'pdo_sqlite'), $config);
|
||||||
|
|
||||||
|
if (!DBALType::hasType('foo')) {
|
||||||
|
DBALType::addType('foo', 'Symfony\Bridge\Doctrine\Tests\PropertyInfo\Fixtures\DoctrineFooType');
|
||||||
|
$entityManager->getConnection()->getDatabasePlatform()->registerDoctrineTypeMapping('custom_foo', 'foo');
|
||||||
|
}
|
||||||
|
|
||||||
$this->extractor = new DoctrineExtractor($entityManager->getMetadataFactory());
|
$this->extractor = new DoctrineExtractor($entityManager->getMetadataFactory());
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -45,6 +51,7 @@ class DoctrineExtractorTest extends \PHPUnit_Framework_TestCase
|
|||||||
'simpleArray',
|
'simpleArray',
|
||||||
'bool',
|
'bool',
|
||||||
'binary',
|
'binary',
|
||||||
|
'customFoo',
|
||||||
'foo',
|
'foo',
|
||||||
'bar',
|
'bar',
|
||||||
),
|
),
|
||||||
@ -78,6 +85,7 @@ class DoctrineExtractorTest extends \PHPUnit_Framework_TestCase
|
|||||||
new Type(Type::BUILTIN_TYPE_OBJECT, false, 'Symfony\Bridge\Doctrine\Tests\PropertyInfo\Fixtures\DoctrineRelation')
|
new Type(Type::BUILTIN_TYPE_OBJECT, false, 'Symfony\Bridge\Doctrine\Tests\PropertyInfo\Fixtures\DoctrineRelation')
|
||||||
))),
|
))),
|
||||||
array('simpleArray', array(new Type(Type::BUILTIN_TYPE_ARRAY, false, null, true, new Type(Type::BUILTIN_TYPE_INT), new Type(Type::BUILTIN_TYPE_STRING)))),
|
array('simpleArray', array(new Type(Type::BUILTIN_TYPE_ARRAY, false, null, true, new Type(Type::BUILTIN_TYPE_INT), new Type(Type::BUILTIN_TYPE_STRING)))),
|
||||||
|
array('customFoo', null),
|
||||||
array('notMapped', null),
|
array('notMapped', null),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
@ -70,5 +70,10 @@ class DoctrineDummy
|
|||||||
*/
|
*/
|
||||||
private $binary;
|
private $binary;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @Column(type="custom_foo")
|
||||||
|
*/
|
||||||
|
private $customFoo;
|
||||||
|
|
||||||
public $notMapped;
|
public $notMapped;
|
||||||
}
|
}
|
||||||
|
@ -0,0 +1,84 @@
|
|||||||
|
<?php
|
||||||
|
|
||||||
|
/*
|
||||||
|
* This file is part of the Symfony package.
|
||||||
|
*
|
||||||
|
* (c) Fabien Potencier <fabien@symfony.com>
|
||||||
|
*
|
||||||
|
* For the full copyright and license information, please view the LICENSE
|
||||||
|
* file that was distributed with this source code.
|
||||||
|
*/
|
||||||
|
|
||||||
|
namespace Symfony\Bridge\Doctrine\Tests\PropertyInfo\Fixtures;
|
||||||
|
|
||||||
|
use Doctrine\DBAL\Platforms\AbstractPlatform;
|
||||||
|
use Doctrine\DBAL\Types\ConversionException;
|
||||||
|
use Doctrine\DBAL\Types\Type;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @author Teoh Han Hui <teohhanhui@gmail.com>
|
||||||
|
*/
|
||||||
|
class DoctrineFooType extends Type
|
||||||
|
{
|
||||||
|
/**
|
||||||
|
* Type name.
|
||||||
|
*/
|
||||||
|
const NAME = 'foo';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* {@inheritdoc}
|
||||||
|
*/
|
||||||
|
public function getName()
|
||||||
|
{
|
||||||
|
return self::NAME;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* {@inheritdoc}
|
||||||
|
*/
|
||||||
|
public function getSQLDeclaration(array $fieldDeclaration, AbstractPlatform $platform)
|
||||||
|
{
|
||||||
|
return $platform->getClobTypeDeclarationSQL(array());
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* {@inheritdoc}
|
||||||
|
*/
|
||||||
|
public function convertToDatabaseValue($value, AbstractPlatform $platform)
|
||||||
|
{
|
||||||
|
if (null === $value) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (!$value instanceof Foo) {
|
||||||
|
throw new ConversionException(sprintf('Expected %s, got %s', 'Symfony\Bridge\Doctrine\Tests\PropertyInfo\Fixtures\Foo', gettype($value)));
|
||||||
|
}
|
||||||
|
|
||||||
|
return $foo->bar;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* {@inheritdoc}
|
||||||
|
*/
|
||||||
|
public function convertToPHPValue($value, AbstractPlatform $platform)
|
||||||
|
{
|
||||||
|
if (null === $value) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (!is_string($value)) {
|
||||||
|
throw ConversionException::conversionFailed($value, self::NAME);
|
||||||
|
}
|
||||||
|
|
||||||
|
$foo = new Foo();
|
||||||
|
$foo->bar = $value;
|
||||||
|
|
||||||
|
return $foo;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* {@inheritdoc}
|
||||||
|
*/
|
||||||
|
public function requiresSQLCommentHint(AbstractPlatform $platform)
|
||||||
|
{
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,23 @@
|
|||||||
|
<?php
|
||||||
|
|
||||||
|
/*
|
||||||
|
* This file is part of the Symfony package.
|
||||||
|
*
|
||||||
|
* (c) Fabien Potencier <fabien@symfony.com>
|
||||||
|
*
|
||||||
|
* For the full copyright and license information, please view the LICENSE
|
||||||
|
* file that was distributed with this source code.
|
||||||
|
*/
|
||||||
|
|
||||||
|
namespace Symfony\Bridge\Doctrine\Tests\PropertyInfo\Fixtures;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @author Teoh Han Hui <teohhanhui@gmail.com>
|
||||||
|
*/
|
||||||
|
class Foo
|
||||||
|
{
|
||||||
|
/**
|
||||||
|
* @var string
|
||||||
|
*/
|
||||||
|
public $bar;
|
||||||
|
}
|
Reference in New Issue
Block a user