ZF2 Doctrine 2 ObjectSelect with distinct on field

2019-02-20 16:59发布

问题:

to populate my form I use the fieldset approach. For one given form field I will use a select and the options are coming directly from an entity like this:

$this->add(
            array(
                'type' => 'DoctrineModule\Form\Element\ObjectSelect',
                'name' => 'city',
                'options' => array(
                    'label' => 'City: ',
                    'object_manager' => $this->_om,
                    'target_class' => 'Hotbed\Entity\AllAdresses',
                    'property' => 'city',
                    'is_method' => true,
                    'find_method' => array(
                        'name' => 'findBy',
                        'params' => array(
                            'criteria' => array('postal_code' => $postalCode),
                            'orderBy' => array('city' => 'ASC'),
                        ),
                    ),
                ),
                'attributes' => array(
                    'class' => 'form-control input-large',
                    'required' => '*'
                ),
            )
    );

This works pretty well. The only inconvient is that I have to put a distinct on the field city. How can I solve this problem? Regards Andrea

回答1:

The way I got around this was to create a function in the repository to return the distinct entities, and then specify that function name in your form element.

So in your case, for example:

In your repository:

public function findDistinctCitiesByPostalCode($postalCode) {
    $dql = "SELECT DISTINCT a.city "
         . "FROM Hotbed\Entity\AllAdresses a "
         . "WHERE a.postalCode :postalCode";

    $qry = $this->getEntityManager()->createQuery($dql);
    $qry->setParameter('postalCode', $postalCode);

    $results = $qry->getArrayResult(); 

    // $results will be an array in the format 
    // array(array('city' => 'city_1'), array('city' => 'city_1'),....)
    // so you'll need to loop through and create an array of entities
    foreach ($results as $row) {
        $addresses[] = new Hotbed\Entity\AllAdresses(array('city' => $row['city']);
    }

    return $addresses;        
}

And then in your form:

$this->add(
        array(
            'type' => 'DoctrineModule\Form\Element\ObjectSelect',
            'name' => 'city',
            'options' => array(
                'label' => 'City: ',
                'object_manager' => $this->_om,
                'target_class' => 'Hotbed\Entity\AllAdresses',
                'property' => 'city',
                'is_method' => true,
                'find_method' => array(
                    'name' => 'findDistinctCitiesByPostalCode'
                )
            )
        )
);