【问题标题】:Yii2 Model ViaTableYii2 模型 ViaTable
【发布时间】:2018-07-21 01:59:30
【问题描述】:

为简单起见,假设我有 3 个表:menupage 和一个联结表 menu_page

因此,如果我想获取页面“主页”可用的所有菜单,我在模型中定义了一个关系:

public function getAllMenus() {
    return $this->hasMany(Menu::className(), ['id' => 'menu_id'])->viaTable(PageMenu::tableName(), ['page_id' => 'id']);
}

但是现在我们在菜单表中添加了一个名为show_all_pages的属性,如果设置为1,则应该返回菜单,否则我们应该检查菜单是否可以在主页上使用。

有没有办法在这里添加这个条件?

【问题讨论】:

  • 您希望它全局集成到关系中还是任何特定的controlleraction 都需要它?
  • 在关系中
  • 下面的答案应该可以工作

标签: php yii2 yii2-model


【解决方案1】:

您可以使用andWhere 子句将此过滤器应用于show_all_pages

public function getAllMenus() {
    return $this->hasMany(Menu::className(), ['id' => 'menu_id'])
                ->viaTable(PageMenu::tableName(), ['page_id' => 'id'])
                ->andWhere(['show_all_pages' => 1]);
}

【讨论】:

  • 如果我理解正确,您将在已经与 pagemenu 连接的查询上添加一个额外的条件。这个想法是菜单可以有字段 show_all_pages 但在 pagemenu 表上没有记录。
  • @Eduardo “您正在为已经与 pagemenu 连接的查询添加一个额外的条件” - 这是正确的,但是我不明白您评论的下一部分,但实际上这 @ 987654325@ 用于将show_all_pages = 1 添加到生成的sql 的WHERE 子句中
  • 我的情况我需要或者使用viaTable或者show_all_pages属性条件做join,都不能应用。
【解决方案2】:

到目前为止我发现的解决方案是分离 Active Queries 并做一个 Union:

public function getSelectedMenus() {

        return $this->hasMany(Menu::className(), ['id' => 'menu_id'])->viaTable(PageMenu::tableName(), ['page_id' => 'id'])->onCondition(['menu.active' => Page::ACTIVE]);
    }

    public function getAllMenus() {
        return Menu::find()->where(['active' => Page::ACTIVE, 'show_all_pages' => 1]);
    }

    public function getMenus() {

        $selectedMenus = $this->getSelectedMenus();
        $allMenus = $this->getAllMenus();

        return $selectedMenus->union($allMenus);

    }

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多