在Yii中使用动态过滤器和动态连接执行搜索

时间:2014-07-31 13:01:44

标签: php mysql yii

我在执行查询时遇到问题并且找不到适合我情况的任何内容,所以这是我的方案。

我正在显示包含信息的dataTable,并且我可以应用多个过滤器。

到目前为止,这么好。 现在的问题是我必须实现像动态过滤器这样的东西,意思是:

  • 用户按下一个按钮,显示"添加过滤器"(他可以按下它 很多时候他想添加多个过滤器。)
  • 当他按下该按钮时,会出现一个 div 元素,其中包含2个元素。 下拉列表和输入框。
  • 用户可以在下拉列表中选择要搜索的字段 并在输入中写下他想要搜索的值。
  • 他按下"搜索"并执行查询。

让我们说,在下拉列表中,用户选择"公司"并且在搜索栏中他写了#34; foo bar"。

在控制器中,我检测到选项"公司"被选中了。问题是,"公司"我不在主表中搜索,例如,2个关系。因为也可以从该表中导出数据,所以我正在进行LEFT JOINS,但我正在设置对params的约束。

我已经尝试了多项事情,我现在正在:

//this initial query is always performed
$test_query = 'SELETC a.*
               FROM tableA a
               LEFT JOIN TableB b ON b.name = a.name
               ';
$whereTxt = "<some_other_where_conditions>"; 
$bindParam[':some_field'] = $_POST["field_value"] //this $_POST is here only for better understanding, I don't actualy have the untreated value here.


现在,如果&#34;公司&#34;在下拉列表中检测到过滤器:

if($company_filter){ 
  $test_query .= 'LEFT JOIN relation_table1 t1 ON a.team_id = t1.id
                  LEFT JOIN relation_table2 t2 ON t1.company_id = t2.id';
  $whereTxt .= " AND retaion_table2.company_name LIKE :company_name";
  $bindParam[':company_name'] = "% ".$_POST["company_name"]." %";
}

问题在这里 我怎么把这一切包起来?

我试过了:

$list = $this->getDBConnection()->createCommand($test_query)->where($whereTxt, $bindParam)->queryAll();

失败,在查询执行中甚至没有考虑where参数

如果尝试了其他变体,但结果相同,则params未绑定或查询失败。

理想情况下,我会:

        $list = $this->getDBConnection()->createCommand()
            ->select("a.*")
            ->from('tableA a')
            ->leftjoin('regular_join')
            ->leftJoin('other_regular_join')
            ->where($whereTxt, $bindParam)
            ->queryAll();

但是这样,我无法添加

->leftJoin(...)

动态核心?由于过滤器,用户可能/可能没有选择我真的必须使用。

TL;博士

使用getDBConnection() - &gt; createCommand()我需要动态插入 LeftJoins ,具体取决于用户在搜索过滤器中选择的内容,绑定其中< / em>参数和参数

我知道我想要达到的目标可能并不清楚,如果我无法让自己理解,那就道歉。

1 个答案:

答案 0 :(得分:0)

不知道为什么我这么困惑。

而不是绑定 where params ,我只是将 where 添加到查询本身,然后将值绑定到最后,最后得到如下内容:

$test_query= 'SELECT a.* FROM ....';

if($company_filter){ 
  $test_query .= 'LEFT JOIN relation_table1 t1 ON a.team_id = t1.id
                  LEFT JOIN relation_table2 t2 ON t1.company_id = t2.id';
  $whereTxt .= " AND relation_table2.company_name LIKE :company_name";
  $bindParam[':company_name'] = "%".$_POST["company_name"]."%";
}

$list = $this->getDBConnection()->createCommand($test_query." WHERE ".$whereTxt)->bindValues($bindParam)->queryAll();


另外,感谢dgtal@Yii forum