見出し画像

PHP:複数条件での検索結果をUNIONでつなぐ 

select * from kounyu where eventid=? AND cartno like ?

こうやって複数条件をつないでいくことはできるけど

たとえばこういう検索窓ってキーワードの中にどのテーブルのキーワードが入るのかがわからない。


まず愚直に場合分けするとこうなる


if(テキストフィールドと期間の両方に入力がある){

   ※if(購入IDの場合)else if (名前の場合)else if(ニックネームの場合)
}
if(テキストフィールドのみに入力がある){
   ※if(購入IDの場合)else if (名前の場合)else if(ニックネームの場合)
}else if(期間だけの場合){

}else(何も入力がない場合)

}

のだけど※のところで

イベントID:1
かつ
お客様ニックネーム:田中

っていう検索結果と

イベントID:1
かつ
お客様名:田中

が両方出てこないと正解じゃない。しかし

select * from kounyu where eventid=? AND (nickname like ? OR customername like? OR cartno like?)

これだと なんかだめで
論理はあっているはず
どこか書き間違えたか
けどこの書き方のままANDとORが増えていくと結局「期間」が条件に加わったときに優先順位がどうなっているかわからなくて破綻する(できるかもしれないけど時間かかりそう)

ということで

場合分けしてWHERE句を生成するというひともいたのだけど、
それもあとから見づらいと思い(bindValueのとこでまた場合分けになるし)

select * from kounyu where eventid=? AND cartno like ?
select * from kounyu where eventid=? AND customername like ?

上記二つの検索結果をつないで表示する(重複は省く)というのでUNIONというのが使えるということで

$search_word = htmlspecialchars($_POST['word']);
            $search ='%'.$search_word.'%';

            $sth ="select * from kounyu where eventid=? AND cartno like ? UNION select * from kounyu where eventid=? AND customername like ? UNION select * from kounyu where eventid=? AND customer like ? ORDER BY kounyu_id DESC;";
            $sql = $dbh->prepare($sth);
            $sql->bindValue(1,$dataevent[0]['id'],PDO::PARAM_INT);
            $sql->bindValue(2,$search,PDO::PARAM_STR);
            $sql->bindValue(3,$dataevent[0]['id'],PDO::PARAM_INT);
            $sql->bindValue(4,$search,PDO::PARAM_STR);
            $sql->bindValue(5,$dataevent[0]['id'],PDO::PARAM_INT);
            $sql->bindValue(6,$search,PDO::PARAM_STR);
            $sql->execute();

こうしたら思った通りの挙動になった

ただしORDERBY句は最後に一回だけ加える。UNIONする前に毎回やるとエラーになる。