[Form] Made validation of form children configurable. Set the option "cascade_validation" to true
if you need it.
This commit is contained in:
parent
efada56312
commit
0c70a410e5
@ -38,6 +38,7 @@ class FieldTypeValidatorExtension extends AbstractTypeExtension
|
||||
$builder
|
||||
->setAttribute('validation_groups', $options['validation_groups'])
|
||||
->setAttribute('validation_constraint', $options['validation_constraint'])
|
||||
->setAttribute('cascade_validation', $options['cascade_validation'])
|
||||
->addValidator(new DelegatingValidator($this->validator));
|
||||
}
|
||||
|
||||
@ -46,6 +47,7 @@ class FieldTypeValidatorExtension extends AbstractTypeExtension
|
||||
return array(
|
||||
'validation_groups' => null,
|
||||
'validation_constraint' => null,
|
||||
'cascade_validation' => false,
|
||||
);
|
||||
}
|
||||
|
||||
|
@ -127,6 +127,29 @@ class DelegatingValidator implements FormValidatorInterface
|
||||
}
|
||||
}
|
||||
|
||||
static public function validateFormChildren(FormInterface $form, ExecutionContext $context)
|
||||
{
|
||||
if ($form->getAttribute('cascade_validation')) {
|
||||
$propertyPath = $context->getPropertyPath();
|
||||
$graphWalker = $context->getGraphWalker();
|
||||
|
||||
// The Execute constraint is called on class level, so we need to
|
||||
// set the property manually
|
||||
$context->setCurrentProperty('children');
|
||||
|
||||
// Adjust the property path accordingly
|
||||
if (!empty($propertyPath)) {
|
||||
$propertyPath .= '.';
|
||||
}
|
||||
|
||||
$propertyPath .= 'children';
|
||||
|
||||
foreach (self::getFormValidationGroups($form) as $group) {
|
||||
$graphWalker->walkReference($form->getChildren(), $group, $propertyPath, true);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static protected function getFormValidationGroups(FormInterface $form)
|
||||
{
|
||||
$groups = null;
|
||||
|
@ -10,9 +10,10 @@
|
||||
<value>Symfony\Component\Form\Extension\Validator\Validator\DelegatingValidator</value>
|
||||
<value>validateFormData</value>
|
||||
</value>
|
||||
<value>
|
||||
<value>Symfony\Component\Form\Extension\Validator\Validator\DelegatingValidator</value>
|
||||
<value>validateFormChildren</value>
|
||||
</value>
|
||||
</constraint>
|
||||
<property name="children">
|
||||
<constraint name="Valid" />
|
||||
</property>
|
||||
</class>
|
||||
</constraint-mapping>
|
||||
|
@ -798,6 +798,81 @@ class DelegatingValidatorTest extends \PHPUnit_Framework_TestCase
|
||||
DelegatingValidator::validateFormData($form, $context);
|
||||
}
|
||||
|
||||
public function testValidateFormChildren()
|
||||
{
|
||||
$graphWalker = $this->getMockGraphWalker();
|
||||
$metadataFactory = $this->getMockMetadataFactory();
|
||||
$context = new ExecutionContext('Root', $graphWalker, $metadataFactory);
|
||||
$form = $this->getBuilder()
|
||||
->setAttribute('cascade_validation', true)
|
||||
->setAttribute('validation_groups', array('group1', 'group2'))
|
||||
->getForm();
|
||||
$form->add($this->getForm('firstName'));
|
||||
|
||||
$graphWalker->expects($this->at(0))
|
||||
->method('walkReference')
|
||||
->with($form->getChildren(), 'group1', 'children', true);
|
||||
$graphWalker->expects($this->at(1))
|
||||
->method('walkReference')
|
||||
->with($form->getChildren(), 'group2', 'children', true);
|
||||
|
||||
DelegatingValidator::validateFormChildren($form, $context);
|
||||
}
|
||||
|
||||
public function testValidateFormChildrenAppendsPropertyPath()
|
||||
{
|
||||
$graphWalker = $this->getMockGraphWalker();
|
||||
$metadataFactory = $this->getMockMetadataFactory();
|
||||
$context = new ExecutionContext('Root', $graphWalker, $metadataFactory);
|
||||
$context->setPropertyPath('path');
|
||||
$form = $this->getBuilder()
|
||||
->setAttribute('cascade_validation', true)
|
||||
->getForm();
|
||||
$form->add($this->getForm('firstName'));
|
||||
|
||||
$graphWalker->expects($this->once())
|
||||
->method('walkReference')
|
||||
->with($form->getChildren(), 'Default', 'path.children', true);
|
||||
|
||||
DelegatingValidator::validateFormChildren($form, $context);
|
||||
}
|
||||
|
||||
public function testValidateFormChildrenSetsCurrentPropertyToData()
|
||||
{
|
||||
$graphWalker = $this->getMockGraphWalker();
|
||||
$metadataFactory = $this->getMockMetadataFactory();
|
||||
$context = new ExecutionContext('Root', $graphWalker, $metadataFactory);
|
||||
$form = $this->getBuilder()
|
||||
->setAttribute('cascade_validation', true)
|
||||
->getForm();
|
||||
$form->add($this->getForm('firstName'));
|
||||
$test = $this;
|
||||
|
||||
$graphWalker->expects($this->once())
|
||||
->method('walkReference')
|
||||
->will($this->returnCallback(function () use ($context, $test) {
|
||||
$test->assertEquals('children', $context->getCurrentProperty());
|
||||
}));
|
||||
|
||||
DelegatingValidator::validateFormChildren($form, $context);
|
||||
}
|
||||
|
||||
public function testValidateFormChildrenDoesNothingIfDisabled()
|
||||
{
|
||||
$graphWalker = $this->getMockGraphWalker();
|
||||
$metadataFactory = $this->getMockMetadataFactory();
|
||||
$context = new ExecutionContext('Root', $graphWalker, $metadataFactory);
|
||||
$form = $this->getBuilder()
|
||||
->setAttribute('cascade_validation', false)
|
||||
->getForm();
|
||||
$form->add($this->getForm('firstName'));
|
||||
|
||||
$graphWalker->expects($this->never())
|
||||
->method('walkReference');
|
||||
|
||||
DelegatingValidator::validateFormChildren($form, $context);
|
||||
}
|
||||
|
||||
public function testValidateIgnoresNonRoot()
|
||||
{
|
||||
$form = $this->getMockForm();
|
||||
|
Reference in New Issue
Block a user