JAVAWEB开发之mybatis详解(二)——高级映射、查询缓存、mybatis与Spring整合以及懒加载的配置和逆向工程

mybatis基础知识回顾

1. mybatis是什么?
  • mybatis是一个持久层框架,是Apache下的开源项目,前身是ibatis,是一个不完全的ORM框架,mybatis提供输入和输出的映射,需要程序员自己手动写SQL语句,mybatis重点对SQL语句进行灵活操作。
  • 适用场合:需求变化频繁,数据模型不固定的项目,例如:互联网项目。
2.mybatis架构:
  • SqlMapConfig.xml(名称不固定),配置内容:数据源、事务、properties、typeAliases、settings、mappers配置。
  • SqlSessionFactory:会话工厂,作用是创建SqlSession,实际开发中以单例模式管理SqlSessionFactory。
  • SqlSession:会话,是一个面向用户(程序员)的接口,使用mapper代理方法开发是不需要程序员直接调用Sqlsession的方法。它是线程不安全的,最佳使用场合是方法体内。
3.mybatis开发DAO的方法
  3.1 原始DAO开发方法,需要程序员编写Dao接口和实现类,此方法在当前企业中还有使用因为ibatis用的就是这种原始的Dao开发方式。
  3.2 mapper代理方法,程序员只需要编写mapper接口(相当于DAO接口),mybatis自动根据mapper接口和mapper接口对应的statement自动生成代理对象(接口实现类对象),注意使用mapper代理方法开发需要遵循以下规则:
  • mapper.xml中namespace是mapper接口的全限定名。
  • mapper.xml中statement的id为mapper接口的方法名。
  • mapper.xml中statement输入类型(parameterType)和mapper接口方法输入参数类型一致。
  • mapper.xml中statement输出类型(resultType)和mapper接口方法返回结果类型一致。
resultType和resultMap都可以完成输出映射:
resultType映射要求SQL查询的列名和输出映射pojo类型的属性名一致。
resultMap映射时对SQL查询的列名和输出映射pojo类型的属性名做一个对应关系。
4.动态SQL:
#{}和${}完成输入参数的属性值获取,通过OGNL获取parameterType指定的pojo的属性名。
#{}:占位符号,好处是防止SQL注入。
${}: SQL拼接符号,无法防止SQL注入。
if、where以及foreach的使用。

mybatis重点高级知识清单

1.使用resultMap完成高级映射(重点)
—|学习商品订单数据模型(一对一、一对多、多对多)
—|resultMap实现一对一、一对多、多对多
—|延迟加载
2.查询缓存(重点)
—|一级缓存
—|二级缓存
3.mybatis和Spring的整合(重点)
4.mybatis逆向工程(常用)

商品订单数据模型

JAVAWEB开发之mybatis详解(二)——高级映射、查询缓存、mybatis与Spring整合以及懒加载的配置和逆向工程_第1张图片
技巧总结:学会在企业中如何去分析陌生表的数据模型
1.学习单表记录了什么东西(去学习理解需求)
2.学习单表重要字段的意义(优先学习不能为空的字段)
3.学习表与表之间的关系(一对一、一对多、多对多)
   通过表的外键分析表之间的关系。
注意:分析表与表之间的关系是建立在业务意义基础之上的。
JAVAWEB开发之mybatis详解(二)——高级映射、查询缓存、mybatis与Spring整合以及懒加载的配置和逆向工程_第2张图片
用户表user:记录了购买商品的用户
订单表orders:记录了用户所创建的订单信息
订单明细表orderdetail:记录了用户所创建订单的详细信息
商品信息表items:记录了商家提供的商品信息。
分析表与表之间的订单关系:
(1) 用户表user和订单orders:
user—>orders: 一个用户可以创建多个订单  多对多
orders—>user: 一个订单只能由一个用户创建  一对一
(2) 订单表orders和订单明细表orderdetail:
orders—>orderdetail: 一个订单可以包括多个订单明细  一对多
orderdetail—>orders: 一个订单明细只能属于一个订单   一对一
(3)订单明细orderdetail和商品信息items
orderdetail—>items: 一个订单明细只能对应一个商品信息  一对一
items—>orderdetail: 一个商品对应多个订单明细   一对多

一对一查询

需求

查询订单信息关联查询用户信息

sql语句

查询语句:
先确定主查询表:订单信息表
再确定关联查询表:用户信息
通过orders关联穿用户使用user_id一个外键,根据一条订单数据只能查询出一条用户记录就可以使用内连接
[sql] view plain copy
  1. SELECT   
  2.     orders.*, user.username, user.sex  
  3. FROM  
  4.     orders,  
  5.     user  
  6. WHERE  
  7.     orders.user_id = user.id;  
JAVAWEB开发之mybatis详解(二)——高级映射、查询缓存、mybatis与Spring整合以及懒加载的配置和逆向工程_第3张图片

使用resultType实现

创建PO类

创建基础表单的PO类

一对一查询映射的pojo

创建pojo包括 订单信息和用户信息,resultType才可以完成映射
创建OrderCustom作为自定义pojo,继承 SQL查询中列最多的POJO类
[java] view plain copy
  1. public class OrderCustom extends Orders {  
  2.     //补充用户信息  
  3.     private String username;  
  4.     private String sex;  
  5.     private String address;  
  6.      //提供对应的setter和getter方法  
  7.      ......  
  8. }  

mapper.xml

