[Form] ChoiceType: Fix a notice when 'choices' normalizer is replaced

This commit is contained in:
Paráda József 2016-01-17 01:29:59 +01:00 committed by Fabien Potencier
parent ab43f389e2
commit be056fd0bf
3 changed files with 82 additions and 0 deletions

View File

@ -291,6 +291,10 @@ class ChoiceType extends AbstractType
// forms)
$labels = $choiceLabels->labels;
// The $choiceLabels object is shared with the 'choices' closure.
// Since that normalizer can be replaced, labels have to be cleared here.
$choiceLabels->labels = array();
return function ($choice, $key) use ($labels) {
return $labels[$key];
};

View File

@ -14,6 +14,7 @@ namespace Symfony\Component\Form\Tests\Extension\Core\Type;
use Symfony\Component\Form\ChoiceList\View\ChoiceGroupView;
use Symfony\Component\Form\ChoiceList\View\ChoiceView;
use Symfony\Component\Form\Extension\Core\ChoiceList\ObjectChoiceList;
use Symfony\Component\Form\Tests\Fixtures\ChoiceSubType;
class ChoiceTypeTest extends \Symfony\Component\Form\Test\TypeTestCase
{
@ -1887,4 +1888,30 @@ class ChoiceTypeTest extends \Symfony\Component\Form\Test\TypeTestCase
// Trigger data initialization
$form->getViewData();
}
/**
* This covers the case when:
* - Custom choice type added after a choice type.
* - Custom type is expanded.
* - Custom type replaces 'choices' normalizer with a custom one.
* In this case, custom type should not inherit labels from the first added choice type.
*/
public function testCustomChoiceTypeDoesNotInheritChoiceLabels()
{
$builder = $this->factory->createBuilder();
$builder->add('choice', 'choice', array(
'choices' => array(
'1' => '1',
'2' => '2',
),
)
);
$builder->add('subChoice', new ChoiceSubType());
$form = $builder->getForm();
// The default 'choices' normalizer would fill the $choiceLabels, but it has been replaced
// in the custom choice type, so $choiceLabels->labels remains empty array.
// In this case the 'choice_label' closure returns null and not the closure from the first choice type.
$this->assertNull($form->get('subChoice')->getConfig()->getOption('choice_label'));
}
}

View File

@ -0,0 +1,51 @@
<?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\Component\Form\Tests\Fixtures;
use Symfony\Component\Form\AbstractType;
use Symfony\Component\OptionsResolver\OptionsResolver;
/**
* @author Paráda József <joczy.parada@gmail.com>
*/
class ChoiceSubType extends AbstractType
{
/**
* {@inheritdoc}
*/
public function configureOptions(OptionsResolver $resolver)
{
$resolver->setDefaults(array('expanded' => true));
$resolver->setNormalizer('choices', function () {
return array(
'attr1' => 'Attribute 1',
'attr2' => 'Attribute 2',
);
});
}
/**
* {@inheritdoc}
*/
public function getName()
{
return 'sub_choice';
}
/**
* {@inheritdoc}
*/
public function getParent()
{
return 'choice';
}
}