У меня есть 2 таблицы (слайдеры, изображения), связанные с таблицей junction (sliders_images), отношение работает нормально, но я недд для получения связанных данных с определенным порядком, атрибут, который определяет правильный порядок, находится в таблице соединений, отношение определено в виде:
public function getImages(){ return $this->hasMany(Images::className(), ['id' => 'image_id']) ->viaTable('sliders_images', ['slider_id' => 'id'], function($query){ $query->orderBy('sliders_images.display_order ASC'); }); }
когда я вызываю $model->images
я получаю правильные изображения, но неправильный порядок, используя foreach, изображения были упорядочены по id, как я могу получить изображения, упорядоченные по другому атрибуту?
Правильный способ – добавить соединение с таблицей соединений ->joinWith('slidersImages')
для получения атрибутов таблицы соединений, а затем упорядочить по одному из них. Полный код:
public function getImages(){ return $this->hasMany(Images::className(), ['id' => 'image_id']) ->via('slidersImages') ->joinWith('slidersImages SI') ->orderBy('SI.display_order ASC'); }
В этом случае orderBy
будет применен к первому запросу ( SELECT * FROM sliders_images ...
), поэтому, если вы проверите сгенерированный sql:
echo $model->getImages()->createCommad()->rawSql;
то вы увидите что-то вроде этого
SELECT * FROM images WHERE id IN (4, 2, 3, 1)
и здесь будет правильный порядок. Но в результате набора вы получили порядок по id (1, 2, 3, 4).
Поэтому, чтобы получить правильный заказ, вы должны добавить желаемый orderBy
на свой hasMany
:
public function getImages(){ return $this->hasMany(Images::className(), ['id' => 'image_id']) ->viaTable('sliders_images', ['slider_id' => 'id']) ->orderBy(['images.display_order' => SORT_ASC]); }
Связанная тема: ActiveRecord где и порядок по таблице