Skip to content

Commit 169b397

Browse files
committed
check for the correct field type
HTML allow to define different form fields with the same name. Imagine the following form: <html> <body> <form action="/"> <input type="hidden" name="option" value="default"> <input type="radio" name="option" value="A"> <input type="radio" name="option" value="B"> <input type="hidden" name="settings[1]" value="0"> <input type="checkbox" name="settings[1]" value="1" id="setting-1"> <button>klickme</button> </form> </body> </html> Since the `FormFieldRegistry` can only handle one field per name, the hidden field option is registered first before the radio field with the same name is evaluated. Thus, the `FormFieldRegistry` returns an `InputFormField` instance on which the `addChoices()` method can not be called.
1 parent 65862c9 commit 169b397

File tree

2 files changed

+26
-1
lines changed

2 files changed

+26
-1
lines changed

src/Symfony/Component/DomCrawler/Form.php

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@
1111

1212
namespace Symfony\Component\DomCrawler;
1313

14+
use Symfony\Component\DomCrawler\Field\ChoiceFormField;
1415
use Symfony\Component\DomCrawler\Field\FormField;
1516

1617
/**
@@ -444,7 +445,9 @@ private function addField(\DOMNode $node)
444445
if ('select' == $nodeName || 'input' == $nodeName && 'checkbox' == strtolower($node->getAttribute('type'))) {
445446
$this->set(new Field\ChoiceFormField($node));
446447
} elseif ('input' == $nodeName && 'radio' == strtolower($node->getAttribute('type'))) {
447-
if ($this->has($node->getAttribute('name'))) {
448+
// there may be other fields with the same name that are no choice
449+
// fields already registered (see https://github.com/symfony/symfony/issues/11689)
450+
if ($this->has($node->getAttribute('name')) && $this->get($node->getAttribute('name')) instanceof ChoiceFormField) {
448451
$this->get($node->getAttribute('name'))->addChoice($node);
449452
} else {
450453
$this->set(new Field\ChoiceFormField($node));

src/Symfony/Component/DomCrawler/Tests/FormTest.php

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -782,6 +782,28 @@ public function testFormRegistrySetValues()
782782
));
783783
}
784784

785+
public function testDifferentFieldTypesWithSameName()
786+
{
787+
$dom = new \DOMDocument();
788+
$dom->loadHTML('
789+
<html>
790+
<body>
791+
<form action="/">
792+
<input type="hidden" name="option" value="default">
793+
<input type="radio" name="option" value="A">
794+
<input type="radio" name="option" value="B">
795+
<input type="hidden" name="settings[1]" value="0">
796+
<input type="checkbox" name="settings[1]" value="1" id="setting-1">
797+
<button>klickme</button>
798+
</form>
799+
</body>
800+
</html>
801+
');
802+
$form = new Form($dom->getElementsByTagName('form')->item(0), 'http://example.com');
803+
804+
$this->assertInstanceOf('Symfony\Component\DomCrawler\Field\ChoiceFormField', $form->get('option'));
805+
}
806+
785807
protected function getFormFieldMock($name, $value = null)
786808
{
787809
$field = $this

0 commit comments

Comments
 (0)