How to solve symfony 3 error Expected argument of type "string", "yourBundle/Form/xformType" given


Are you implementing the new version of Symfony in your old symfony 2 project ? That's quite obvious in almost all the cases. We want to enjoy the latest features of symfony when we can, however is not always as simple as change your composer.json, run composer update and wait that everything works as a clock !

Upgrading will take more than that and you'll need to read carefully the new documentation of symfony 3 (read more about forms here). For now, let's solve this little issue :

Your controller

When you face this issue, your controller will probably look like this :

<?php
use yourBundle\Entity\MyClass;
use yourBundle\Form\MyClassType;

private function createCreateForm(MyClass $entity)
{
   $form = $this->createForm(new MyClass(), $entity, array(
       'action' => $this->generateUrl('myclass_create'),
       'method' => 'POST',
   ));

   return $form;
}

// and your edit with something like :

private function createEditForm(Projects $entity)
{
   $form = $this->createForm(new MyClass(), $entity, array(
        'action' => $this->generateUrl('projects_update', array('id' => $entity->getId())),
        'method' => 'PUT',
   ));

   return $form;
}

The error is pretty simple, you can't initialize directly createForm method with the first parameter as a new MyClass instance, instead we will call the static class property of the problem class like this :

<?php
use yourBundle\Entity\MyClass;
use yourBundle\Form\MyClassType;

private function createCreateForm(MyClass $entity)
{
   $form = $this->createForm(MyClassType::class, $entity, array(
       'action' => $this->generateUrl('myclass_create'),
       'method' => 'POST',
   ));

   return $form;
}

private function createEditForm(MyClass $entity)
{
   // Note the change of the first parameter of createForm
   $form = $this->createForm(MyClassType::class, $entity, array(
        'action' => $this->generateUrl('projects_update', array('id' => $entity->getId())),
        'method' => 'PUT',
   ));

   return $form;
}

Your formType

Your old formType may should look like :

namespace yourBundle\Form;

use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\FormBuilderInterface;
use Symfony\Component\OptionsResolver\OptionsResolverInterface;

class ProjectsType extends AbstractType
{
    /**
     * @param FormBuilderInterface $builder
     * @param array $options
     */
    public function buildForm(FormBuilderInterface $builder, array $options)
    {
        $builder
            ->add('name','text',array('attr' => array('class' => 'form-control')))
            ->add('number','number',array('attr' => array('class' => 'form-control')))
            ->add('date','date', array('widget'=>'single_text','format' => 'yyyy-MM-dd HH:mm','attr' => array('class' => 'form-control')))
            ->add('description','textarea',array('attr' => array('class' => 'form-control')))
        ;
    }
  /// other functions
}

As seen on the controller, the declaration type has changed in Symfony 3, to solve the problem we will change the second parameter of the ->add property in the builder for:

namespace yourBundle\Form;

use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\FormBuilderInterface;
use Symfony\Component\OptionsResolver\OptionsResolverInterface;

//Note that you need to include the typeClass of every type that you include
use Symfony\Component\Form\Extension\Core\Type\TextType;
use Symfony\Component\Form\Extension\Core\Type\TextareaType;
use Symfony\Component\Form\Extension\Core\Type\DateType;
use Symfony\Component\Form\Extension\Core\Type\NumberType;

class ProjectsType extends AbstractType
{
    /**
     * @param FormBuilderInterface $builder
     * @param array $options
     */
    public function buildForm(FormBuilderInterface $builder, array $options)
    {
        $builder
            ->add('name',TextType::class,array('attr' => array('class' => 'form-control')))
            ->add('number',NumberType::class,array('attr' => array('class' => 'form-control')))
            ->add('date',DateType::class, array('widget'=>'single_text','format' => 'yyyy-MM-dd HH:mm','attr' => array('class' => 'form-control')))
            ->add('description',TextareaType::class,array('attr' => array('class' => 'form-control')))
        ;
    }
  /// other functions
}

And that would be enough to solve that frustrating and little error, with Symfony 3 type names were removed. Instead of referencing types by name, you must reference them by their fully-qualified class name (FQCN) instead.

Have fun !

Become a more social person