Hari K T Hari K T - 7 days ago 4
PHP Question

How to make Symfony2 form optional field not null on save

I have an image field which is optional. When you upload image, it will save the filename on the database (using events via doctrine ).

The problem is when you edit an already uploaded form and don't add an image, it makes the image field to null.

Is there a way to check / remove the field value setting to null if no image is uploaded?

The Entity, Form code is as below :

class Product
{

/**
* @ORM\Column(type="string", nullable=true)
*
* @Assert\Image
*/
private $image;
}


Form

class ProductType extends AbstractType
{
public function buildForm(FormBuilderInterface $builder, array $options)
{
$builder->add('image', FileType::class, [
'required' => !$options['update'],
]);

$builder->addEventListener(FormEvents::PRE_SET_DATA, function (FormEvent $event) {
$form = $event->getForm();
$product = $event->getData();

if (null == $form->get('image')->getData()) {
// $form->remove('image');
}
});
}

public function configureOptions(OptionsResolver $resolver)
{
$resolver->setDefaults(array(
'data_class' => 'AppBundle\Entity\Product'
));
}

public function getBlockPrefix()
{
return 'appbundle_product';
}

public function setDefaultOptions(OptionsResolverInterface $resolver)
{
$resolver->setRequired([
'update',
]);
}
}


// In controller

$editForm = $this->createForm(
'AppBundle\Form\ProductType',
$product,
[
'update' => true
]
);

Answer

You need the event PRE_SUBMIT, try this:

public function buildForm(FormBuilderInterface $builder, array $options)
{
    $builder->add('image', FileType::class, [
        'required' => !$options['update'],
    ]);

    $builder->addEventListener(FormEvents::PRE_SUBMIT, function (FormEvent $event) {
        $form = $event->getForm();
        $product = $event->getData();

        if(empty($product['image'])){
            //No new image for existing field was given. Make field disabled so doctrine will not update with empty
            $config = $event->getForm()->get('image')->getConfig();
            $options = $config->getOptions();
            $event->getForm()->add(
                'image',
                $config->getType()->getName(),
                array_replace(
                    $options,
                    ['disabled' => true]
                )
            );
        }
    });
}