mybatis学习笔记5:连接池和事务控制、动态SQL语句

一、连接池简介

  • 连接池就是用于存储连接的一个容器
  • 容器其实就是一个集合,只是该集合必须是线程安全的,不允许两个线程拿到同一个连接
  • 该集合还必须满足队列的特性:先进先出

二、mybatis中的连接池

1.两种基本方式

1.1POOLED

  • 采用传统的javax.sql.DataSource规范中的连接池,mybatis中有针对规范的实现
  • 配置方式
    在这里插入图片描述

1.2UNPOOLED

  • 采用传统的获取连接的方式,虽然也实现Javax.sql.DataSource接口,但是并没有使用池的思想。
  • 配置方式
    在这里插入图片描述

2.两种方式的区别

在这里插入图片描述

3.UNPOOLED实现细节

  • 利用cltr+n搜索unpooled查看源码
    在这里插入图片描述
  • 找到getConnection然后按照如下顺序追踪源码
    在这里插入图片描述- 发现这种方式获取连接的思路就和利用JDBC获取连接一样

4.POOLED实现细节(推荐使用)

  • 同样的方式,找到pooled的相关源码,找打getConnection函数
    在这里插入图片描述
  • 也就是说mybatis在这种方式中,设置了两个连接池
    在这里插入图片描述- 所以实际开发中使用POOLED方式

三、mybatis中的事务控制的设置(暂时了解)

1、四大相关问题

  • 什么是事务
  • 事务的四大特性ACID
  • 不考虑隔离性会产生的3个问题
  • 解决办法:四种隔离级别

2.实现方式

  • 它是通过sqlsession对象的commit方法和rollback方法实现事务的提交和回滚

3.细节分析

分析出事务提交和回滚的最终执行代码

  • 它是通过sqlsession对象的commit方法和rollback方法实现事务的提交和回滚
  • 那根据前面的学习知道sqlsession只是接口,这里是DefaultSqlSession类实现了它,下面进入这个类,找到相关方法
    在这里插入图片描述- 进入executor
    在这里插入图片描述- 同样根据前文的学习,这里应该是BaseExecutor类实现了这个接口,下面进入这个类

在这里插入图片描述

  • 进入Transaction接口,进一步进入JdbcTransaction实现类

在这里插入图片描述

  • 继续进入connection,发现都是使用的java本身的sql相关的包
    在这里插入图片描述

3.手动提交事务配置

在这里插入图片描述

  • 每次执行,日志会打印输出,表示是手动提交

在这里插入图片描述

4.自动提交事务配置

  • 查看openssion方法
    在这里插入图片描述
  • 设置
    在这里插入图片描述

四、动态SQL语句

1.if标签

  • dao接口新增按条件查询方法
/**
     * 条件查询
     * user 可能只有用户名 或者其他
     * @param user
     * @return
     */
    List<User> findUserByCondition(User user);
  • 映射配置文件中新增配置

    <select id="findUserByCondition" resultType="User" parameterType="User">
          select * from user where 1 = 1
          <if test="username!=null">
              and username = #{username}
          </if>

    </select>
  • 注意点
    在这里插入图片描述- 同理,如果有多个条件,则多加几条if即可
    <select id="findUserByCondition" resultType="User" parameterType="User">
          select * from user where 1 = 1
          <if test="username!=null">
              and username = #{username}
          </if>
          <if test="sex != null">
            and sex = #{sex}
          </if>
    </select>

2.where标签

可以去除只使用if标签时,必须写where 1=1

    <select id="findUserByCondition" resultType="User" parameterType="User">
        select * from user
        <where>
            <if test="username!=null">
            and username = #{username}
            </if>
            <if test="sex != null">
            and sex = #{sex}
            </if>
        </where>
    </select>

3.foreach标签

问题引入

  • 如何通过mybatis实现select * from user where id in(41,42,49)呢?
  • 就是这种带有一个查询范围的情况如何实现呢?foreach标签就是解决这个问题的

代码解决

  • QueryVo中定义相关属性

public class QueryVo {

    private User user;
    List<Integer> ids;
    public List<Integer> getIds() {
        return ids;
    }

    public void setIds(List<Integer> ids) {
        this.ids = ids;
    }
    public User getUser() {
        return user;
    }

    public void setUser(User user) {
        this.user = user;
    }
}
  • dao接口定义相关方法
   /**
     * 根据queryvo完成查询
     * @param queryVo
     * @return
     */
    List<User> findUserByQueryVo(QueryVo queryVo);
  • 映射配置文件相关配置
   <select id="findUserInIds" resultType="user" parameterType="user"  >
        select * from user
        <where>
            <if test="ids !=null and ids.size()>0">
                <foreach collection="ids" open="and id in (" close=")" item="uid" separator=",">
                    #{uid}
                </foreach>

            </if>

        </where>

    </select>
  • 测试类进行测试

    @Test
    public void testFindUserInIds(){
        QueryVo queryVo = new QueryVo();
        List<Integer> ids = new ArrayList<Integer>();
        ids.add(41);
        ids.add(42);
        ids.add(43);
        queryVo.setIds(ids);


        List<User> users = userDao.findUserInIds(queryVo);
        for (User item : users) {
            System.out.println(item);
        }
    }
  • 结果
    在这里插入图片描述- foreach使用注意点
    在这里插入图片描述

4.简化sql语句的标签:sql

  • 在映射配置文件中,有大量的重复的sql语句,这个可以通过sql标签来一次定义,多出使用
    在这里插入图片描述- 基本使用
 <sql id="selectAllUser">
        select  * from user;
    </sql>

在这里插入图片描述- 测试类测试通过

1.一个容易报错的细节

  • 继续上述的使用,这次使用在上述配置中
    <!-- 根据queryvo中的Id集合实现查询用户列表 -->
    <select id="findUserInIds" resultType="user" parameterType="user"  >
        <!--select * from user-->
        <include refid="selectAllUser"></include>
        <where>
            <if test="ids !=null and ids.size()>0">
                <foreach collection="ids" open="and id in (" close=")" item="uid" separator=",">
                    #{uid}
                </foreach>
            </if>
        </where>

    </select>
  • 运行测试类,发现报错
    在这里插入图片描述- 这是因为在定义sql标签中的sql语句时加了;
    在这里插入图片描述
  • 去掉;后再运行测试类,可以通过
  • 以后配置映射文件中的所有sql都不建议加分号
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值