feature #19790 [FrameworkBundle] add support for prioritizing form type extension tags (dmaicher)

This PR was merged into the 3.2-dev branch.

Discussion
----------

[FrameworkBundle] add support for prioritizing form type extension tags

| Q             | A
| ------------- | ---
| Branch?       | "master"
| Bug fix?      | no
| New feature?  | yes
| BC breaks?    | no
| Deprecations? | no
| Tests pass?   | yes
| Fixed tickets | #19735
| License       | MIT
| Doc PR        | https://github.com/symfony/symfony-docs/pull/6958

This PR proposes to add support for `priority` on `form.type_extension` dependecyinjection tags to enable sorting/prioritizing form type extensions.

Issue was mentioned here: https://github.com/symfony/symfony/issues/19735

Commits
-------

a3db5f0 [FrameworkBundle] add support for prioritizing form type extension tags
This commit is contained in:
Fabien Potencier 2016-09-14 14:07:36 -07:00
commit 3416f2128d
3 changed files with 47 additions and 15 deletions

View File

@ -6,6 +6,7 @@ CHANGELOG
* The `Controller::getUser()` method has been deprecated and will be removed in
Symfony 4.0; typehint the security user object in the action instead.
* Added possibility to prioritize form type extensions with `'priority'` attribute on tags `form.type_extension`
3.1.0
-----

View File

@ -11,6 +11,7 @@
namespace Symfony\Bundle\FrameworkBundle\DependencyInjection\Compiler;
use Symfony\Component\DependencyInjection\Compiler\PriorityTaggedServiceTrait;
use Symfony\Component\DependencyInjection\ContainerBuilder;
use Symfony\Component\DependencyInjection\Compiler\CompilerPassInterface;
use Symfony\Component\DependencyInjection\Exception\InvalidArgumentException;
@ -23,6 +24,8 @@ use Symfony\Component\DependencyInjection\Exception\InvalidArgumentException;
*/
class FormPass implements CompilerPassInterface
{
use PriorityTaggedServiceTrait;
public function process(ContainerBuilder $container)
{
if (!$container->hasDefinition('form.extension')) {
@ -48,12 +51,14 @@ class FormPass implements CompilerPassInterface
$typeExtensions = array();
foreach ($container->findTaggedServiceIds('form.type_extension') as $serviceId => $tag) {
foreach ($this->findAndSortTaggedServices('form.type_extension', $container) as $reference) {
$serviceId = (string) $reference;
$serviceDefinition = $container->getDefinition($serviceId);
if (!$serviceDefinition->isPublic()) {
throw new InvalidArgumentException(sprintf('The service "%s" must be public as form type extensions are lazy-loaded.', $serviceId));
}
$tag = $serviceDefinition->getTag('form.type_extension');
if (isset($tag[0]['extended_type'])) {
$extendedType = $tag[0]['extended_type'];
} else {

View File

@ -59,7 +59,10 @@ class FormPassTest extends \PHPUnit_Framework_TestCase
), $extDefinition->getArgument(1));
}
public function testAddTaggedTypeExtensions()
/**
* @dataProvider addTaggedTypeExtensionsDataProvider
*/
public function testAddTaggedTypeExtensions(array $extensions, array $expectedRegisteredExtensions)
{
$container = new ContainerBuilder();
$container->addCompilerPass(new FormPass());
@ -72,26 +75,49 @@ class FormPassTest extends \PHPUnit_Framework_TestCase
));
$container->setDefinition('form.extension', $extDefinition);
$container->register('my.type_extension1', 'stdClass')
->addTag('form.type_extension', array('extended_type' => 'type1'));
$container->register('my.type_extension2', 'stdClass')
->addTag('form.type_extension', array('extended_type' => 'type1'));
$container->register('my.type_extension3', 'stdClass')
->addTag('form.type_extension', array('extended_type' => 'type2'));
foreach ($extensions as $serviceId => $tag) {
$container->register($serviceId, 'stdClass')->addTag('form.type_extension', $tag);
}
$container->compile();
$extDefinition = $container->getDefinition('form.extension');
$this->assertSame($expectedRegisteredExtensions, $extDefinition->getArgument(2));
}
$this->assertSame(array(
'type1' => array(
'my.type_extension1',
'my.type_extension2',
/**
* @return array
*/
public function addTaggedTypeExtensionsDataProvider()
{
return array(
array(
array(
'my.type_extension1' => array('extended_type' => 'type1'),
'my.type_extension2' => array('extended_type' => 'type1'),
'my.type_extension3' => array('extended_type' => 'type2'),
),
array(
'type1' => array('my.type_extension1', 'my.type_extension2'),
'type2' => array('my.type_extension3'),
),
),
'type2' => array(
'my.type_extension3',
array(
array(
'my.type_extension1' => array('extended_type' => 'type1', 'priority' => 1),
'my.type_extension2' => array('extended_type' => 'type1', 'priority' => 2),
'my.type_extension3' => array('extended_type' => 'type1', 'priority' => -1),
'my.type_extension4' => array('extended_type' => 'type2', 'priority' => 2),
'my.type_extension5' => array('extended_type' => 'type2', 'priority' => 1),
'my.type_extension6' => array('extended_type' => 'type2', 'priority' => 1),
),
array(
'type1' => array('my.type_extension2', 'my.type_extension1', 'my.type_extension3'),
'type2' => array('my.type_extension4', 'my.type_extension5', 'my.type_extension6'),
),
),
), $extDefinition->getArgument(2));
);
}
/**