观点评论|伴鱼数据库选型的思考,为什么我们 all in TiDB

_原题为 伴鱼数据库选型的思考 , 为什么我们 all in TiDB
作者:伴鱼技术团队
技术选型是由技术方向和业务场景 trade-off 决定的 , 脱离业务场景来说技术选型是没有任何意义的 , 所以本文只是阐述了伴鱼技术团队数据库选型的过程 , 这并不是 MySQL、MongoDB 和 TiDB 之间直接的比较 , 只能说明 TiDB 更适合伴鱼的业务场景和技术规划 , 另外由于 TiDB 是非常新的数据库技术 , 所以这也能体现出伴鱼技术团队对新技术的态度、技术后发优势的理解、成本与效率的衡权和技术生态与红利的思考 。
为什么放弃 MongoDB? 伴鱼是 2015 年成立的 , 那个时候 NoSQL 还如日中天 , 关系型数据库为了应付海量的数据只能业务侵入式的分库分表 , 虽然 Google 在 2012 年发布了 NewSQL 数据库 Spanner 的论文 , 但是工业界还没有一款可以使用的 NewSQL 数据库 , 综合当时的各种情况 , 伴鱼选择的是 MongoDB 。
不过 , 在 2015 年到 2017 年之间 , 对于伴鱼来说 MongoDB 确实是一个上佳之选 , 主要有以下几个方面的原因:

  • 开发更高效:公司初期处于探索期 , 产品迭代非常快 , MongoDB 是 NoSQL 数据库 , 不需要做建库建表等 DDL 操作 , 特别在产品快速迭代 , 需要频繁增减字段的时候就更高效 , 当然这个也是有代价的 , 从本质上来说 , MongoDB 是读模式 , 它几乎不检查写入的内容是否合法 , 对数据 Schema 的解释是在应用程序的代码中 , 导致写入数据的约束性是没有保证的 。
  • 运维更高效:当时公司研发非常少 , 这段时间整个后端只有两个工程师 , 没有专职的运维和 DBA, 但是 MongoDB 的单机性能比 MySQL 要高不少 , 不但对数据库的运维成本要低不少 , 并且当时除了几个热点库外 , 其他的库 MongoDB 可以直接扛住流量压力 , 省去了中间的 Cache 层 , 让开发和运维都更高效 。
  • 有事务需求的场景不多:当时使用的是 MongoDB 2.x 和 3.x , 只提供了数据一致性的选择(强一致性、单调一致性和最终一致性)和原子操作 , 在少数的几个场景 , 比如交易相关的场景 , 通过选择强一致性和原子操作 , 再在应用层实现 MVCC 的机制 , 可以满足简单的事务需求 。
总体来说 , 在伴鱼产品的探索期 , 为了效率牺牲一点数据约束性和事务能力是值得的 , 但是 2017 年底伴鱼产品方向比较明确后 , 业务场景从探索期转变到快速发展期 , 对数据库的需求从效率优先转变为效率、事务能力与生态并重:
  • 有事务需求的场景急增:事务场景从最初与钱相关的交易扩展到一些虚拟货币 , 并且由于并发量的增加 , 之前没有事务保障的场景出现竞争的情况越来越多 , 还在应用层通过 MVCC 机制实现简单的事务是非常低效的 , 并且在应用层实现事务的正确性也是很难保证的 。 (一个有趣的故事:Jeff Dean 曾经说过自己对 Bigtable 最后悔的事情是没有提供跨行事务支持 , 导致业务就会在上层企图自己搞事务 , 并且业务实现的分布式事务大部分都是错的 , 所以在后来的 Spanner 数据库中 Jeff Dean 直接提供了官方分布式事务支持 。 )
  • 对大数据生态的需求急增:在产品探索期的时候 , 也有很强的数据分析需求 , 不过当时数据总量小 , 在 MongoDB 的隐藏从库中直接分析就足够了 , 但是产品快速发展期 , 数据量急剧增加 , 在 OLTP 数据库中进行 OLAP 操作已经力不从心了 。 但是通过大数据生态来进行数据分析 , 对于 MongoDB 来说有一个非常残酷的现实 , 基本所有的大数据生态都是围绕 MySQL 生态打造的 , 如果想接入 MongoDB 的数据 , 意味着需要重新大量造轮子 。
  • 对数据约束性的要求更高:由于业务快速的发展 , 服务可能会出现多人维护和移交的情况 , 如果存储的数据没有约束 , 意味着存储的数据 Schema 是不可控的 , 这很容易让后面参与的工程师崩溃和掉进坑里 , 这个时候数据的约束性变成是一个更高优秀级的需求 , 关系数据库的写模式变成更好的选择 。
到产品快速发展期 , 由于业务场景对数据库的需求已经发生了很大的改变 , 所以在这个时候 , 伴鱼技术团队开始谨慎思考数据库重新选型的问题 , 我们理想型的数据库是这样的:
  • 高可用;
  • 高吞吐;
  • 支持 ACID 事务;
  • 大数据生态友好;
  • 有水平扩张能力 , 并且尽量做到不侵入业务;
基于上面这些需求 , 我们开始了数据库的重新选型之路 。
初识 TiDB 早在 2015 年的时候我就非常关注分布式数据库 , 当时已经经历过高并发高 QPS 的场景 , 利用分布式架构解决无状态高并发高 QPS 场景是不复杂的 , 但是分布式存储由于涉及到一致性问题是非常有挑战的 , 如果还想支持 ACID 事务那就更难了 , 所以当时就对分布式数据库技术特别感兴趣 , 开始关注 OceanBase 并且收集和研究相关的理论和架构文档 。
后来同事推荐说有个叫 TiDB 的数据库 , 目前有些公司也在用了 , 反馈也不错 , 所以我们决定调研一下 。 TiDB 官网的文档做的非常友好 , 不论是理论还是架构的文章都非常齐全 , 几乎一口气就把所有的文章都看了一遍(当时文章比现在要少) , 完备的理论支持、优雅的架构设计、与 Google Spanner 一脉相承的设计思路让我们对 TiDB 的前景非常看好 , 并且功能上完全满足我们的要求 , 所以当时就决定长期关注 TiDB , 并且准备进行初步验证 。


推荐阅读