Question

Having the following code in the form:

        ->add('groups', 'model', array(
              'class' => 'FOS\UserBundle\Propel\Group',
              'required' => true,
              'multiple' => true,
              'expanded' => true,
              'query' => GroupQuery::create()->orderByName(),
          ))

This renders the checkboxes correctly, but does not set the defaultvalues. When I set "expanded => false", it becomes a select list, but then the default values are set correctly.. Bug in Symfony?

Was it helpful?

Solution

This is a bug when you use propel instead of doctrine.

I had the same problem as you and found out why it isnt working.
There is a function in vendor/symfony/symfony/src/Symfony/Component/Form/Extension/Core/ChoiceList/ChoiceList.php named getValuesForChoices.
This function compares 2 objects with '==='. In doctrine, this works but it returns false if you use Propel.

public function getValuesForChoices(array $choices)
{
    $choices = $this->fixChoices($choices);
    $values = array();

    foreach ($choices as $i => $givenChoice) {
        foreach ($this->choices as $j => $choice) {
            if ($choice === $givenChoice) {
                $values[$i] = $this->values[$j];
                unset($choices[$i]);

                if (0 === count($choices)) {
                    break 2;
                }
            }
        }
    }

    return $values;
}

This is the function where it fails. The comparing will fail because the objects has difference numbers example: It trys to compare this: object(Vendor\Bundle\Model\Tag)#506 object(Vendor\Bundle\Model\Tag)#397

NOTE: This is not a fix but a explain of the problem.

Whenever i use the propel function to check if the objects are equal, the checkboxes are filled:

public function getValuesForChoices(array $choices)
{
    $choices = $this->fixChoices($choices);
    $values = array();
    foreach ($choices as $i => $givenChoice) {

        foreach ($this->choices as $j => $choice) {

            if ($choice->equals($givenChoice)) {
                $values[$i] = $this->values[$j];
                unset($choices[$i]);

                if (0 === count($choices)) {
                    break 2;
                }
            }
        }
    }

    return $values;
}

Another interesting thing is the InstancePooling of propel.

From the documentation:
http://propelorm.org/Propel/documentation/03-basic-crud.html#propel-instance-pool

Propel keeps a list of the objects that you already retrieved in memory to avoid calling the same request twice in a PHP script. This list is called the instance pool, and is automatically populated from your past requests. The instance pool is consulted whenever searching for an object using its primary key via findPk or findOneById (which is an alias for the former).

However, i'm just a beginner and i don't know very much about propel and symfony, so i don't know why this isnt working.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top