责编:保安队长
配图: 猫仙大人
关于 SQL 和 ORM 的争论,永远都不会终止,我也一直在思考这个问题。昨天又跟群里的小伙伴进行了一番讨论,感触还是有一些,于是就有了今天这篇文。
声明:本文不会下关于 Mybatis 和 JPA 两个持久层框架哪个更好这样的结论。只是摆事实,讲道理,所以,请各位看官勿喷。
关于 Mybatis 和 JPA 孰优孰劣的问题,争论已经很多年了。一直也没有结论,毕竟每个人的喜好和习惯是大不相同的。我也看过知乎上一些问答,各有各的理由,感觉都挺有道理。如果让我不带感情色彩地去分辨,其实我也是懵的,因为真的是公说公有理婆说婆有理。
而在国内,不得不承认,到今年( 2019 年),用 Mybatis 的公司确实是要比用 JPA 的多,但是在 2015 年以前,用 Hibernate 的公司确实也是很多的。为什么在国内,会有这样的现象发生?而在国外,老外会一如既往地使用 JPA 呢?我们来分析分析。
在最近(2018)的JVM 生态报告中(https://snyk.io/blog/jvm-ecosystem-report-2018-platform-application/),Mybatis是使用率是很低的。可以看图:
可以看出,Mybatis 的占比只有可怜的 6%,大家看到这个统计结果应该会很吃惊,你会觉得,不对啊,我公司以及我很多朋友都在用 Mybatis 啊,好像没听说过有人用 JPA 的,这个统计结果是错的吧?造成这种印象的原因也很简单,因为语言和技术的流行度有地域性偏差的,接着来看下 Google Trends 就明白了:
红色部分是 Mybatis 的主要使用人群。
再从下面这个对比来看,MyBatis 的关注主要集中在中日韩。知道日韩为啥也高吗,猜中有奖哦,哈哈!
首先,必须指出,对于青年程序员,其实都会质疑这个图的可信度。中老年程序员都在感叹国外其实更注重开发效率和面向对象的分析和设计。但我可以非常负责任地告诉你,这图是真的。那么,造成这种现象的原因是?
总结起来,有如下原因:
国内做互联网的 Java 程序很多都是拷贝阿里的,阿里一开始用例iBatis (日本韩国是怎么回事呢)。大量的老系统都是基于 iBatis/MyBatis 的,市场上对 MyBatis 熟悉的人才更多,招聘和培训更容易,有的青年程序员以为“ MyBatis 早已统一全球了”就是一个很好的证明。
小公司需要大量入门级的程序员,像大神甚至一个都请不起,请问大神们那些牛 b 框架哪个更快让菜鸟们上手,降低公司学习成本。注意这个成本会一直跟随公司,想必大神们创业直接前后端分离了,毕竟钱嘛多的是。
国内绝大部分项目都是面向表结构编程的,把 java 对象仅当成数据容器,查询和模型变更都设计在一张表上,所谓业务逻辑就是一堆增删改查的 sql 集合,当然用 mybatis 方便。在逻辑不复杂,或者你判断软件生命周期不会超过一年的时候,直接用表结构编程是最方便快捷的。
国内普遍都是分布式,流量和性能决定了需要经常进行优化,而是用 Mybatis 对复杂需求的优化很方便。
国内好多项目都是应付领导的某些奇葩需求。需要面向领导编程。一大半时间其实都是在解决领导的需求。国内项目需要大量报表统计(看看帆软卖的这么好就知道了),需要提供给领导作为决策。看到这里,各位领导不要骂我 ,真的不是黑领导的。
虽然,实际上 SpringDataJPA 是非常简单的,但是,但是,JPA/Hibernate 后期调试跟踪问题很麻烦,改起来也麻烦。别忘了,牛逼如你的人全公司甚至一个都没。还有什么缓存什么 Criteria 什么 Lazy ,虽然这些你学了也不见得能用上,但一个框架,你不学还是不行的。而且, JPA 对于增删改很方便,复杂查询却是软肋,有同学会说,JPA 也能写 SQL 语句啊,我想说的是,既然都用 orm 了,你再写 sql ,那不就失去了 oop 的内涵了吗?不优雅好吧。
实际上在 Mybatis 的应用场景里面,开发者要的就是自动封装,把sql查询结果转化为指定的 java 对象。这个在 iBatis 阶段,需要开发者自己定义大量的 xml 配置,去指定数据库表字段与 Java 实体类之间的关系。并且,对于每一条 sql,都需要在 xml 中写相应的语句,虽然有代码生成器,但开发量还是不小的。
但 Mybatis 发展到今天,已经非常完美地做好了自动封装数据对象这件事,支持的插件也比较丰富。对于常见的增删改查,也不需要自己写一行代码,这已经无限接近于 Hibernate 的能力了。
用 jpa 的核心是让我们关注对象建模,而不是关心底层数据库映射。只有你在考虑数据和行为在一起的充血模型、贴身职责,聚合根状态变迁,值对象不变性的情况下,你才会发现 jpa 给你提供了很多便利,根本不需要关注底层存储模型。
在复杂的逻辑、超长的软件生命周期。使用 DDD 的设计方法是目前看比较合理的选择,维护的成本比较低。
DDD 全称是(Domain-Driven Design)这是 2004 年就出来的理论,复杂逻辑的应对之道。DDD 大会在欧洲等地办了一届又一届,CQRS、Event Sourcing 等探索层出不穷,这也是为什么国外比较流行 JPA 原因。
不过,国内主要是随着这两年随着微服务火爆也有人谈起来DDD了。
但其实 DDD 也不是银弹,需要大拿能把控全局,国内缺的就是这种大拿,搬砖的太多。
无他,唯手熟尔。国外一个项目,做了几年十几年都是很正常的。我以前接触过一个巴基斯坦的电商项目,做了十几年,也跑的好好的,这就是证据。
使用技术也是有惯性的。
个人感觉,也咨询了国际友人。老外的项目,在数据体量和种类上完全达不到国内的水平。所以,他们对于性能上的渴求度没有那么高。追求的是稳定,可维护性好。国内一个双11,如果用 hibernate ,那只能死掉了。
也说明,老外的需求主要是在业务上,技术层面较少考虑。
整个状况,和对 OOAD 的重视有很大关系,我在做 DDD 技术落地的时候,用 MyBatis 非常蹩脚,用 JPA/Hibernate 会好很多。
JPA/Hibernate 比较复杂,团队中要有人 Hold 住它,否则及其容易踩坑;另外,真要使用,建议使用它的一个功能子集,不要所有功能都用。也可以尝试使用更简单 EBean ORM。
JPA/Hibernate 对分库分表的支持有一下坑。虽然,使用 Shareding-JDBC 或 MyCa t等技术,可以不关心分库分表,但是,JPA/Hibernate 在某些情况下(比如加载子集合的时候)可能会不带分区键。国外分库分表的少,国内几乎是标配。
最后,从多维度对这两个知名框架做些比较:
最后的最后,欢迎在评论区留下你最宝贵的意见 ,勿喷哦!
参考资料:
https://www.zhihu.com/question/50729231/answer/549761974
趋势图来源:https://trends.google.com/trends/explore?q=%2Fm%2F04t80p,MyBatis