Saya mempunyai pertanyaan SQL ini yang melakukan apa yang saya mahu:
SELECT `Table1`.* FROM `Table1` LEFT JOIN `Table2` ON `Table1`.`idTable2` = `Table2`.`id` WHERE (`Table1`.`idOwner`=156 AND `Table2`.`enabled`=1 AND day(Table2.creationDate) <= 5 AND date_format(Table2.creationDate, '%Y-%m') = '2022-12') OR (`Table1`.`idOwner`=156 AND `Table2`.`enabled`=1 AND date_format(Table2.creationDate, '%Y-%m') != '2023-01' AND date_format(Table2.creationDate, '%Y-%m') != '2022-12')
Saya cuba menyalinnya sebagai pembina pertanyaan Yii seperti ini:
Table1::find() ->joinWith(['table2']) ->where(['Table1.idOwner' => $idOwner, 'Table2.enabled' => 1]) ->andWhere(['<=', 'day(Table2.creationDate)', $expirationDay]) ->andWhere(['=', "date_format(Table2.creationDate, '%Y-%m')", $previousExpirationMonthYear]) ->orWhere(['Table1.idOwner' => $idOwner, 'Table2.enabled' => 1]) ->andWhere(['!=', "date_format(Table2.creationDate, '%Y-%m')", $currentExpirationMonthYear]) ->andWhere(['!=', "date_format(Table2.creationDate, '%Y-%m')", $previousExpirationMonthYear]) ->all();
Tetapi saya mencetak SQL yang dijana oleh pembina pertanyaan ini menggunakan getRawSql()
dan ia kembali dengan cara yang pelik ini:
SELECT `Table1`.* FROM `Table1` LEFT JOIN `Table2` ON `Table1`.`idTable2` = `Table2`.`id` WHERE (((((((`Table1`.`idOwner`=156) AND (`Table2`.`enabled`=1)) AND (day(Table2.creationDate) <= 5)) AND (date_format(Table2.creationDate, '%Y-%m') = '2022-12')) OR ((`Table1`.`idOwner`=156) AND (`Table2`.`enabled`=1))) AND (date_format(Table2.creationDate, '%Y-%m') != '2023-01')) AND (date_format(Table2.creationDate, '%Y-%m') != '2022-12')) AND (`Table1`.`idOwner`='156')
Maaf jika ini sukar dibaca.
Bolehkah sesiapa membantu saya membuat pembina pertanyaan seperti yang saya mahukan? Saya akan bersyukur
Setiap kali anda menggunakan
andWhere()
或orWhere()
, pembina pertanyaan mengambil syarat sedia ada dan melakukan sesuatu seperti ini:atau
Masing-masing.
Jadi jika anda menghadapi situasi yang rumit, cuba hubungi
Anda akan dapat
Tetapi dalam kes anda, anda perlu mendapatkan sesuatu seperti:
Untuk mencapai hasil yang serupa, anda boleh membina keadaan kompleks pertama dengan cara yang sama, tetapi syarat kedua mesti dibina dalam satu panggilan
orWhere()
. Atau untuk menjadikannya lebih mudah dibaca, anda boleh membina dua keadaan kompleks secara berasingan dalam satu panggilan: