Java框架之MyBatis框架(二)

  Mybatis框架是相对于优化dao层的框架,其有效的减小了频繁的链接数据库(在配置文件xml中进行配置),将sql语句与java代码进行分离(写在XXXXmapper.xml文件中,一个表对应一个xml文件),有效的处理了各类条件(定义了输入类型pojo)而且将结果又映射到java对象中(定义了输出类型)。须要注意的是每一个表对应的xml文件的地址须要在配置文件中进行配置(能够指引整个文件夹),当使用动态代理的接口mapper时,须要注意好其的四个规范!而且其能够将查询及输出结果封装到一个类,并提供了if、where、foreach标签进行优化。java

1、输入类型优化:mysql

开发中经过可使用pojo传递查询条件。sql

查询条件多是综合的查询条件,不只包括用户查询条件还包括其它的查询条件(好比查询用户信息的时候,将用户购买商品信息也做为查询条件),这时可使用包装对象传递输入参数。数据库

包装对象:Pojo类中的一个属性是另一个pojo。数组

 

需求:根据用户名模糊查询用户信息,查询条件放到QueryVo的user属性中。mybatis

package com.oracle.pojo;

public class QueryVo {
    private User user;

    public User getUser() {
        return user;
    }

    public void setUser(User user) {
        this.user = user;
    }

    @Override
    public String toString() {
        return "QueryVo [user=" + user + "]";
    }
    
}

2、输出类型优化:oracle

  resultType能够指定将查询结果映射为pojo,但须要pojo的属性名和sql查询的列名一致方可映射成功。app

        若是sql查询字段名和pojo的属性名不一致,能够经过resultMap将字段名和属性名做一个对应关系 ,resultMap实质上还须要将查询结果映射到pojo对象中。框架

        resultMap能够实现将查询结果映射为复杂类型的pojo,好比在查询结果映射对象中包括pojo和list实现一对一查询和一对多查询。ide

3、动态Sql:

经过mybatis提供的各类标签方法实现动态拼接sql:if/where/foreach

<!--根据姓名和性别查询用户  使用where标签代替之前的 1=1 再加上if这样就能够即便没有一个条件同样能够执行sql语句或者有其中一个!-->
    <select id="getUserBySexAndUserName" parameterType="user" resultType="user">
            <!-- include标签加载sql片断,后面是其片断的id -->
        <include refid="get"></include>
        <!-- where标签:一是添加关键字where,二是处理第一个and关键字 -->
    <where>
    <if test="username!=null and username!=''">
             and username like "%"#{username}"%" 
    </if>
    <if test="sex!=null and sex!=''">
             and sex =#{sex} 
    </if>
    </where>
    </select>
    <!--SQL片断  -Sql中可将重复的sql提取出来,使用时用include引用便可,最终达到sql重用的目的。通常用于表链接时查询多个字段的时候-->
    <sql id="get">
        select * from user 
    </sql>
    <!-- 根据多个条件查询 -->
    <select id="getUserByQuery" parameterType="Query" resultType="user">
    select * from user where id in
        <!-- foreach标签,进行遍历 -->
        <!-- collection:遍历的集合,这里是Query的ids属性 -->
        <!-- item:遍历的项目,能够随便写,可是和后面的#{}里面要一致 -->
        <!-- open:在前面添加的sql片断 -->
        <!-- close:在结尾处添加的sql片断 -->
        <!-- separator:指定遍历的元素之间使用的分隔符 -->
    <foreach collection="ids" item="i" open="(" close=")" separator=",">
        #{i}
    </foreach>
    </select>
    

Sql片断:sql中可将重复的sql提取出来,使用时用include引用便可,最终达到sql重用的目的。

    若是要使用别的Mapper.xml配置的sql片断,能够在refid前面加上对应的Mapper.xml的namespace。

foreach标签:向sql传递数组或List,mybatis使用foreach解析。

4、关联查询:

一、一对一查询:

<!--查询全部的订单信息以及其关联的用户信息  -->
        <!-- 由于两个表是一对一!为使用resultMap,因此在orders下添加私有的User类对应的user属性,由于没法将数据映射到user里面
        因此开始下面的手动映射 -->
    <resultMap type="orders" id="orderUserResultMap">
    <id property="id" column="id" />
    <result property="userId" column="user_id" />
    <result property="number" column="number" />
    <result property="createtime" column="createtime" />
    <result property="note" column="note" />

    <!-- association :配置一对一属性 -->
    <!-- property:order里面的User属性名 -->
    <!-- javaType:属性类型 -->
    <association property="user" javaType="user">
        <!-- id:声明主键,表示user_id是关联查询对象的惟一标识-->
        <id property="id" column="user_id" />
        <result property="username" column="username" />
        <result property="address" column="address" />
    </association>

