rak*_*ete 18 activerecord yii2
我有三个数据库表:
产品(id,名称)
product_has_adv(产品,优势,排序,重要)
优势(身份证,文字)
在ProductModel中我定义了这个:
public function getAdvantages()
{
return $this->hasMany(AdvantageModel::className(), ['id' => 'advantage'])
->viaTable('product_has_advantage', ['product' => 'id']);
}
Run Code Online (Sandbox Code Playgroud)
我毫无问题地获得了优势.
但是现在我需要添加一个product_has_advantage.important = 1 clausel,并通过product_has_advantage-table中的sort-columen对优势进行排序.
我如何以及在哪里实现它?
aro*_*hev 35
使用via和viaTable关系方法将导致两个单独的查询.
您可以在第三个参数中指定callable,如下所示:
public function getAdvantages()
{
return $this->hasMany(AdvantageModel::className(), ['id' => 'advantage'])
->viaTable('product_has_advantage', ['product' => 'id'], function ($query) {
/* @var $query \yii\db\ActiveQuery */
$query->andWhere(['important' => 1])
->orderBy(['sort' => SORT_DESC]);
});
}
Run Code Online (Sandbox Code Playgroud)
important将应用过滤器,但排序不会,因为它发生在第一个查询中.因此,IN语句中的ID顺序将被更改.
根据您的数据库逻辑,最好将列important和sort列移动到advantage表中.
然后只需添加条件并对现有方法链进行排序:
public function getAdvantages()
{
return $this->hasMany(AdvantageModel::className(), ['id' => 'advantage'])
->viaTable('product_has_advantage', ['product' => 'id'])
->andWhere(['important' => 1])
->orderBy(['sort' => SORT_DESC]);
}
Run Code Online (Sandbox Code Playgroud)
小智 5
仅供参考https://github.com/yiisoft/yii2/issues/10174列
几乎是不可能的ORDER BY viaTable()。对于 Yii 2.0.7,它从查询中返回 ID 集viaTable(),并且最终/顶部查询IN()子句忽略顺序。
小智 5
使用viaTable具有关系的方法将导致两个单独的查询,但是如果不需要link()方法,则可以按以下方式使用innerJoin按product_has_advantage表进行排序:
public function getAdvantages()
{
$query = AdvantageModel::find();
$query->multiple = true;
$query->innerJoin('product_has_advantage','product_has_advantage.advantage = advantage.id');
$query->andWhere(['product_has_advantage.product' => $this->id, 'product_has_advantage.important' => 1]);
$query->orderBy(['product_has_advantage.sort' => SORT_DESC]);
return $query;
}
Run Code Online (Sandbox Code Playgroud)
注意,$query->multiple = true因为Yii2具有hasMany关系,因此允许您使用此方法。
小智 5
对于一段时间后来到这里并且不喜欢上述解决方案的人,我通过在过滤器通过表之后连接回到通过表来使其工作。
上述代码示例:
public function getAdvantages()
{
return $this->hasMany(AdvantageModel::className(), ['id' => 'advantage'])
->viaTable('product_has_advantage', ['product' => 'id'])
->innerJoin('product_has_advantage','XXX')
->orderBy('product_has_advantage.YYY'=> SORT_ASC);
}
Run Code Online (Sandbox Code Playgroud)
请注意使用正确的连接路径更改 XXX,并使用正确的排序列更改 YYY。
| 归档时间: |
|
| 查看次数: |
29015 次 |
| 最近记录: |