錯誤方式一:
在mybatis的動態sql語句中使用<if>標簽可以判斷sql中的條件是否成立。
<select id="getPerson" resultType="com.lzj.bean.Employee">
select * from tbl_employee
where
<if test="id!=null">
id=#{id}
</if>
<if test="lastName!=null and lastName!=''">
and last_name like #{lastName}
</if>
<if test="email!=null and email.trim()!=''">
and email=#{email}
</if>
<if test="gender==0 or gender==1">
and gender=#{gender}
</if>
</select>
在上面的動態sql語句中存在一個問題,當第一條sql判斷語句
<if test="id!=null">
id=#{id}
</if>
失敗時,即id值為null,而lastName、email和gender判斷成功后,最后sql語句就會變為:
select * from tbl_employee where and last_name like #{lastName} and email=#{email} and gender=#{gender}
where后面多一個and,執行sql時會失敗。
改正方式一:
在where條件后面加了一條判斷1=1,然后在id的判斷后加上and關鍵字,這樣當下面if條件中的任何一個判斷失敗后,都不會影響整個sql語句。
<select id="getPerson" resultType="com.lzj.bean.Employee">
select * from tbl_employee
where 1=1
<if test="id!=null">
and id=#{id}
</if>
<if test="lastName!=null and lastName!=''">
and last_name like #{lastName}
</if>
<if test="email!=null and email.trim()!=''">
and email=#{email}
</if>
<if test="gender==0 or gender==1">
and gender=#{gender}
</if>
</select>
錯誤方式二:
有些人習慣在每個if判斷中的數據庫字段的后面加and關鍵字,例如
<select id="getPerson" resultType="com.lzj.bean.Employee">
select * from tbl_employee
where
<if test="id!=null">
id=#{id} and
</if>
<if test="lastName!=null and lastName!=''">
last_name like #{lastName} and
</if>
<if test="email!=null and email.trim()!=''">
email=#{email} and
</if>
<if test="gender==0 or gender==1">
gender=#{gender}
</if>
</select>
但是上述情況存在一個弊端,當最后一個if判斷gender失敗時,sql語句就變成了:
select * from tbl_employee where id=#{id} and last_name like #{lastName} and email=#{email} and
where條件的最后多一個and,sql語句執行的時候也會失敗。
改正方式二:
在最后一個if語句中庫表字段后加and關鍵字,然后在最后加1=1判斷
<select id="getPerson" resultType="com.lzj.bean.Employee">
select * from tbl_employee
where
<if test="id!=null">
id=#{id} and
</if>
<if test="lastName!=null and lastName!=''">
last_name like #{lastName} and
</if>
<if test="email!=null and email.trim()!=''">
email=#{email} and
</if>
<if test="gender==0 or gender==1">
gender=#{gender} and
</if>
1=1
</select>
建議方式:
用<where>和<if> 進行組合,當條件不成立時,if條件后的內容包括and也不會存在,因此不會對整個sql語句產生影響。注意and關鍵字要放在每個<if>語句中的庫表字段賦值的前面。因為,一旦判斷不成功,<where> 會把對應的and關鍵字去掉(還有or關鍵字)。
<select id="getPerson" resultType="com.lzj.bean.Employee">
select * from tbl_employee
<where>
<!-- test:判斷表達式(OGNL)
遇見特殊符號應該去寫轉義字符:&&、''等字符
-->
<if test="id!=null">
id=#{id}
</if>
<if test="lastName!=null and lastName!=''">
and last_name like #{lastName}
</if>
<if test="email!=null and email.trim()!=''">
and email=#{email}
</if>
<!-- ognl會進行字符串與數字的轉換判斷 "0"==0 -->
<if test="gender==0 or gender==1">
and gender=#{gender}
</if>
</where>
</select>
上述很多特殊字符可以寫成轉義的形式,例如
1
<select id="getEmpsByConditionIf" resultType="com.atguigu.mybatis.bean.Employee">
select * from tbl_employee
<!-- where -->
<where>
<if test="id!=null">
id=#{id}
</if>
<if test="lastName!=null && lastName!=""">
and last_name like #{lastName}
</if>
<if test="email!=null and email.trim()!=""">
and email=#{email}
</if>
<if test="gender==0 or gender==1">
and gender=#{gender}
</if>
</where>
</select>
注意,`<if>`失敗后, `<where>` 關鍵字只會去掉庫表字段賦值前面的and,不會去掉后面的and關鍵字,即注意,`<where>` 只會去掉`<if>` 語句中的最開始的and關鍵字。所以下面的形式是不可取的
<select id="getPerson" resultType="com.lzj.bean.Employee">
select * from tbl_employee
<where>
<if test="id!=null">
id=#{id} and
</if>
<if test="lastName!=null and lastName!=''">
last_name like #{lastName} and
</if>
<if test="email!=null and email.trim()!=''">
email=#{email} and
</if>
<if test="gender==0 or gender==1">
gender=#{gender}
</if>
</where>
</select>
``
因為,失敗后,`不會自動去掉后面的and關鍵字,這種形式與錯誤方式二種原理相同。
---------------------
作者:蒼鷹蛟龍
來源:CSDN
原文:https://blog.csdn.net/u010502101/article/details/79117000
版權聲明:本文為博主原創文章,轉載請附上博文鏈接!