Bladeren bron

[Form] Added option 'data' to Field for populating a field with a fixed value

Bernhard Schussek 14 jaren geleden
bovenliggende
commit
e5ed98c324

+ 12 - 1
src/Symfony/Component/Form/Field.php

@@ -65,6 +65,7 @@ class Field extends Configurable implements FieldInterface
 
     public function __construct($key = null, array $options = array())
     {
+        $this->addOption('data');
         $this->addOption('trim', true);
         $this->addOption('required', true);
         $this->addOption('disabled', false);
@@ -74,6 +75,14 @@ class Field extends Configurable implements FieldInterface
 
         $this->key = (string)$key;
 
+        if (isset($options['data'])) {
+            // Populate the field with fixed data
+            // Set the property path to NULL so that the data is not
+            // overwritten by the form's data
+            $this->setData($options['data']);
+            $this->setPropertyPath(null);
+        }
+
         parent::__construct($options);
 
         if ($this->getOption('value_transformer')) {
@@ -87,7 +96,9 @@ class Field extends Configurable implements FieldInterface
         $this->normalizedData = $this->normalize($this->data);
         $this->transformedData = $this->transform($this->normalizedData);
 
-        $this->setPropertyPath($this->getOption('property_path'));
+        if (!$this->getOption('data')) {
+            $this->setPropertyPath($this->getOption('property_path'));
+        }
     }
 
     /**

+ 4 - 12
src/Symfony/Component/Form/Form.php

@@ -73,12 +73,6 @@ class Form extends Field implements \IteratorAggregate, FormInterface
 
         parent::__construct($name, $options);
 
-        // If data is passed to this constructor, objects from parent forms
-        // should be ignored
-//        if (null !== $data) {
-//            $this->setPropertyPath(null);
-//        }
-
         // Enable CSRF protection, if necessary
         // TODO only in root form
         if ($this->getOption('csrf_provider')) {
@@ -86,14 +80,12 @@ class Form extends Field implements \IteratorAggregate, FormInterface
                 throw new FormException('The object passed to the "csrf_provider" option must implement CsrfProviderInterface');
             }
 
+            $fieldName = $this->getOption('csrf_field_name');
             $token = $this->getOption('csrf_provider')->generateCsrfToken(get_class($this));
 
-            $field = new HiddenField($this->getOption('csrf_field_name'), array(
-                'property_path' => null,
-            ));
-            $field->setData($token);
-
-            $this->add($field);
+            $this->add(new HiddenField($fieldName, array(
+                'data' => $token,
+            )));
         }
     }
 

+ 2 - 4
src/Symfony/Component/Form/FormContext.php

@@ -130,9 +130,10 @@ class FormContext implements FormContextInterface
      */
     public function getForm($name, $data = null)
     {
-        $form = new Form(
+        return new Form(
             $name,
             array(
+                'data' => $data,
                 'validator' => $this->validator,
                 'csrf_field_name' => $this->csrfFieldName,
                 'csrf_provider' => $this->csrfProtection ? $this->csrfProvider : null,
@@ -140,9 +141,6 @@ class FormContext implements FormContextInterface
                 'field_factory' => $this->fieldFactory,
             )
         );
-        $form->setData($data);
-
-        return $form;
     }
 
     /**

+ 18 - 1
tests/Symfony/Tests/Component/Form/FieldTest.php

@@ -19,7 +19,7 @@ require_once __DIR__ . '/Fixtures/RequiredOptionsField.php';
 use Symfony\Component\Form\ValueTransformer\ValueTransformerInterface;
 use Symfony\Component\Form\PropertyPath;
 use Symfony\Component\Form\FieldError;
-use Symfony\Component\Form\FormContext;
+use Symfony\Component\Form\Form;
 use Symfony\Component\Form\ValueTransformer\TransformationFailedException;
 use Symfony\Tests\Component\Form\Fixtures\Author;
 use Symfony\Tests\Component\Form\Fixtures\TestField;
@@ -489,6 +489,23 @@ class FieldTest extends \PHPUnit_Framework_TestCase
         $this->assertEquals('ROOT', $this->field->getRoot());
     }
 
+    public function testFieldsInitializedWithDataAreNotUpdatedWhenAddedToForms()
+    {
+        $author = new Author();
+        $author->firstName = 'Bernhard';
+
+        $field = new TestField('firstName', array(
+            'data' => 'foobar',
+        ));
+
+        $form = new Form('author', array(
+            'data' => $author,
+        ));
+        $form->add($field);
+
+        $this->assertEquals('foobar', $field->getData());
+    }
+
     public function testGetRootReturnsFieldIfNoParent()
     {
         $this->assertEquals($this->field, $this->field->getRoot());