MyBatis 示例-動態 SQL

MyBatis 的動態 SQL 包括以下幾種元素:

 

詳細的使用參考官網文檔:http://www.mybatis.org/mybatis-3/zh/dynamic-sql.html

本章內容簡單描述這些動態 SQL 在使用的過程中需要注意的地方。

choose, when, otherwise

比如我們要實現如下功能:

  • 當學生姓名不爲空,則只用學生姓名作爲條件查詢
  • 當學生性別不爲空,則只用學生性別作爲條件查詢
  • 當學生姓名和學生性別都爲空,則要求學生學生證件號不爲空

針對這種情況,MyBatis 提供了 choose 元素,它有點像 Java 中的 switch 語句。

<select id="listByConditions" parameterType="studentQuery" resultMap="BaseResultMap">
    select
    <include refid="Base_Column_List" />
    from t_student
    <where>
        <choose>
            <when test="name != null and name != ''">
                AND name LIKE CONCAT('%', #{name}, '%')
            </when>
            <when test="sex != null">
                AND sex = #{sex}
            </when>
            <otherwise>
                AND selfcard_no is not null
            </otherwise>
        </choose>
    </where>
</select>

trim, where, set

比如下面的動態 SQL 有什麼問題?

<select id="listByConditions" parameterType="studentQuery" resultMap="BaseResultMap">
    SELECT id, name, sex, selfcard_no, note
    FROM t_student
    WHERE
    <if test="ids != null and ids.size() > 0">
      id IN
      <foreach collection="ids" item="item" open="(" close=")" separator=",">
        #{item}
      </foreach>
    </if>
    <if test="name != null and name != ''">
      AND name LIKE CONCAT('%', #{name}, '%')
    </if>
    <if test="sex != null">
      AND sex = #{sex}
    </if>
    <if test="selfcardNo != null">
      AND selfcard_no = #{selfcardNo}
    </if>
</select>

如果這些條件沒有一個能匹配上會發生什麼?最終這條 SQL 會變成這樣:

SELECT id, name, sex, selfcard_no, note
FROM t_student
WHERE

這樣會導致 SQL 語句執行失敗。如果僅僅第二個條件匹配又會怎樣?這條 SQL 最終會是這樣:

SELECT id, name, sex, selfcard_no, note
FROM t_student
WHERE
AND name LIKE CONCAT('%', 'a', '%')

這個查詢也會失敗。

MyBatis 提供了 <where> 元素可以解決上面的問題,將上面的動態 SQL 改成如下形式。

<select id="listByConditions" parameterType="studentQuery" resultMap="BaseResultMap">
    SELECT id, name, sex, selfcard_no, note
    FROM t_student
    <where>
        <if test="ids != null and ids.size() > 0">
            AND id IN
            <foreach collection="ids" item="item" open="(" close=")" separator=",">
                #{item}
            </foreach>
        </if>
        <if test="name != null and name != ''">
            AND name LIKE CONCAT('%', #{name}, '%')
        </if>
        <if test="sex != null">
            AND sex = #{sex}
        </if>
        <if test="selfcardNo != null">
            AND selfcard_no = #{selfcardNo}
        </if>
    </where>
</select>

foreach

實現批量新增功能,動態 SQL 如下:

<insert id="batchInsertByNoAutoInc" parameterType="list">
    <selectKey keyProperty="id" resultType="long" order="BEFORE">
        select if(max(id) is null, 1, max(id) + 2) as newId from t_student
    </selectKey>
    insert into t_student (name, sex, selfcard_no, note)
    values
    <foreach collection="list" item="item" index="index" separator=",">
        (
        #{item.name,jdbcType=VARCHAR},
        #{item.sex,jdbcType=TINYINT},
        #{item.selfcardNo,jdbcType=BIGINT},
        #{item.note,jdbcType=VARCHAR}
        )
    </foreach>
</insert>

批量新增的操作需要確保 list 中必須有值。

 

MyBatis 實用篇

MyBatis 概念

MyBatis 示例-簡介

MyBatis 示例-類型處理器

MyBatis 示例-傳遞多個參數

MyBatis 示例-主鍵回填

MyBatis 示例-動態 SQL

MyBatis 示例-聯合查詢

MyBatis 示例-緩存

MyBatis 示例-插件

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章