? ? ? ?在講MyBatis動態(tài)SQL之前,先教大家怎么通過MyBatis插件自動生成mapper對應(yīng)的文件和對應(yīng)的bean文件笋熬。使用起來非常簡單碱璃。
? ? ? ?第一步计济,在pom.xml文件里面添加plugin。這里要注意configurationFile部分這個字段指明generatorConfig.xml文件的位置各吨。generatorConfig.xml在第二步會教大家怎么配置撩满。這里我們指定的目錄是resources/generator文件夾下面,大家根據(jù)自己的實(shí)際情況來指定绅你。
<plugin>
<groupId>org.mybatis.generator</groupId>
<artifactId>mybatis-generator-maven-plugin</artifactId>
<version>1.3.2</version>
<dependencies>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>5.1.35</version>
</dependency>
</dependencies>
<configuration>
<!--配置文件的路徑-->
<configurationFile>${basedir}/src/main/resources/generatorConfig.xml</configurationFile>
<overwrite>true</overwrite>
</configuration>
</plugin>
? ? ? ?第二步伺帘,generatorConfig.xml文件的配置,主要改的地方就是jdbcConnection字段里面數(shù)據(jù)庫相關(guān)的信息忌锯。以及javaModelGenerator伪嫁,sqlMapGenerator,javaClientGenerator字段目標(biāo)文件的位置偶垮。和table字段里面改成自己的表格张咳。關(guān)于這些東西generatorConfig.xml文件里面咱們也注釋的很清楚。
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE generatorConfiguration
PUBLIC "-//mybatis.org//DTD MyBatis Generator Configuration 1.0//EN"
"http://mybatis.org/dtd/mybatis-generator-config_1_0.dtd">
<generatorConfiguration>
<!--執(zhí)行命令 mvn mybatis-generator:generate-->
<context id="test" targetRuntime="MyBatis3">
<plugin type="org.mybatis.generator.plugins.EqualsHashCodePlugin"></plugin>
<plugin type="org.mybatis.generator.plugins.SerializablePlugin"></plugin>
<plugin type="org.mybatis.generator.plugins.ToStringPlugin"></plugin>
<commentGenerator>
<!-- 這個元素用來去除指定生成的注釋中是否包含生成的日期 false:表示保護(hù) -->
<!-- 如果生成日期似舵,會造成即使修改一個字段脚猾,整個實(shí)體類所有屬性都會發(fā)生變化,不利于版本控制砚哗,所以設(shè)置為true -->
<property name="suppressDate" value="true"/>
<!-- 是否去除自動生成的注釋 true:是 : false:否 -->
<property name="suppressAllComments" value="false"/>
</commentGenerator>
<!--數(shù)據(jù)庫鏈接URL龙助,用戶名、密碼 -->
<jdbcConnection driverClass="com.mysql.jdbc.Driver"
connectionURL="jdbc:mysql://192.168.13.98/dcim" userId="root" password="123456">
</jdbcConnection>
<javaTypeResolver>
<!-- This property is used to specify whether MyBatis Generator should
force the use of java.math.BigDecimal for DECIMAL and NUMERIC fields, -->
<property name="forceBigDecimals" value="false"/>
</javaTypeResolver>
<!-- 生成模型的包名和位置 -->
<javaModelGenerator targetPackage="com.pilot.dcim.alarmmanage.entity.model"
targetProject="src/main/java">
<property name="enableSubPackages" value="true"/>
<property name="trimStrings" value="true"/>
</javaModelGenerator>
<!-- 生成映射文件的包名和位置 -->
<sqlMapGenerator targetPackage="com.pilot.dcim.alarmmanage.mapper"
targetProject="src/main/resources">
<property name="enableSubPackages" value="true"/>
</sqlMapGenerator>
<!-- 生成DAO的包名和位置 -->
<javaClientGenerator type="XMLMAPPER"
targetPackage="com.pilot.dcim.alarmmanage.mapper"
implementationPackage="com.pilot.dcim.alarmmanage.service.impl"
targetProject="src/main/java">
<property name="enableSubPackages" value="true"/>
</javaClientGenerator>
<!-- 要生成哪些表 -->
<table tableName="alarmgroup" domainObjectName="AlarmGroup"
enableCountByExample="false" enableUpdateByExample="false"
enableDeleteByExample="false" enableSelectByExample="false"
selectByExampleQueryId="false"></table>
<table tableName="alarmparam" domainObjectName="AlarmParam"
enableCountByExample="false" enableUpdateByExample="false"
enableDeleteByExample="false" enableSelectByExample="false"
selectByExampleQueryId="false"></table>
<table tableName="alarmsetting" domainObjectName="AlarmSetting"
enableCountByExample="false" enableUpdateByExample="false"
enableDeleteByExample="false" enableSelectByExample="false"
selectByExampleQueryId="false"></table>
<table tableName="faultevent" domainObjectName="FaultEvent"
enableCountByExample="false" enableUpdateByExample="false"
enableDeleteByExample="false" enableSelectByExample="false"
selectByExampleQueryId="false"></table>
</context>
</generatorConfiguration>
? ? ? ?第三步蛛芥,上面兩部都配置好之后提鸟,執(zhí)行命令 mvn mybatis-generator:generate 就會在對應(yīng)的目錄下生成我們想要的文件军援。
? ? ? ?MyBatis的動態(tài)SQL是基于OGNL的表達(dá)式的。它對SQL語句進(jìn)行靈活的操作称勋。通過表達(dá)式判斷來實(shí)現(xiàn)對SQL的靈活拼接胸哥、組裝。我們著重講說MyBatis動態(tài)SQL里面一些元素的使用赡鲜。
一空厌、MyBatis動態(tài)SQL標(biāo)簽的學(xué)習(xí)
1.1、if 條件判斷標(biāo)簽
? ? ? ?if標(biāo)簽通用用于通過判斷參數(shù)值來決定是否使用某個查詢條件银酬。
1.1.1嘲更、if 判斷數(shù)字
? ? ? ?if 判斷數(shù)字,大部分都是判斷等于或者不等于某個數(shù)字捡硅。
<if test="filter == 1">
...
</if>
1.1.2哮内、if 判斷字符串
? ? ? ?大部分情況下都是去判斷傳遞過來的字符串是否為空。當(dāng)然咱們也是可以添加別的條件限制的壮韭,比如以啥字符串開頭北发,以啥字符串結(jié)尾。
1.1.2.1喷屋、判斷字符串是否為空,或者字符串等于某個值
<select id="selectUser" resultType="com.tuacy.mybatisdemo.model.User">
select * from user
<where>
<if test="user.name != null and user.name == '0'.toString()">
and name = #{user.name}
</if>
</where>
</select>
1.1.2.2琳拨、判斷字符串是否包含
<select id="selectUser" resultType="com.tuacy.mybatisdemo.model.User">
select * from user
<where>
<if test=" user.name != null and user.name.contains('1'.toString())">
and name = #{user.name}
</if>
</where>
</select>
1.1.2.3、判斷是否以字符串開頭
<select id="selectUser" resultType="com.tuacy.mybatisdemo.model.User">
select * from user
<where>
<if test=" user.name != null and user.name.startsWith('1'.toString())">
and name = #{user.name}
</if>
</where>
</select>
1.1.3屯曹、判斷列表
? ? ? ?經(jīng)常判斷列表是否為null狱庇,或者列表是否為空。列表判斷也是很簡單的直接 <if test=" nameList != null and nameList.size() > 0 "> 就搞定了恶耽。
一個簡單的實(shí)例密任,通過用戶名(list)查詢用戶
List<User> selectUserByName(@Param("nameList") List<String> nameList);
<!-- 通過用戶名查找用戶 -->
<select id="selectUserByName" resultType="com.tuacy.mybatisdemo.model.User">
select * from user
<where>
<if test=" nameList != null and nameList.size() > 0 ">
<trim prefix=" name in ">
<foreach collection="nameList" item="i" index="index" open="(" separator="," close=")">
<if test="i != null">
#{i}
</if>
</foreach>
</trim>
</if>
</where>
</select>
1.2、choose偷俭,when浪讳,otherwise標(biāo)簽(switch case)
? ? ? ?choose,when涌萤,otherwise標(biāo)簽的作用類似與咱們java里面的switch case的作用淹遵。
<choose>
<when test="item.name != null">
#{item.name,jdbcType=VARCHAR},
</when>
<otherwise>
null,
</otherwise>
</choose>
1.3、foreach循環(huán)標(biāo)簽
? ? ? ?foreach的主要用在構(gòu)建in條件中负溪,它可以在SQL語句中進(jìn)行迭代一個集合透揣。大部分都是對一個list進(jìn)行循環(huán)。
? ? ? ?foreach元素的屬性主要有 item川抡,index辐真,collection,open,separator拆祈,close恨闪。
foreach元素 | 解釋 |
---|---|
collection | 迭代的對象 |
item | 迭代過程中的每個元素 |
index | 迭代過程中的位置 |
open | 語句以什么開始 |
separator | 語句以什么作為分隔符 |
close | 語句以什么結(jié)束 |
? ? ? ?在使用foreach的時候最關(guān)鍵的也是最容易出錯的就是collection屬性倘感,該屬性是必須指定的放坏,但是在不同情況 下,該屬性的值是不一樣的老玛,主要有一下3種情況:
- 如果傳入的是單參數(shù)且參數(shù)類型是一個List的時候淤年,collection屬性值為list。
- 如果傳入的是單參數(shù)且參數(shù)類型是一個array數(shù)組的時候蜡豹,collection的屬性值為array麸粮。
- 如果傳入的參數(shù)是多個的時候,我們就需要把它們封裝成一個Map了镜廉,當(dāng)然單參數(shù)也可以弄诲。
一個簡單的實(shí)例
<select id="dynamicForeachTest" parameterType="java.util.List" resultType="Blog">
select * from t_blog where id in
<foreach collection="list" index="index" item="item" open="(" separator="," close=")">
#{item}
</foreach>
</select>
array
<select id="dynamicForeach2Test" parameterType="java.util.ArrayList" resultType="Blog">
select * from t_blog where id in
<foreach collection="array" index="index" item="item" open="(" separator="," close=")">
#{item}
</foreach>
</select>
map
<select id="dynamicForeach3Test" parameterType="java.util.HashMap" resultType="Blog">
select * from t_blog where title like "%"#{title}"%" and id in
<foreach collection="ids" index="index" item="item" open="(" separator="," close=")">
#{item}
</foreach>
</select>
上面說的都是沒有指定@Param的情況,如果指定了@Param則collection的屬性值是@Param指定的名字娇唯。
1.4齐遵、trim標(biāo)簽
? ? ? ?trim標(biāo)記是一個格式化的標(biāo)記,可以完成set或者是where標(biāo)記的功能塔插。
trim屬性 | 描述 |
---|---|
prefix | 給sql語句拼接的前綴 |
suffix | 給sql語句拼接的后綴 |
prefixesToOverride | 去除sql語句前面的關(guān)鍵字或者字符梗摇,該關(guān)鍵字或者字符由prefixesToOverride屬性指定,假設(shè)該屬性指定為”AND”想许,當(dāng)sql語句的開頭為”AND”伶授,trim標(biāo)簽將會去除該”AND |
suffixesToOverride | 去除sql語句后面的關(guān)鍵字或者字符,該關(guān)鍵字或者字符由suffixesToOverride屬性指定 |
<trim prefix="WHERE" prefixOverrides="AND">
<if test="state != null">
state = #{state}
</if>
<if test="title != null">
AND title like #{title}
</if>
<if test="author != null and author.name != null">
AND author_name like #{author.name}
</if>
</trim>
1.5流纹、where標(biāo)簽
? ? ? ?where標(biāo)簽是非常有用的糜烹,他有兩個作用:
- 當(dāng)where標(biāo)簽里面元素的元素都不滿足條件的時候,不會插入where語句漱凝。
- where標(biāo)簽里面若語句的開頭為“AND”或“OR”疮蹦,where 元素也會將它們?nèi)コ?/li>
有這么一個例子,我呢有一個user表(pkid, name, phone, password)碉哑,現(xiàn)在根據(jù)我們傳入的條件來查詢user信息挚币。
<!-- 查找指定的用戶 -->
<select id="selectUser" resultType="com.tuacy.mybatisdemo.model.User">
select * from user
<where>
<if test="user.pkid != null">
pkid = #{user.pkid}
</if>
<if test="user.name != null">
and name = #{user.name}
</if>
<if test="user.phone != null">
and phone = #{user.phone}
</if>
<if test="user.password != null">
and password = #{user.password}
</if>
</where>
</select>
1.6、set標(biāo)簽
? ? ? ?set標(biāo)簽和where標(biāo)簽一樣扣典。會自動加上set關(guān)鍵字妆毕,并且去掉不必要的一些字符。
<set>
<if test="userId !=null and userId !=''">
AND A.userId = #{userId,jdbcType=CHAR}
</if>
<if test="userName !=null and userName !=''">
AND A.userName = #{userName,jdbcType=CHAR}
</if>
</set>
1.7贮尖、bind標(biāo)簽
? ? ? ?bind 標(biāo)簽可以使用 OGNL 表達(dá)式創(chuàng)建一個變量井將其綁定到上下文中笛粘。咱就可以簡單的認(rèn)為是聲明了一個變量。
這個例子里面,我純粹的是把user.name替換成了user.name了薪前。
<select id="selectUser" resultType="com.tuacy.mybatisdemo.model.User">
select * from user
<where>
<bind name="userName" value="user.name"/>
<if test=" userName != null ">
and name = #{userName}
</if>
</where>
</select>
這例子里面咱用bind標(biāo)簽聲明了一個模糊查詢的變量
<select id="selectUser" resultType="com.tuacy.mybatisdemo.model.User">
select * from user
<where>
<bind name="patternName" value="'%' + user.name + '%'" />
<if test=" user.name != null ">
and name like #{patternName}
</if>
</where>
</select>
二润努、MyBatis動態(tài)SQL實(shí)例
? ? ? ?最后我們根據(jù)今天所學(xué)到的內(nèi)容,給出兩個比較復(fù)雜的MyBats動態(tài)SQL示括。
2.1铺浇、批量插入并且更新主鍵
<!-- 批量插入并且更新主鍵 -->
<insert id="insertUserBatch" parameterType="java.util.List" useGeneratedKeys="true" keyProperty="pkid">
insert into user (name, password, phone)
values
<foreach collection="list" item="item" index="index" separator=",">
<trim prefix="(" suffix=")" suffixOverrides=",">
<choose>
<when test="item.name != null">
#{item.name,jdbcType=VARCHAR},
</when>
<otherwise>
null,
</otherwise>
</choose>
<choose>
<when test="item.password != null">
#{item.password,jdbcType=VARCHAR},
</when>
<otherwise>
null,
</otherwise>
</choose>
<choose>
<when test="item.phone != null">
#{item.phone,jdbcType=VARCHAR},
</when>
<otherwise>
null,
</otherwise>
</choose>
</trim>
</foreach>
</insert>
2.2、批量更新
<!-- 批量更新 -->
<update id="updateUserBatch" parameterType="java.util.List">
update user
<trim prefix="set" suffixOverrides=",">
<trim prefix="name =case" suffix="end,">
<foreach collection="list" item="i" index="index">
<if test="i.name!=null">
when pkid=#{i.pkid} then #{i.name}
</if>
</foreach>
</trim>
<trim prefix=" password =case" suffix="end,">
<foreach collection="list" item="i" index="index">
<if test="i.password!=null">
when pkid=#{i.pkid} then #{i.password}
</if>
</foreach>
</trim>
<trim prefix="phone =case" suffix="end,">
<foreach collection="list" item="i" index="index">
<if test="i.phone!=null">
when pkid=#{i.pkid} then #{i.phone}
</if>
</foreach>
</trim>
</trim>
where
<foreach collection="list" separator="or" item="i" index="index">
pkid=#{i.pkid}
</foreach>
</update>
? ? ? ?上面涉及到的所有實(shí)例的下載地址:https://github.com/tuacy/mybatisdemo