[html] view plain copy
  1.   
  2.    <resultMap type="test.lx.mybatis.po.Orders" id="ordersUserResultMap">  
  3.       
  4.       
  5.     <id column="id" property="id"/>  
  6.     <result column="user_id" property="userId"/>  
  7.     <result column="number" property="number"/>  
  8.     <result column="createtime" property="createtime"/>  
  9.     <result column="note" property="note"/>  
  10.       
  11.       
  12.            
  13.          <id column="user_id" property="id"/>  
  14.            
  15.          <result column="username" property="username"/>  
  16.          <result column="sex" property="sex"/>  
  17.      association>  
  18.    resultMap>  
注意的是:两个id的配置以及column的配置 外层的id配置一般指主查询表的主键,内层一般指的是关联查询的外键,共同点是其column的值都为执行其SQL语句查询出来的名称。起property是对应查询表的PO类中的属性名。

mapper.java

[java] view plain copy
  1. // 一对一查询,查询订单关联查询用户,使用resultMap  
  2. public List findOrderUserListResultMap() throws Exception;  

小结

resultType:要自定义pojo 保证SQL查询列名要和pojo的属性对应,这种方法相对较简单,所以应用广泛。
resultMap:使用association完成一对一映射需要配置resultMap,过程有点复杂,如果要实现延迟加载就只能使用resultMap来进行实现,如果为了方便对关联信息的解析,也可使用association将关联信息映射到pojo中方便解析。

一对多查询

需求

查询所有订单信息及订单下的订单明细信息

SQL语句

主查询表:订单表
关联查询表:订单明细
[sql] view plain copy
  1. SELECT   
  2.   orders.*,  
  3.   user.username,  
  4.   user.sex ,  
  5.   orderdetail.id orderdetail_id,  
  6.   orderdetail.items_num,  
  7.   orderdetail.items_id  
  8. FROM  
  9.   orders,  
  10.   USER,  
  11.   orderdetail  
  12. WHERE orders.user_id = user.id  AND orders.id = orderdetail.orders_id  
查询结果


需要将订单明细内容设置到对应的订单中

resultMap进行一对多映射思路

