Pull to refresh

Doctrine и сортировка для связи многие к одному

Reading time 2 min
Views 2.7K
Довольно давно использую связку Zend Framework и Doctrine и очень не хватало сортировки для коллекций получаемых по ссылке. Оказалось, что это легко реализовать.

Позже в одном из проектов, созданном компанией в которой я работаю, был найден подобный метод, но, увы, не ясно просочилось-ли это от разработчиков Doctrine или было создано в недрах моей команды. Смущает тот факт, что найденный фрагмент кода написан для СУБД, которая в нашей компании не используется.

Все манипуляции производились на версии 1.1.3, но должны принести плоды и при использовании более ранних версий Doctrine.

Метод заключается в правке единственного файла. Да, внесение модификаций в код сторонней библиотеки не есть гуд, но, к сожалению, на данный момент другого выхода не видно. Или я плохо искал?

Открываем файл Doctrine/Relation.php и находим место описания массива определений:

protected $definition = array(… );

Добавляем еще одну пару ключ/значение:

'order' => null,

Это необходимо по причине того, что Doctrine именно на базе этого массива составляет список передаваемых в свои классы определений, указанных при формировании связей.

Находим определение функции getRelationDql и добавляем туда код для реализации сортировки. Таким образом функция будет иметь следующий вид:

public function getRelationDql($count)
{
    $component = $this->getTable()->getComponentName();

    $dql  = 'FROM ' . $component
          . ' WHERE ' . $component . '.' . $this->definition['foreign']
          . ' IN (' . substr(str_repeat('?, ', $count), 0, -2) . ')';

    if (!empty($this->definition['order']))
    {
        $dql .= ' ORDER BY ' . $this->definition['order'];
    }

    return $dql;
}

Т.е. мы указываем необходимость сортировки в случае, если это определено в описании связи. Именно в этом фрагменте кода ORDER BY может принимать другие формы для разных диалектов SQL.

Осталось в определении связи задать сортировку:

$this->hasMany('Products', array('local'=>'id','foreign'=>'category_id', 'order'=>'position desc'));

Таким образом происходит сортировка коллекций для связи многие к одному, что и требовалось получить. Надеюсь, что статья будет кому-то полезна.
Tags:
Hubs:
+15
Comments 19
Comments Comments 19

Articles