Mapper接口
来源:互联网 发布:万达怎么了 知乎 编辑:程序博客网 时间:2024/05/26 07:30
title:Mapper接口
date:2017年11月25日17:27:07
categories: Mybatis
前言
之前在说到Mybatis插件的时候说以后要好好分析下Mybatis的四大组件,之前一直在为公司忙搭建RocketMQ消息集群的事情,就耽误了一段时间,最近终于有时间来分析下了,要分析四大组件,还是要从一次完整的查询过程说起,把Mybatis的核心源码都过一遍。
从一次查询说起
我们做一次Mybatis的查询测试
@Test public void testSelect() { SqlSession session = null; try { session = MybatisUtil.getCurrentSession(); UserDao userDao = session.getMapper(UserDao.class); List<Integer> list = new ArrayList<Integer>(); list.add(1); list.add(3); list.add(25); List<User> userList = userDao.queryList(list); System.out.println(JSON.toJSONString(userList)); } catch (Exception e) { // TODO: handle exception } finally { if (session != null) session.close(); } }
对应的Mapper配置文件
<?xml version="1.0" encoding="UTF-8"?><!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd"><mapper namespace="com.wangcc.mybatis.dao.UserDao"><resultMap type="User" id="UserMapper"><result property="id" column="t_id"/><result property="name" column="t_name"/></resultMap><select id="queryList" resultMap="UserMapper">select * from t_user where t_id in <foreach collection="list" item="uId" index="index" open="(" separator="," close=")">#{uId}</foreach></select><insert id="insert" parameterType="User">insert into t_user (t_name,address) values(#{name},#{address})</insert><insert id="batchInsert" >insert into t_user (t_name,address) values <foreach collection="list" item="user" separator=",">(#{user.name},#{user.address})</foreach></insert></mapper>
如果你是初次使用Mybatis,那么你一定会好奇为什么这里的UserDao都是接口并不是具体的实现类。
而如果你熟悉JDK动态代理,那么一看到这种接口可以直接执行方法的情况,那么肯定是用了代理,那么虽然我们能够知道为什么可以直接执行,但是我们也要了解他具体是怎么实现的。我们就以
UserDao userDao = session.getMapper(UserDao.class);
为Debug入口。
进入getMapper方法
public <T> T getMapper(Class<T> type) { return configuration.<T>getMapper(type, this); }
我们发现还是调用了构建SqlSession的最重要的对象Configuration的方法。
DefaultSqlSession对象中保存着Configuration对象的引用。
进入到Configuration中
public <T> T getMapper(Class<T> type, SqlSession sqlSession) { return mapperRegistry.getMapper(type, sqlSession); }
我们发现是调用的MapperRegistry对象(Configuration保存着其引用,在初始化Mybatis的配置文件的时候,就会将所有的Mapper接口注册到MapperRegistry的Map\
public <T> T getMapper(Class<T> type, SqlSession sqlSession) { //在knownMappers中查找是否已经注册了,如果没有注册直接抛出异常,注册Mapper接口是在初始化Mybatis配置文件时必须就要完成的工作,不能在调用getMapper的时候再动态去注册 final MapperProxyFactory<T> mapperProxyFactory = (MapperProxyFactory<T>) knownMappers.get(type); if (mapperProxyFactory == null) throw new BindingException("Type " + type + " is not known to the MapperRegistry."); try { return mapperProxyFactory.newInstance(sqlSession); } catch (Exception e) { throw new BindingException("Error getting mapper instance. Cause: " + e, e); } }
进入newInstance方法
public T newInstance(SqlSession sqlSession) { //封装了一个MapperProxy对象,即组合模式,为了解耦,我们一般能不用继承就不用继续,尽量使用组合,这里MapperProxy是实现了InvocationHandler接口的类 final MapperProxy<T> mapperProxy = new MapperProxy<T>(sqlSession, mapperInterface, methodCache); return newInstance(mapperProxy); }
newInstance(mapperProxy) 得到Mapper接口的代理对象
@SuppressWarnings("unchecked") protected T newInstance(MapperProxy<T> mapperProxy) { return (T) Proxy.newProxyInstance(mapperInterface.getClassLoader(), new Class[] { mapperInterface }, mapperProxy); }
到现在,如何得到Mapper接口的代理对象的流程就走完了
阅读全文
0 0
- Mapper接口
- [mybatis]Mapper接口代理开发
- MyBatis Mapper接口实现原理
- [Mybatis] Mapper接口原理分析
- mybatis mapper接口代理开发
- mybatis 中的mapper接口问题
- Mabatis接口之Mapper接口开发
- doMoreDoBetter利用mybatis生成pojo、mapper接口、mapper XML文件
- 基于注解的Mybatis mapper 接口注意事项
- myBatis mapper接口方法重载问题
- Mabatis自动生成entity和mapper接口
- mybatis mapper接口要不要抛出异常
- Mybatis 用接口实现Mapper的操作
- mybatis使用mapper接口生成实现类
- spring mybatis mapper接口注解方式注入
- myBatis Mapper接口注入null指针
- Mybatis-Dao层开发之Mapper接口
- Mybatis续、Mapper映射器接口规则
- Action类的三种编写方式(七)
- Leetcode:Word Ladder II
- 课堂总结
- 模拟实现strlen、strcpy、strcmp、strncmp等字符串函数
- msp430g2553的IIC通信
- Mapper接口
- java 动态绑定
- poj 3469 Dual Core CPU
- 程序员进阶清单 | 每天用干货喂饱你
- ParameterHandler
- 吴家坟女子专修学院郭杜校区计算机分院的学年总结
- Spring学习笔记-Core模块
- Java intern方法的用法
- 复变函数第三章-复变函数的积分