</resultMap>

<!-- 一对一关联,查询订单,订单内部包含用户属性 -->
<select id="getOrdersUser" resultMap="orderUserResultMap">
    SELECT
    o.id,
    o.user_id userId,
    o.number,
    o.createtime,
    o.note,
    u.username,
    u.address
    FROM
    `orders` o
    LEFT JOIN `user` u ON o.user_id = u.id
</select>

二、一对多查询:

<!-- 查询全部的用户信息以及对应的订单信息 -->
    <resultMap type="user" id="getAllUser">
        <id property="id" column="id"/>
        <result property="username" column="username"/>
        <result property="birthday" column="birthday"/>
        <result property="sex" column="sex"/>
        <result property="address" column="address"/>
        <!--一对多的关系    property是指集合的属性名字  javaType是指类型   ofType是泛型的意思-->
        <collection property="list" javaType="list" ofType="orders">
            <!-- 配置主键,是关联Order的惟一标识 -->
            <id property="id" column="oid"/>
            <result property="number" column="number"/>
            <result property="createtime" column="createtime"/>
            <result property="note" column="note"/>
        </collection>
    </resultMap>
    <select id="getUserOrders" resultMap="getAllUser">
    SELECT
        u.id,
        u.username,
        u.birthday,
        u.sex,
        u.address,
        o.id oid,
        o.number,
        o.createtime,
        o.note
    FROM
        `user` u
    LEFT JOIN `orders` o ON u.id = o.user_id
        
    
    </select>
public class User {
    private Integer id;
    private String username;
    private String birthday;
    private String sex;
    private String address;
    private List<Orders> list;//一对多,得list

5、逆向工程:

一、导入:

二、修改:

generatorConfig.xml中配置Mapper生成的详细信息:

  注意:

  1. 修改要生成的数据库表
  2. pojo文件所在包路径
  3. Mapper所在的包路径
    <?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>
        <context id="testTables" targetRuntime="MyBatis3">
            <commentGenerator>
                <!-- 是否去除自动生成的注释 true:是 : false:否 -->
                <property name="suppressAllComments" value="true" />
            </commentGenerator>
            <!--数据库链接的信息:驱动类、链接地址、用户名、密码 -->
            <jdbcConnection driverClass="com.mysql.jdbc.Driver"
                connectionURL="jdbc:mysql://localhost:3306/mybatis" userId="root" password="root">
            </jdbcConnection>
            <!-- <jdbcConnection driverClass="oracle.jdbc.OracleDriver" connectionURL="jdbc:oracle:thin:@127.0.0.1:1521:yycg" 
                userId="yycg" password="yycg"> </jdbcConnection> -->
    
            <!-- 默认false,把JDBC DECIMAL 和 NUMERIC 类型解析为 Integer,为 true时把JDBC DECIMAL 
                和 NUMERIC 类型解析为java.math.BigDecimal -->
            <javaTypeResolver>
                <property name="forceBigDecimals" value="false" />
            </javaTypeResolver>
    
            <!-- targetProject:生成PO类的位置 -->
            <javaModelGenerator targetPackage="cn.oracle.ssm.po"
                targetProject=".\src">
                <!-- enableSubPackages:是否让schema做为包的后缀 -->
                <property name="enableSubPackages" value="false" />
                <!-- 从数据库返回的值被清理先后的空格 -->
                <property name="trimStrings" value="true" />
            </javaModelGenerator>
            <!-- targetProject:mapper映射文件生成的位置 -->
            <sqlMapGenerator targetPackage="cn.oracle.ssm.mapper"
                targetProject=".\src">
                <!-- enableSubPackages:是否让schema做为包的后缀 -->
                <property name="enableSubPackages" value="false" />
            </sqlMapGenerator>
            <!-- targetPackage:mapper接口生成的位置 -->
            <javaClientGenerator type="XMLMAPPER"
                targetPackage="cn.oracle.ssm.mapper" targetProject=".\src">
                <!-- enableSubPackages:是否让schema做为包的后缀 -->
                <property name="enableSubPackages" value="false" />
            </javaClientGenerator>
            <!-- 指定数据库表 -->
            <table schema="" tableName="user"></table>
            <table schema="" tableName="order"></table>
        </context>
    </generatorConfiguration>

     

三、生成逆向代码:

运行GeneratorSqlmap.java!

生成pojo、mapper!

 

注意:

1. 逆向工程生成的代码只能作单表查询

2. 不能在生成的代码上进行扩展,由于若是数据库变动,须要从新使用逆向工程生成代码,原来编写的代码就被覆盖了。

3. 一张表会生成4个文件

相关文章
相关标签/搜索