Mybatis底层原理(二)SqlSession运行过程

1.SqlSession是一个接口,包含了查询、修改、插入、删除的方法。我们既可以直接使用这些方法也可以使用Mapper来代理使用这些方法。

1.1 Mapper的动态代理

1.1.1 Mapper映射是通过动态代理来实现的,我们来看下MapperProxyFactory部分源码:

public class MapperProxyFactory<T>
/*    */ {
/*    */   private final Class<T> mapperInterface;
/* 28 */   private Map<Method, MapperMethod> methodCache = new ConcurrentHashMap();
/*    */ 
/*    */   public MapperProxyFactory(Class<T> mapperInterface) {
/* 31 */     this.mapperInterface = mapperInterface;
/*    */   }
/*    */ 
/*    */   public Class<T> getMapperInterface() {
/* 35 */     return this.mapperInterface;
/*    */   }
/*    */ 
/*    */   public Map<Method, MapperMethod> getMethodCache() {
/* 39 */     return this.methodCache;
/*    */   }
/*    */ 
/*    */   protected T newInstance(MapperProxy<T> mapperProxy)
/*    */   {
/* 44 */     return Proxy.newProxyInstance(this.mapperInterface.getClassLoader(), new Class[] { this.mapperInterface }, mapperProxy);
/*    */   }
/*    */ 
/*    */   public T newInstance(SqlSession sqlSession) {
/* 48 */     MapperProxy mapperProxy = new MapperProxy(sqlSession, this.mapperInterface, this.methodCache);
/* 49 */     return newInstance(mapperProxy);
/*    */   }
/*    */ }

可以看到动态代理对接口的绑定,他的作用就是生成动态代理对象,而代理的方法则被放到了MapperProxy中;

1.1.2 查看MapperProxy的部分源码:

public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
/* 39 */     if (Object.class.equals(method.getDeclaringClass())) {
/* 40 */       return method.invoke(this, args);
/*    */     }
/* 42 */     MapperMethod mapperMethod = cachedMapperMethod(method);
/* 43 */     return mapperMethod.execute(this.sqlSession, args);
/*    */   }
/*    */ 
/*    */   private MapperMethod cachedMapperMethod(Method method) {
/* 47 */     MapperMethod mapperMethod = (MapperMethod)this.methodCache.get(method);
/* 48 */     if (mapperMethod == null) {
/* 49 */       mapperMethod = new MapperMethod(this.mapperInterface, method, this.sqlSession.getConfiguration());
/* 50 */       this.methodCache.put(method, mapperMethod);
/*    */     }
/* 52 */     return mapperMethod;
/*    */   }
一旦mapper是个代理对象,那么它会调用invoke方法,首先判断他是否是一个类,若不是则会生成MapperMethod对象,他是通过cachedMapperMethod方法初始化,然后执行execute方法把sqlSession和当前运行参数传入。

再看execute方法里面做了什么:

 public Object execute(SqlSession sqlSession, Object[] args)
/*     */   {
/*     */     Object result;
/*  44 */     if (SqlCommandType.INSERT == this.command.getType()) {
/*  45 */       Object param = this.method.convertArgsToSqlCommandParam(args);
/*  46 */       result = rowCountResult(sqlSession.insert(this.command.getName(), param));
/*     */     }
/*     */     else
/*     */     {
/*     */       Object result;
/*  47 */       if (SqlCommandType.UPDATE == this.command.getType()) {
/*  48 */         Object param = this.method.convertArgsToSqlCommandParam(args);
/*  49 */         result = rowCountResult(sqlSession.update(this.command.getName(), param));
/*     */       }
/*     */       else
/*     */       {
/*     */         Object result;
/*  50 */         if (SqlCommandType.DELETE == this.command.getType()) {
/*  51 */           Object param = this.method.convertArgsToSqlCommandParam(args);
/*  52 */           result = rowCountResult(sqlSession.delete(this.command.getName(), param));
/*     */         }
/*     */         else
/*     */         {
/*     */           Object result;
/*  53 */           if (SqlCommandType.SELECT == this.command.getType())
/*     */           {
/*     */             Object result;
/*  54 */             if ((this.method.returnsVoid()) && (this.method.hasResultHandler())) {
/*  55 */               executeWithResultHandler(sqlSession, args);
/*  56 */               result = null;
/*     *
  • 3
    点赞
  • 7
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值