配置驼峰命名打开的“东窗”

一、记一个配置驼峰映射而踩的坑

背景

因为建立的表的字段与实体类都遵循驼峰命名规则,在Mybatis使用时想省去建立映射。如:lm_loan.loan_no 与实体类LmLoan.loanNo 就满足规则。

bu t 好好的接口突然出现系统的接口,分页失效 经过一系列查找,定位到是因为自己配置驼峰命名映射的 ,导致分页配置没生效。

代码如下:

image-20210113220344625

但是如果将上面两段代码调换位置如下,驼峰分页配置就能能生效。

image-20210113220836083

what 还能这样,这不合理啊,不讲武德啊…,,进过分析后,整理整理如下

这种配置代码,自己之前都会是参考网上的博客,或者小demo,屡试不爽,但是这次怎么就掉坑里了呢? 害 大意了 没有闪

二、QA问题

Q1、为什么出现上面的现象,也就掉换一下配置的代码就能生效?

A1: 与何时第一次执行sessionFactory.getObject()有关;

分析:当我们将驼峰命名的配置放到设置分页配置的前面时, 是设置驼峰那行代码是首次调用getObject()方法,代码如下:

    public SqlSessionFactory getObject() throws Exception {
        if (this.sqlSessionFactory == null) {
          // 这里会进行参数属性设置,然后构建出一个SqlSessionFactory 赋值给当前类的sqlSessionFactory属性
            this.afterPropertiesSet();
        }

        return this.sqlSessionFactory;
    }

afterPropertiesSet设置代码如下:

image-20210114093407397

也就是说这个工厂SqlSessionFactory只会初始化一次,第二次调用getObject()时,工厂已经被初始化了,所以会返回第一次生成的SqlSessionFactory,虽然设置了分页属性,但是构建的工厂其实没有分页插件属性

我的写的坑货代码执行逻辑大致如下:

image-20210113235130987

buildSqlSessionFactory()的方法主要就是进行将基础设置封装成Configuration源码如下:

    protected SqlSessionFactory buildSqlSessionFactory() throws IOException {
			/**省略了部分代码**/
      // 1、根据配置的mapper 扫描路径解析xml 或者mapper文件;mapperLocation也就是配置的扫描路径
        XMLMapperBuilder xmlMapperBuilder = new XMLMapperBuilder(mapperLocation.getInputStream(), configuration, mapperLocation.toString(), configuration.getSqlFragments());
                        xmlMapperBuilder.parse();
      
      // 2、注册加载插件信息;(配置的分页插件拦截器也就此处加载)
      Interceptor plugin = var26[var5];
                configuration.addInterceptor(plugin);
                if (LOGGER.isDebugEnabled()) {
                    LOGGER.debug("Registered plugin: '" + plugin + "'");
                }
      // 返回一个构造的DefaultSqlSessionFactory,所有的配置信息,就在configuration当中
     return this.sqlSessionFactoryBuilder.build(configuration); 
      /**省略了部分代码**/
    }

  • 修改

所以将驼峰设置的代码放到最后一行后,等第一次执行getObject()方法时,分页的参数已经设置,构建的工厂bean也就有该分页属性了。而驼峰需要设置的参数map-underscore-to-camel-case 通过拿到Configuration的引用设置进去即可。

  • 或者直接自己提前构造一个Configuration 设置驼峰属性。之后构造工厂后也就可以生效

    // 因为与@Configuration 类名相同,所以需要使用全类名
    org.apache.ibatis.session.Configuration configuration = new org.apache.ibatis.session.Configuration();
    configuration.setMapUnderscoreToCamelCase(true);
    sessionFactory.setConfiguration(configuration);
    

Q2、为什么不直接通过配置YML开启驼峰命名?
mybatis:
  configuration:
    map-underscore-to-camel-case : true

A2: 这种配置不会生效

这样确实简单方便,但是这样的前提是需要SqlSessionFactory这个类是由Mybatis的自动配置类生成。但是上面的SqlSessionFactory 是我们自己构造加入容器当中。所以这种配置不会生效。

原因:Mybatis的自动配置类MybatisAutoConfiguration中有下面一段代码

image-20210113230558356

@ConditionalOnMissingBean 注解表示当容器不存在这个类型的bean,才会进行下面这个自动配置。通过YML配置mybatis.configuration.map-underscore-to-camel-case = true 是通过属性绑定到属性类MybatisProperties中,然后设置到

configuration中从而生效。既然都没执行这代码,所以也就不会生效了。


小结

  • 尽管是配置类的代码,还是不能盲目参考网上的代码,可能因为自己项目配置的不同,而产生特殊的效果----产生bu g
  • 要知其然,也要尽量去知其所以然,多了解底层的原理,能更好的思考问题;
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 2
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值