MyBatis 真正的力量是在映射語句中。這里是奇跡發生的地方。 對於所有的力量, SQL
映射的 XML 文件是相當的簡單。當然如果你將它們和對等功能的 JDBC 代碼來比較,你會
發現映射文件節省了大約 95%的代碼量。 MyBatis 的構建就是聚焦於 SQL 的,使其遠離於
普通的方式。
SQL 映射文件有很少的幾個頂級元素(
按照它們應該被定義的順序):
cache - 配置給定命名空間的緩存。
cache-ref – 從其他命名空間引用緩存配置。
resultMap – 最復雜,也是最有力量的元素,用來描述如何從數據庫結果集中來加載你的對象。
cache - 配置給定命名空間的緩存。
cache-ref – 從其他命名空間引用緩存配置。
resultMap – 最復雜,也是最有力量的元素,用來描述如何從數據庫結果集中來加載你的對象。
sql – 可以重用的 SQL 塊,也可以被其他語句引用。
insert – 映射插入語句
update – 映射更新語句
delete – 映射刪除語句
select – 映射查詢語句
insert – 映射插入語句
update – 映射更新語句
delete – 映射刪除語句
select – 映射查詢語句
select <select id=”selectPerson” parameterType=”int” resultType=”hashmap”> SELECT * FROM PERSON WHERE ID = #{id} </select>
這個語句被稱作 selectPerson,使用一個 int (或 Integer)類型的參數,並返回一個 HashMap類型的對象,其中的鍵是列名,值是列對應的值
----------------------select 元素:----------------
<select id=”selectPerson” <!--在命名空間中唯一的標識符,可以被用來引用這條語句。--> parameterType=”int” <!--將會傳入這條語句的參數類的完全限定名或別名。--> parameterMap=”deprecated” resultType=”hashmap” <!--返回的期望類型的類的完全限定名或別名。注意集合情形,那應該是集合可以包含的類型,而不能是集 合本身。使用 resultType 或 resultMap,但不能同時使用> resultMap=”personResultMap” <!--命名引用外部的 resultMap。返回 map 是 MyBatis 最具力量的特性,對其有一個很好的理解的話,許 多復雜映射的情形就能被解決了。使用 resultMap 或 resultType,但不能同時使用。--> flushCache=”false” <!--將其設置為 true, 無論語句什么時候被調用,都會導致緩存被清空。默認值: false。--> useCache=”true” <!--將其設置為 true,將會導致本條語句的結果被緩存。默認值: true。> timeout=”10000” <!--這個設置驅動程序等待數據庫返回請求結果,並拋出異常時間的最大等待值。 默認不設置(驅動自行處理)。--> fetchSize=”256” <!--這是暗示驅動程序每次批量返回的結果行數。默認不設置(驅動自行處理)。--> statementType=”PREPARED” <!--STATEMENT,PREPARED 或 CALLABLE 的一種。這會讓 MyBatis使用選擇使用 Statement, PreparedStatement 或 CallableStatement。默認值: PREPARED。--> resultSetType=”FORWARD_ONLY” <!--FORWARD_ONLY|SCROLL_SENSITIVE|SCROLL_INSENSITIVE中的一種。 默認是不設置(驅動自行處理)。--> >
insert
,
update
,
delete
數據修改語句 insert , update 和 delete 在它們的實現中非常相似:
數據修改語句 insert , update 和 delete 在它們的實現中非常相似:
<insert id="insertAuthor" parameterType="domain.blog.Author" flushCache="true" statementType="PREPARED" keyProperty="" useGeneratedKeys="" timeout="20000">
支持自動生成主鍵的數據庫可以使用這個
<insert id="insertAuthor" parameterType="domain.blog.Author" useGeneratedKeys=”true” keyProperty=”id”> insert into Author (username,password,email,bio) values (#{username},#{password},#{email},#{bio}) </insert>
不支持的可以使用這個
<insert id="insertAuthor" parameterType="domain.blog.Author"> <selectKey keyProperty="id" resultType="int" order="BEFORE"> select CAST(RANDOM()*1000000 as INTEGER) a from SYSIBM.SYSDUMMY1 </selectKey> insert into Author(id, username, password, email,bio, favourite_section) values(#{id}, #{username}, #{password}, #{email}, #{bio},#{favouriteSection,jdbcType=VARCHAR}) </insert>
屬性描述:
keyProperty:selectKey 語句結果應該被設置的目標屬性
resultType :結果的類型。 MyBatis 通常可以算出來,但是寫上也沒有問題。MyBatis 允許任何簡單類型用作主鍵的類型,包括字符串。
order :這可以被設置為 BEFORE 或 AFTER。如果設置為 BEFORE,那么它會首先選擇主鍵,設置 keyProperty 然后執行插入語句。如果
設置為 AFTER,那么先執行插入語句,然后是 selectKey 元素-這和如 Oracle 數據庫相似,可以在插入語句中嵌入序列調用。
statementType : MyBatis 支持 STATEMENT, PREPARED 和CALLABLE 語句的映射類型,
分別代表 PreparedStatement 和CallableStatement 類型。
sql
這個元素可以被用來定義
可重用的 SQL 代碼段,可以包含在其他語句中。比如:
這個 SQL 片段可以被包含在其他語句中,例如:
<sql id=”userColumns”> id,username,password </sql>
這個 SQL 片段可以被包含在其他語句中,例如:
<select id=”selectUsers” parameterType=”int” resultType=”hashmap”> select <include refid=”userColumns”/>from some_table where id = #{id} </select>
字符串替換
默認情況下,使用#{}格式的語法會導致 MyBatis 創建預處理語句屬性並以它為背景設
置安全的值(比如?)。這樣做很安全,很迅速, 也是首選的做法,有時你只是想直接在 SQL
語句中插入一個不改變的字符串。比如,像 ORDER BY,你可以這樣來使用:
ORDER BY ${columnName}
這里 MyBatis 不會修改或轉義字符串。
重要: 接受從用戶輸出的內容並提供給語句中不變的字符串,這樣做是不安全的。這會
導致潛在的 SQL 注入攻擊,因此你不應該允許用戶輸入這些字段,或者通常自行轉義並檢查。
默認情況下,使用#{}格式的語法會導致 MyBatis 創建預處理語句屬性並以它為背景設
置安全的值(比如?)。這樣做很安全,很迅速, 也是首選的做法,有時你只是想直接在 SQL
語句中插入一個不改變的字符串。比如,像 ORDER BY,你可以這樣來使用:
ORDER BY ${columnName}
這里 MyBatis 不會修改或轉義字符串。
重要: 接受從用戶輸出的內容並提供給語句中不變的字符串,這樣做是不安全的。這會
導致潛在的 SQL 注入攻擊,因此你不應該允許用戶輸入這些字段,或者通常自行轉義並檢查。
resultMap
----------------------------------將返回的結果映射到Map
<select id=”selectUsers” parameterType=”int” resultType=”hashmap”> select id, username, hashedPassword from some_table where id = #{id} </select>
----------------------------------將返回的結果映射到Bean
<select id=”selectUsers” parameterType=”int” resultType=”com.someapp.model.User”> select id, username, hashedPasswordfrom some_tablewhere id = #{id} </select>
這個可以輸入類的別名,而不用輸入類的全路徑
<!-- 在XML配置文件中--> <typeAlias type=”com.someapp.model.User” alias=”User”/> <!-- 在SQL映射的XML文件中--> <select id=”selectUsers” parameterType=”int” resultType=”User”> select id, username, hashedPassword from some_table where id = #{id} </select>
如果列名沒有精確匹配,你可以在列名上使用
select
字句的別名(一個
標准的 SQL 特性)來匹配標簽
標准的 SQL 特性)來匹配標簽
<select id=”selectUsers” parameterType=”int” resultType=” User”> select user_id as “id”, user_name as “userName”, hashed_password as “hashedPassword” from some_table where id = #{id} </select>
》》》解決列名不匹配的另外一種方式
<resultMap id="userResultMap" type="User"> <id property="id" column="user_id" /> <result property="username" column="user_name"/> <result property="password" column="hashed_password"/> </resultMap>
引用它的語句使用 resultMap 屬性就行了(注意我們去掉了 resultType 屬性)。比如:
<select id=”selectUsers” parameterType=”int” resultMap=”userResultMap”> select user_id, user_name, hashed_password from some_table where id = #{id} </select>