浅显的理解Beetlsql源码

理解与springboot结合的Beetlsql源码

首先,我们要引入两个Bean,一个SqlManagerFactoryBean和BeetlSqlScannerConfigurer。

我们再看下这两个类的组件:
SqlManagerFactoryBean的 组件
SqlManagerFactoryBean:是一个工厂bean,用于创建一个叫做SqlManager的对象,这个对象很重要,之后会详细进行讲解。

  /**
     * BeetlSql数据源,用于封装DataSource的,可以指定主从数据源
     */
	BeetlSqlDataSource cs;
    /**
     * 数据库样式-MySqlStyle、OracleStyle等等,都集成的是DBStyle
     */
    DBStyle dbStyle;
    /**
     * 名称转换样式,顾名思义就是对数据库中的属性进行转换、UnderlinedNameConversion、DefaultNameConversion等等
     */
    NameConversion nc;
    /**
     * 拦截器
     */
    Interceptor[] interceptors;
    /**
     * BeetlSql核心类
     */
    SQLManager sqlManager;
    
    /**
     * 对指定的路径的md文件进行加载操作
     */
    SQLLoader sqlLoader;

BeetlSqlScannerConfigurer组件
BeetlSqlScannerConfigurer:它主要继承了一个接口,叫做BeanDefinitionRegistryPostProcessor的一个后置处理器和设置一个ApplicationContextAware等等。
BeetlSqlScannerConfigurer的基本属性

 	/**
     * 基本包,用于指定在该基本包路径下进行扫描,可以支持;空格,等分割多个包
     */
    String basePackage;
    
    String daoSuffix="Dao";
    /**
     * Spring上下文
     */
    ApplicationContext applicationContext;
    /**
     * Bean名称
     */
    String beanName;

    BeanNameGenerator nameGenerator;
    /**
     * sqlManagerFactoryBean名称
     */
    String sqlManagerFactoryBeanName;

下面我们深入的讲解下其创建流程和使用流程。
创建流程-即对象的生成流程
1.通过BeetlSqlScannerConfigurer这个后置处理器的postProcessBeanDefinitionRegistry方法
2.利用BeetlSqlClassPathScanner的scan扫描特定的包,然后找出指定后缀的相应的接口,然后往容器中注册BeetlSqlFactoryBean类的工厂bean(即生成相应BeanDefinition),这个工厂bean即在自动注入的时候,通过getObject方法获取相应的对象。
3.其中getObject方法,就是通过SqlManager的getMapper方法获取相应的代理对象(jdk代理)
4.然后其代理执行类为MapperJavaProxy,即实现了InvocationHandler方法
使用流程-即解析sql到发送sql到数据库的整个流程

@Override
    public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
        Class caller = method.getDeclaringClass();
        String methodName = method.getName();
        if(methodName.equals("toString")){
        	return "BeetlSql Mapper "+mapperInterface;
        }
        SqlResource resource = (SqlResource)this.mapperInterface.getAnnotation(SqlResource.class);
        String sqlId = null;
        if(resource!=null){
        		String preffix = resource.value();
        		String name = method.getName();
        		sqlId = preffix+"."+name;
        }else{
        		sqlId = this.builder.getIdGen().getId(method.getDeclaringClass(),entityClass, method);  
        }
        MapperInvoke invoke = sqlManager.getMapperConfig().getAmi(caller, methodName);
        if (invoke != null) {
            //内置的方法,直接调用Invoke
            return invoke.call(this.sqlManager, this.entityClass, sqlId, method, args);

        } else {
            //解析方法以及注解,找到对应的处理类
            MethodDesc desc = MethodDesc.getMetodDesc(sqlManager, this.entityClass, method, sqlId);
            if (desc.sqlReady.length() == 0) {
                invoke = MapperInvokeDataConfig.getMethodDescProxy(desc.type);
                Object ret = invoke.call(this.sqlManager, this.entityClass, sqlId, method, args);
                return ret;
            } else {
                invoke = MapperInvokeDataConfig.getSQLReadyProxy();;
                Object ret = invoke.call(this.sqlManager, this.entityClass, desc.sqlReady, method, args);
                return ret;
            }
        }
    }

其实最终都是调用的是SqlManager的对象。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值