resultMap提供collection完成关联信息映射到集合对象中。
在orders类中创建集合属性orderdetails:
[java] view plain copy
  1. public class Orders {  
  2.     private Integer id;  
  3.     private Integer userId;  
  4.     private String number; //商品编号  
  5.       
  6.     private Date createtime;  
  7.       
  8.     private String note;  
  9.       
  10.     //关联用户信息  
  11.     private User user;  
  12.       
  13.     //订单明细  
  14.     private List orderDetails;  
  15.        //  
  16.        ......  

mapper.xml

[html] view plain copy
  1.   
  2.     <resultMap type="orders" id="orderAndOrderDetails" extends="ordersUserResultMap">  
  3.           
  4.           
  5.           
  6.     <resultMap type="user" id="userOrderDetailResultMap">  
  7.           
  8.         <id column="user_id" property="id"/>  
  9.         <result column="username" property="username"/>  
  10.         <result column="sex" property="sex"/>  
  11.           
  12.         <collection property="orderlist" ofType="test.lx.mybatis.po.Orders">  
  13.             <id column="id" property="id"/>  
  14.             <result column="user_id" property="userId"/>  
  15.             <result column="number" property="number"/>  
  16.             <result column="createtime" property="createtime"/>  
  17.             <result column="note" property="note"/>  
  18.               
  19.             <collection property="orderDetails" ofType="test.lx.mybatis.po.OrderDetail">  
  20.                   
  21.                 <association property="items" javaType="test.lx.mybatis.po.Items">  
  22.                     <id column="item_id" property="id"/>  
  23.                     <result column="items_name" property="name"/>  
  24.                     <result column="items_detail" property="detail"/>  
  25.                 association>  
  26.             collection>  
  27.         collection>  
  28.     resultMap>  

mapper.java

[java] view plain copy
  1. // 一对多查询,查询订单关联查询订单明细以及商品信息,使用resultMap  
  2.     public List findUserOrderDetail() throws Exception;  

多对多查询

一对多是多对多的特例。
需求1:
查询显示字段:用户账号、用户名称、用户性别、商品名称、商品价格(最常见)
企业开发中常见明细列表,用户购买商品明细列表,
使用resultType将上边查询列映射到pojo输出。
 
需求2:
查询显示字段:用户账号、用户名称、购买商品数量、商品明细(鼠标移上显示明细)
使用resultMap将用户购买的商品明细列表映射到user对象中。
实现方法和一对多一样。

延迟加载

使用延迟加载的意义

在进行数据查询时,为了提高数据库查询性能,尽量使用单表查询,因为单表查询比多表关联查询速度快。

如果查询单表就可以满足需求,一开始先查询单表,当需要关联信息时,再关联查询。当需要关联信息时才进行查询就叫做延迟加载。mybatis中resultMap提供延迟加载功能,通过resultMap配置延迟加载。

JAVAWEB开发之mybatis详解(二)——高级映射、查询缓存、mybatis与Spring整合以及懒加载的配置和逆向工程_第7张图片

在SqlMapConfig.xml中配置全局参数

[html] view plain copy
  1.   
  2.     <settings>  
  3.          
  4.        <setting name="lazyLoadingEnabled" value="true"/>  
  5.          
  6.        <setting name="aggressiveLazyLoading" value="false"/>  
  7.     settings>  

延迟加载实现

实现思路

需求:查询订单及用户信息,一对一查询
刚开始只查询订单信息,当需要用户信息时调用Orders类中的getUser()方法执行延迟加载,向数据库发出SQL。

mapper.xml

[html] view plain copy
  1.   
  2.     <resultMap type="orders" id="orderCustomLazyLoading">  
  3.           
  4.           
  5.         <id column="id" property="id"/>  
  6.         <result column="user_id" property="userId"/>  
  7.         <result column="number" property="number"/>  
  8.         <result column="createtime" property="createtime"/>  
  9.         <result column="note" property="note"/>  
  10.           
  11.     <diskStore path="/Users/liuxun/Desktop/ehcache" />  
  12.     <defaultCache   
  13.         maxElementsInMemory="1000"   
  14.         maxElementsOnDisk="10000000"  
  15.         eternal="false"   
  16.         overflowToDisk="false"   
  17.         diskPersistent="true"  
  18.         timeToIdleSeconds="120"  
  19.         timeToLiveSeconds="120"   
  20.         diskExpiryThreadIntervalSeconds="120"  
  21.         memoryStoreEvictionPolicy="LRU">  
  22.     defaultCache>  
  23. ehcache>  

整合ehcache

在mapper.xml下添加ehcache配置
[html] view plain copy
  1.   
  2.       
  3.     <cache type="org.mybatis.caches.ehcache.EhcacheCache">  
  4.         <property name="timeToIdleSeconds" value="12000"/>  
  5.         <property name="timeToLiveSeconds" value="3600"/>  
  6.           
  7.         <property name="maxEntriesLocalHeap" value="1000"/>  
  8.           
  9.         <property name="maxEntriesLocalDisk" value="10000000"/>  
  10.         <property name="memoryStoreEvictionPolicy" value="LRU"/>  
  11.     cache>  
JAVAWEB开发之mybatis详解(二)——高级映射、查询缓存、mybatis与Spring整合以及懒加载的配置和逆向工程_第16张图片

二级缓存的应用场景

对于查询频率高,变化频率低的数据建议使用二级缓存。
对于访问多的查询请求且用户对查询结果的实时性要求不高,此时可采用mybatis二级缓存技术降低数据库的访问量,提高访问速度,业务场景比如:耗时较高的统计分析sql、电话账单查询sql等。
实现方法如下:通过设置刷新时间间隔,由mybatis每隔一段时间自动清空缓存,根据数据变化频率设置缓存刷新时间间隔flushInterval,比如设置30分钟、60分钟、24小时等,根据需求而定。

mybatis局限性

mybatis二级缓存对细粒度的数据级别的缓存实现不好,比如如下需求:对商品信息进行缓存,由于商品信息查询访问量大,但是要求用户每次都能查询最新的商品信息,此时如果使用mybatis的二级缓存就无法实现当一个商品变化时只刷新该商品的缓存信息而不刷新其它商品的信息,因为mybaits的二级缓存区域以mapper为单位划分,当一个商品信息变化会将所有商品信息的缓存数据全部清空。解决此类问题需要在业务层根据需求对数据有针对性缓存。

项目代码

完整代码已经上传GitHub(https://github.com/LX1993728/mybatisDemo_2)
JAVAWEB开发之mybatis详解(二)——高级映射、查询缓存、mybatis与Spring整合以及懒加载的配置和逆向工程_第17张图片JAVAWEB开发之mybatis详解(二)——高级映射、查询缓存、mybatis与Spring整合以及懒加载的配置和逆向工程_第18张图片

OrdersMapperCustom.java
[java] view plain copy
  1. package test.lx.mybatis.mapper;  
  2.   
  3. import java.util.List;  
  4.   
  5. import test.lx.mybatis.po.OrderCustom;  
  6. import test.lx.mybatis.po.Orders;  
  7. import test.lx.mybatis.po.User;  
  8.   
  9. /** 
  10.  * 订单自定义的mapper接口 
  11.  *  
  12.  * @author liuxun 
  13.  * 
  14.  */  
  15. public interface OrdersMapperCustom {  
  16.     // 一对一查询,查询订单关联查询用户,使用resultType  
  17.     public List findOrderUserList() throws Exception;  
  18.   
  19.     // 一对一查询,查询订单关联查询用户,使用resultMap  
  20.     public List findOrderUserListResultMap() throws Exception;  
  21.   
  22.     // 一对一查询,查询订单延迟加载用户信息,使用resultMap  
  23.     public List findOrderUserListLazyLoading() throws Exception;  
  24.       
  25.     // 一对多查询,查询订单关联查询订单明细,使用resultMap  
  26.     public List findOrderAndOrderdetails() throws Exception;  
  27.      
  28.     // 一对多查询,查询订单关联查询订单明细以及商品信息,使用resultMap  
  29.     public List findUserOrderDetail() throws Exception;  
  30. }  
OrdersMapperCustom.xml
[html] view plain copy
  1. xml version="1.0" encoding="UTF-8"?>  
  2. PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"  
  3. "http://mybatis.org/dtd/mybatis-3-mapper.dtd">  
  4. <mapper namespace="test.lx.mybatis.mapper.OrdersMapperCustom">  
  5.   
  6.       
  7.     <resultMap type="orders" id="ordersUserResultMap">  
  8.           
  9.           
  10.         <id column="id" property="id"/>  
  11.         <result column="user_id" property="userId"/>  
  12.         <result column="number" property="number"/>  
  13.         <result column="createtime" property="createtime"/>  
  14.         <result column="note" property="note"/>  
  15.           
  16.           
  17.                
  18.              <id column="user_id" property="id"/>  
  19.                
  20.              <result column="username" property="username"/>  
  21.              <result column="sex" property="sex"/>  
  22.          association>  
  23.     resultMap>  
  24.       
  25.       
  26.     <resultMap type="orders" id="orderCustomLazyLoading">  
  27.           
  28.           
  29.         <id column="id" property="id"/>  
  30.         <result column="user_id" property="userId"/>  
  31.         <result column="number" property="number"/>  
  32.         <result column="createtime" property="createtime"/>  
  33.         <result column="note" property="note"/>  
  34.           
  35.     <resultMap type="orders" id="orderAndOrderDetails" extends="ordersUserResultMap">  
  36.           
  37.           
  38.           
  39.     <resultMap type="user" id="userOrderDetailResultMap">  
  40.           
  41.         <id column="user_id" property="id"/>  
  42.         <result column="username" property="username"/>  
  43.         <result column="sex" property="sex"/>  
  44.           
  45.         <collection property="orderlist" ofType="test.lx.mybatis.po.Orders">  
  46.             <id column="id" property="id"/>  
  47.             <result column="user_id" property="userId"/>  
  48.             <result column="number" property="number"/>  
  49.             <result column="createtime" property="createtime"/>  
  50.             <result column="note" property="note"/>  
  51.               
  52.             <collection property="orderDetails" ofType="test.lx.mybatis.po.OrderDetail">  
  53.                   
  54.                 <association property="items" javaType="test.lx.mybatis.po.Items">  
  55.                     <id column="item_id" property="id"/>  
  56.                     <result column="items_name" property="name"/>  
  57.                     <result column="items_detail" property="detail"/>  
  58.                 association>  
  59.             collection>  
  60.         collection>  
  61.     resultMap>  
  62.       
  63.       
  64.     <diskStore path="/Users/liuxun/Desktop/ehcache" />  
  65.     <defaultCache   
  66.         maxElementsInMemory="1000"   
  67.         maxElementsOnDisk="10000000"  
  68.         eternal="false"   
  69.         overflowToDisk="false"   
  70.         diskPersistent="true"  
  71.         timeToIdleSeconds="120"  
  72.         timeToLiveSeconds="120"   
  73.         diskExpiryThreadIntervalSeconds="120"  
  74.         memoryStoreEvictionPolicy="LRU">  
  75.     defaultCache>  
  76. ehcache>  
UserMapper.xml
[html] view plain copy
  1. xml version="1.0" encoding="UTF-8"?>  
  2. PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"  
  3. "http://mybatis.org/dtd/mybatis-3-mapper.dtd">  
  4.   
  5.       
  6.     <cache type="org.mybatis.caches.ehcache.EhcacheCache">  
  7.         <property name="timeToIdleSeconds" value="12000"/>  
  8.         <property name="timeToLiveSeconds" value="3600"/>  
  9.           
  10.         <property name="maxEntriesLocalHeap" value="1000"/>  
  11.           
  12.         <property name="maxEntriesLocalDisk" value="10000000"/>  
  13.         <property name="memoryStoreEvictionPolicy" value="LRU"/>  
  14.     cache>  
  15.        
  16.               
  17.             <if test="userCustom!=null">  
  18.                 <if test="userCustom.username!=null and userCustom.username.trim().length() > 0">  
  19.                     and username like '%${userCustom.username.trim()}%'  
  20.                 if>  
  21.                 <if test="userCustom.sex!=null and userCustom.sex!=''">  
  22.                     and sex = #{userCustom.sex}  
  23.                 if>  
  24.                   
  25.                   
  26.                   
  27.             if>  
  28.       sql>  
  29.        
  30.        
  31.           <result column="username_" property="username"/>  
  32.           <result column="birthday_" property="birthday"/>  
  33.       resultMap>  
  34.        
  35.        
  36.        
  37.          <where>  
  38.              
  39.            <include refid="query_user_where">include>  
  40.              
  41.              
  42.          where>  
  43.       select>  
  44.         
  45.         
  46.          <where>  
  47.              
  48.            <include refid="query_user_where">include>  
  49.              
  50.              
  51.          where>  
  52.        select>  
  53.          
  54.         
  55.        
  56.       <delete id="deleteUser" parameterType="int" >  
  57.        delete from user where id=#{id}  
  58.       delete>  
  59.         
  60.      properties>  
  61.        
  62.        
  63.      <settings>  
  64.           
  65.         <setting name="lazyLoadingEnabled" value="true"/>  
  66.           
  67.         <setting name="aggressiveLazyLoading" value="false"/>  
  68.           
  69.         <setting name="cacheEnabled" value="true"/>  
  70.      settings>  
  71.        
  72.      <typeAliases>  
  73.        
  74.     <environments default="development">  
  75.         <environment id="development">  
  76.               
  77.             <transactionManager type="JDBC" />  
  78.             <dataSource type="POOLED">  
  79.                 <property name="driver" value="${jdbc.driver}" />  
  80.                 <property name="url" value="${jdbc.url}" />  
  81.                 <property name="username" value="${jdbc.username}" />  
  82.                 <property name="password" value="${jdbc.password}" />  
  83.             dataSource>  
  84.         environment>  
  85.     environments>  
  86.   
  87.       
  88.         <mapper resource="sqlmap/User.xml" />  
  89.           
  90.           
  91.           
  92.     <bean id="sqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean">  
  93.         
  94.       <property name="dataSource" ref="dataSource"/>  
  95.         
  96.       <property name="configLocation" value="classpath:mybatis/SqlMapConfig.xml"/>  
  97.     bean>  

开发原始DAO

[java] view plain copy
  1. public class UserDaoImpl extends SqlSessionDaoSupport implements UserDao {  
  2.   
  3.     public User findUserById(int id) throws Exception {  
  4.         // 创建SqlSession  
  5.         SqlSession sqlSession = this.getSqlSession();  
  6.   
  7.         // 根据id查询用户信息  
  8.         User user = sqlSession.selectOne("test.findUserById", id);  
  9.         return user;  
  10.     }  
  11. }  

配置原始DAO

[html] view plain copy
  1.   
  2.     <bean id="userDao" class="test.lx.mybatis.dao.UserDaoImpl">  
  3.       <property name="sqlSessionFactory" ref="sqlSessionFactory"/>  
  4.     bean>  

测试原始DAO接口

[java] view plain copy
  1. public class UserDaoImplTest {  
  2.     // 会话工厂  
  3.     private ApplicationContext applicationContext;  
  4.       
  5.     //创建工厂  
  6.     @Before  
  7.     public void init() throws IOException{  
  8.         // 创建Spring容器  
  9.         applicationContext = new ClassPathXmlApplicationContext("spring/applicationContext.xml");  
  10.     }  
  11.       
  12.     @Test  
  13.     public void testFindUserById() throws Exception{  
  14.         UserDao userDao = (UserDao) applicationContext.getBean("userDao");  
  15.         User user = userDao.findUserById(1);  
  16.         System.out.println(user);  
  17.     }  
  18.       
  19. }  

整合开发mapper代理方法

开发mapper.xml和mapper.java


使用MapperFactoryBean

[html] view plain copy
  1.   
  2.       
  3.      <bean id="userMapper" class="org.mybatis.spring.mapper.MapperFactoryBean">  
  4.       <property name="mapperInterface" value="test.lx.mybatis.mapper.UserMapper"/>  
  5.       <property name="sqlSessionFactory" ref="sqlSessionFactory"/>  
  6.     bean>   
使用此方法对每个mapper都需要配置,比较繁琐

使用MapperScannerConfigurer(扫描mapper)

[html] view plain copy
  1.   
  2.       <property name="sqlSessionFactoryBeanName" value="sqlSessionFactory"/>  
  3.     bean>  
使用扫描器自动扫描mapper,生成代理对象,比较方便。

测试mapper接口

[java] view plain copy
  1. public class UserMapperTest {  
  2.   
  3.     // 会话工厂  
  4.         private ApplicationContext applicationContext;  
  5.           
  6.         //创建工厂  
  7.         @Before  
  8.         public void init() throws IOException{  
  9.             // 创建Spring容器  
  10.             applicationContext = new ClassPathXmlApplicationContext("spring/applicationContext.xml");  
  11.         }  
  12.   
  13.     @Test  
  14.     public void testFindUserById() throws Exception {  
  15.         UserMapper userMapper = (UserMapper) applicationContext.getBean("userMapper");  
  16.         User user = userMapper.findUserById(1);  
  17.         System.out.println(user);  
  18.     }  
  19.   
  20. }  

mybatis逆向工程(Mybatis Generator)

什么是mybatis的逆向工程

mybatis官方为了提高开发效率,提供自动对表单生成SQL,包括:mapper.xml,mapper.java, 表名.java(po类)

在企业开发中通常是在设计阶段对表进行设计、创建。
在开发阶段根据表结构创建对应的po类。
mybatis逆向工程的方向:由数据表—>java代码

逆向工程使用配置

运行逆向工程 方法:
JAVAWEB开发之mybatis详解(二)——高级映射、查询缓存、mybatis与Spring整合以及懒加载的配置和逆向工程_第20张图片
为了避免插件的局限性,还是推荐使用Java程序生成
逆向工程运行所需要的jar包

数据库驱动包。

xml配置

需要使用配置的地方
需要注意的是:涉及到路径时,一定要写绝对路径,相对路径有时是不起作用的。
1.连接数据库的地址和驱动
[html] view plain copy
  1.   
  2.         <jdbcConnection driverClass="com.mysql.jdbc.Driver"  
  3.             connectionURL="jdbc:mysql://localhost:3306/mybatis" userId="root"  
  4.             password="root">  
  5.         jdbcConnection>  
2.需要配置PO类的包路径
[html] view plain copy
  1.   
  2.         <javaModelGenerator targetPackage="test.lx.mybatis.po"  
  3.             targetProject="/Users/liuxun/Workspaces/MyEclipse_2017_CI/Mybatis_generatorSqlMapCustom/src">  
  4.               
  5.             <property name="enableSubPackages" value="false" />  
  6.               
  7.             <property name="trimStrings" value="true" />  
  8.         javaModelGenerator>  
3.配置mapper包的路径
[html] view plain copy
  1.   
  2.         <sqlMapGenerator targetPackage="test.lx.mybatis.mapper"   
  3.             targetProject="/Users/liuxun/Workspaces/MyEclipse_2017_CI/Mybatis_generatorSqlMapCustom/src">  
  4.               
  5.             <property name="enableSubPackages" value="false" />  
  6.         sqlMapGenerator>  
  7.           
  8.         <javaClientGenerator type="XMLMAPPER"  
  9.             targetPackage="test.lx.mybatis.mapper"   
  10.             targetProject="/Users/liuxun/Workspaces/MyEclipse_2017_CI/Mybatis_generatorSqlMapCustom/src">  
  11.               
  12.             <property name="enableSubPackages" value="false" />  
  13.         javaClientGenerator>  
4.指定数据表
[html] view plain copy
  1.   
  2.         <table tableName="items">table>  
  3.         <table tableName="orders">table>  
  4.         <table tableName="orderdetail" >table>  

xml配置使用详解

[html] view plain copy
  1. xml version="1.0" encoding="UTF-8"?>  
  2.   PUBLIC "-//mybatis.org//DTD MyBatis Generator Configuration 1.0//EN"  
  3. "http://mybatis.org/dtd/mybatis-generator-config_1_0.dtd">  
  4.   
  5. <generatorConfiguration>  
  6.   
  7.     <property name="javaFileEncoding" value="UTF-8"/>  
  8.       
  9.     <property name="javaFormatter" value="org.mybatis.generator.api.dom.DefaultJavaFormatter"/>  
  10.       
  11.     <property name="xmlFormatter" value="org.mybatis.generator.api.dom.DefaultXmlFormatter"/>  
  12.   
  13.       
  14.     <property name="beginningDelimiter" value="`"/>  
  15.     <property name="endingDelimiter" value="`"/>  
  16.   
  17.       
  18.     jdbcConnection>  
  19.   
  20.       
  21.         <property name="enableSubPackages" value="true"/>  
  22.   
  23.           
  24.         <property name="trimStrings" value="true"/>  
  25.     javaModelGenerator>  
  26.   
  27.   
  28.       
  29.         <property name="enableSubPackages" value="true"/>  
  30.     sqlMapGenerator>  
  31.   
  32.   
  33.       
  34.         <property name="enableSubPackages" value="true"/>  
  35.   
  36.           
  37.         <property name="constructorBased" value="false"/>  
  38.   
  39.           
  40.         <property name="ignoreQualifiersAtRuntime" value="false"/>  
  41.   
  42.           
  43.         <property name="immutable" value="false"/>  
  44.   
  45.           
  46.         <property name="modelOnly" value="false"/>  
  47.   
  48.           
  49.         <property name="useActualColumnNames" value="false"/>  
  50.   
  51.   
  52.           
  53.              <property name="property" value="userName"/>  
  54.   
  55.                
  56.         <property name="suppressAllComments" value="true" />  
  57.         commentGenerator>  
  58.           
  59.         <jdbcConnection driverClass="com.mysql.jdbc.Driver"  
  60.             connectionURL="jdbc:mysql://localhost:3306/mybatis" userId="root"  
  61.             password="root">  
  62.         jdbcConnection>  
  63.           
  64.         <javaModelGenerator targetPackage="test.lx.mybatis.po"  
  65.             targetProject="/Users/liuxun/Workspaces/MyEclipse_2017_CI/Mybatis_generatorSqlMapCustom/src">  
  66.               
  67.             <property name="enableSubPackages" value="false" />  
  68.               
  69.             <property name="trimStrings" value="true" />  
  70.         javaModelGenerator>  
  71.           
  72.         <sqlMapGenerator targetPackage="test.lx.mybatis.mapper"   
  73.             targetProject="/Users/liuxun/Workspaces/MyEclipse_2017_CI/Mybatis_generatorSqlMapCustom/src">  
  74.               
  75.             <property name="enableSubPackages" value="false" />  
  76.         sqlMapGenerator>  
  77.           
  78.         <javaClientGenerator type="XMLMAPPER"  
  79.             targetPackage="test.lx.mybatis.mapper"   
  80.             targetProject="/Users/liuxun/Workspaces/MyEclipse_2017_CI/Mybatis_generatorSqlMapCustom/src">  
  81.               
  82.             <property name="enableSubPackages" value="false" />  
  83.         javaClientGenerator>  
  84.           
  85.         <table tableName="items">table>  
  86.         <table tableName="orders">table>  
  87.         <table tableName="orderdetail" >table>  
  88.           
  89.     <typeAliases>  
  90.           
  91.         <package name="test.lx.mybatis.po" />  
  92.     typeAliases>  
  93.   
  94.     <mappers>  
  95.           
  96.         <mapper resource="sqlmap/User.xml" />  
  97.         <package name="test.lx.mybatis.mapper" />  
  98.     mappers>  
  99. configuration>  
applicationContext.xml
[html] view plain copy
  1. xml version="1.0" encoding="UTF-8"?>  
  2. <beans xmlns="http://www.springframework.org/schema/beans"  
  3.     xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:mvc="http://www.springframework.org/schema/mvc"  
  4.     xmlns:context="http://www.springframework.org/schema/context"  
  5.     xmlns:aop="http://www.springframework.org/schema/aop" xmlns:tx="http://www.springframework.org/schema/tx"  
  6.     xsi:schemaLocation="http://www.springframework.org/schema/beans   
  7.         http://www.springframework.org/schema/beans/spring-beans-3.2.xsd   
  8.         http://www.springframework.org/schema/mvc   
  9.         http://www.springframework.org/schema/mvc/spring-mvc-3.2.xsd   
  10.         http://www.springframework.org/schema/context   
  11.         http://www.springframework.org/schema/context/spring-context-3.2.xsd   
  12.         http://www.springframework.org/schema/aop   
  13.         http://www.springframework.org/schema/aop/spring-aop-3.2.xsd   
  14.         http://www.springframework.org/schema/tx   
  15.         http://www.springframework.org/schema/tx/spring-tx-3.2.xsd ">  
  16.       
  17.     <context:property-placeholder location="classpath:db.properties" />  
  18.     <bean id="dataSource" class="org.apache.commons.dbcp.BasicDataSource"  
  19.         destroy-method="close">  
  20.         <property name="driverClassName" value="${jdbc.driver}" />  
  21.         <property name="url" value="${jdbc.url}" />  
  22.         <property name="username" value="${jdbc.username}" />  
  23.         <property name="password" value="${jdbc.password}" />  
  24.         <property name="maxActive" value="10" />  
  25.         <property name="maxIdle" value="5" />  
  26.     bean>  
  27.       
  28.       
  29.     <bean id="sqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean">  
  30.         
  31.       <property name="dataSource" ref="dataSource"/>  
  32.         
  33.       <property name="configLocation" value="classpath:mybatis/SqlMapConfig.xml"/>  
  34.     bean>  
  35.       
  36.       
  37.     <bean id="userDao" class="test.lx.mybatis.dao.UserDaoImpl">  
  38.       <property name="sqlSessionFactory" ref="sqlSessionFactory"/>  
  39.     bean>  
  40.       
  41.       
  42.       
  43.      <bean id="userMapper" class="org.mybatis.spring.mapper.MapperFactoryBean">  
  44.       <property name="mapperInterface" value="test.lx.mybatis.mapper.UserMapper"/>  
  45.       <property name="sqlSessionFactory" ref="sqlSessionFactory"/>  
  46.     bean>   
  47.       
  48.       
  49.       <property name="sqlSessionFactoryBeanName" value="sqlSessionFactory"/>  
  50.     bean>  
  51. beans>  
UserDaoImplTest(测试原始Dao代码)
[java] view plain copy
  1. package test.lx.mybatis.dao;  
  2.   
  3. import java.io.IOException;  
  4. import java.io.InputStream;  
  5.   
  6. import org.apache.ibatis.io.Resources;  
  7. import org.apache.ibatis.session.SqlSessionFactory;  
  8. import org.apache.ibatis.session.SqlSessionFactoryBuilder;  
  9. import org.junit.Before;  
  10. import org.junit.Test;  
  11. import org.springframework.context.ApplicationContext;  
  12. import org.springframework.context.support.ClassPathXmlApplicationContext;  
  13.   
  14. import test.lx.mybatis.po.User;  
  15.   
  16. public class UserDaoImplTest {  
  17.     // 会话工厂  
  18.     private ApplicationContext applicationContext;  
  19.       
  20.     //创建工厂  
  21.     @Before  
  22.     public void init() throws IOException{  
  23.         // 创建Spring容器  
  24.         applicationContext = new ClassPathXmlApplicationContext("spring/applicationContext.xml");  
  25.     }  
  26.       
  27.     @Test  
  28.     public void testFindUserById() throws Exception{  
  29.         UserDao userDao = (UserDao) applicationContext.getBean("userDao");  
  30.         User user = userDao.findUserById(1);  
  31.         System.out.println(user);  
  32.     }  
  33.       
  34. }  
UserMapperTest(测试 mapper代理实现DAO接口的代码)
[java] view plain copy
  1. package test.lx.mybatis.mapper;  
  2.   
  3. import java.io.IOException;  
  4. import org.junit.Before;  
  5. import org.junit.Test;  
  6. import org.springframework.context.ApplicationContext;  
  7. import org.springframework.context.support.ClassPathXmlApplicationContext;  
  8.   
  9. import test.lx.mybatis.po.User;  
  10.   
  11. public class UserMapperTest {  
  12.   
  13.     // 会话工厂  
  14.         private ApplicationContext applicationContext;  
  15.           
  16.         //创建工厂  
  17.         @Before  
  18.         public void init() throws IOException{  
  19.             // 创建Spring容器  
  20.             applicationContext = new ClassPathXmlApplicationContext("spring/applicationContext.xml");  
  21.         }  
  22.   
  23.     @Test  
  24.     public void testFindUserById() throws Exception {  
  25.         UserMapper userMapper = (UserMapper) applicationContext.getBean("userMapper");  
  26.         User user = userMapper.findUserById(1);  
  27.         System.out.println(user);  
  28.     }  
  29.   
  30. }  
ItemsMapperTest(*********测试拷贝逆向工程生成的代码)
[java] view plain copy
  1. package test.lx.mybatis.mapper;  
  2.   
  3. import static org.junit.Assert.*;  
  4.   
  5. import java.util.List;  
  6.   
  7. import org.junit.Before;  
  8. import org.junit.Test;  
  9. import org.springframework.context.ApplicationContext;  
  10. import org.springframework.context.support.ClassPathXmlApplicationContext;  
  11.   
  12. import test.lx.mybatis.po.Items;  
  13. import test.lx.mybatis.po.ItemsExample;  
  14.   
  15. /** 
  16.  * 切记: 
  17.  * 不管是查询还是更新,只要涉及到多条记录 不带withBlobs后缀的方法 默认都不会对大文本字段进行操作 
  18.  * 接口方法名中包含Selective的 表示有选择性的进行操作(只查询、更新、添加为参数复制过的属性对应的字段) 
  19.  * 接口方法名中包含Example的 表示可以带有条件筛选 
  20.  *  
  21.  * @author liuxun 
  22.  * 
  23.  */  
  24. public class ItemsMapperTest {  
  25.     private ApplicationContext applicationContext;  
  26.   
  27.     private ItemsMapper itemsMapper;  
  28.   
  29.     @Before  
  30.     public void setUp() throws Exception {  
  31.         // 创建Spring容器  
  32.         applicationContext = new ClassPathXmlApplicationContext("spring/applicationContext.xml");  
  33.         itemsMapper = (ItemsMapper) applicationContext.getBean("itemsMapper");  
  34.     }  
  35.   
  36.     // 自定义条件筛选数量查询  
  37.     @Test  
  38.     public void testCountByExample() {  
  39.         ItemsExample itemsExample = new ItemsExample();  
  40.         ItemsExample.Criteria criteria = itemsExample.createCriteria();  
  41.         criteria.andPriceBetween(300.f, 10000.f);  
  42.         int count = itemsMapper.countByExample(itemsExample);  
  43.         System.out.println(count);  
  44.     }  
  45.   
  46.     // 自定义条件删除  
  47.     @Test  
  48.     public void testDeleteByExample() {  
  49.         ItemsExample itemsExample = new ItemsExample();  
  50.         ItemsExample.Criteria criteria = itemsExample.createCriteria();  
  51.         criteria.andNameLike("%冰箱%"); // 使用like相关属性时 参数外要包括 %%  
  52.         itemsMapper.deleteByExample(itemsExample);  
  53.     }  
  54.   
  55.     // 根据主键进行删除  
  56.     @Test  
  57.     public void testDeleteByPrimaryKey() {  
  58.         itemsMapper.deleteByPrimaryKey(6);  
  59.     }  
  60.   
  61.     // 表示插入全部字段,若某字段对应属性没有复制,默认插为NULL(自增主键例外)  
  62.     @Test  
  63.     public void testInsert() {  
  64.         Items items = new Items();  
  65.         items.setName("电视机");  
  66.         items.setPrice(3000.f);  
  67.         items.setDetail("乐视高清");  
  68.   
  69.         itemsMapper.insert(items);  
  70.     }  
  71.   
  72.     // 选择性插入,插入记录时只对赋值属性对应的字段进行插入  
  73.     @Test  
  74.     public void testInsertSelective() {  
  75.         Items items = new Items();  
  76.         items.setName("电冰箱");  
  77.         items.setPrice(2500.f);  
  78.         items.setDetail("三年包换");  
  79.   
  80.         itemsMapper.insertSelective(items);  
  81.     }  
  82.   
  83.     // 自定义条件查询多条记录,包含大文本字段  
  84.     @Test  
  85.     public void testSelectByExampleWithBLOBs() {  
  86.         ItemsExample itemsExample = new ItemsExample();  
  87.         ItemsExample.Criteria criteria = itemsExample.createCriteria();  
  88.         criteria.andNameIsNotNull();  
  89.         List list = itemsMapper.selectByExampleWithBLOBs(itemsExample);  
  90.         for (Items items : list) {  
  91.             System.out.println(items.getDetail());  
  92.         }  
  93.     }  
  94.   
  95.     // 自定义条件查询多条记录,不对大文本字段进行查询  
  96.     @Test  
  97.     public void testSelectByExample() {  
  98.         ItemsExample itemsExample = new ItemsExample();  
  99.         ItemsExample.Criteria criteria = itemsExample.createCriteria();  
  100.         criteria.andNameIsNotNull();  
  101.         List list = itemsMapper.selectByExample(itemsExample);  
  102.         for (Items items : list) {  
  103.             System.out.println(items.getDetail()); // 大文本字段值为null  
  104.         }  
  105.   
  106.     }  
  107.   
  108.     // 按照主键值进行查询单条记录  
  109.     @Test  
  110.     public void testSelectByPrimaryKey() {  
  111.         Items items = itemsMapper.selectByPrimaryKey(1);  
  112.         System.out.println(items.getDetail());  
  113.     }  
  114.   
  115.     // 自定义条件更新(为POJO赋值过的属性对应的字段),不对PO类中的大文本字段进行更新  
  116.     // 如果PO类对象中的一些属性未赋值,不做任何改变,只更新赋值过的属性 即有选择性的更新  
  117.     @Test  
  118.     public void testUpdateByExampleSelective() {  
  119.         // 此处方法名后缀Selective:表示只对参数record中设置过的属性对应的字段进行更新 没有设置过的不做任何改变  
  120.         // record:封装更新后的结果值   
  121.         // example: 封装 筛选更新记录条件  
  122.         ItemsExample example = new ItemsExample();  
  123.         ItemsExample.Criteria  criteria = example.createCriteria();  
  124.         Items record = new Items();  
  125.         record.setPrice(2500.f);  
  126.         criteria.andNameLike("%机%");  
  127.         itemsMapper.updateByExampleSelective(record, example);  
  128.     }  
  129.   
  130.     // 根据外键强制全部更新数据(没有赋值的映射为NULL) 包含大文本字段  
  131.     @Test  
  132.     public void testUpdateByExampleWithBLOBs() {  
  133.   
  134.     }  
  135.   
  136.     // 根据外键强制全部更新数据(没有赋值的映射为NULL) 不包含大文本字段  
  137.     @Test  
  138.     public void testUpdateByExample() {  
  139.   
  140.     }  
  141.   
  142.     // 根据外键有选择性的更新数据 不包含大文本字段 必须为参数items设置主键值  
  143.     @Test  
  144.     public void testUpdateByPrimaryKeySelective() {  
  145.   
  146.     }  
  147.     // 根据外键全部更新数据(没有赋值的映射为NULL) 包含大文本字段 必须为参数items设置主键值  
  148.     @Test  
  149.     public void testUpdateByPrimaryKeyWithBLOBs() {  
  150.   
  151.     }  
  152.     // 根据外键有全部更新数据(没有赋值的映射为NULL) 不包含大文本字段 必须为参数items设置主键值  
  153.     @Test  
  154.     public void testUpdateByPrimaryKey() {  
  155.   
  156.     }  
  157.   

你可能感兴趣的:(mybatis)