随着唯品会业务的快速发展,订单量的不断增长,原有的订单存储架构已经不能满足公司的发展了,特别是在大促高峰期,原订单库已经成为抢购瓶颈,已经严重制约公司的发展。

唯品会旧订单库包含几十张订单相关表,旧订单库是典型的一主多从架构;主库容量已接近服务器物理空间上限,同时也已经达到 MySQL 的处理上限,很快将无法再处理新增订单。

旧订单库面临的问题有:

1、超大容量问题

  • 订单相关表都已经是超大表,最大表的数据量已经是几十亿,数据库处理能力已经到了极限;
  • 单库包含多个超大表,占用的硬盘空间已经接近了服务器的硬盘极限,很快将无空间可用;

2、性能问题

单一服务器处理能力是有限的,单一订单库的 TPS 也有上限,不管如何优化,总会有达到上限,这限制了单位时间的订单处理能力,这个问题在大促时更加明显,如果不重构,订单达到一定量以后,就无法再继续增长,严重影响到用户体验。

3、升级扩展问题

  • 单一主库无法灵活的进行升级和扩展,无法满足公司快速发展要求;
  • 所有的订单数据都放在同一库里面,存在单点故障的风险;

综上所述,容量、性能问题是急需解决的问题,扩展是为了将来 3~5 年内能够很好的满足唯品会快速发展的需要,而不需要每隔几个月花费人力物力去考虑扩容等问题。

解决方法思考

1、解决容量问题

我们可以考虑到最直接的方式是增加大容量硬盘,或者对 IO 有更高要求,还可以考虑增加 SSD 硬盘来解决容量的问题。此方法无法解决单表数据量问题。

可以对数据表历史数据进行归档,但也需要频繁进行归档操作,而且不能解决性能问题。

2、解决性能问题

提高数据库服务器的配置,这个可以提升一定数量的 QPS 和 TPS,但仍然不能解决单服务器连接数、IO 读写存在上限的问题,此方法仍然存在单点故障的问题。

拆分方法探讨

常见的数据库拆分方式有三种:垂直拆分、水平拆分、垂直水平拆分。

1、垂直拆分

垂直拆库是根据数据库里面的数据表的相关性进行拆分,比如:一个数据库里面既存在用户数据,又存在订单数据,那么垂直拆分可以把用户数据放到用户库、把订单数据放到订单库。如下图:

垂直拆表是对数据表进行垂直拆分的一种方式,常见的是把一个多字段的大表按常用字段和非常用字段进行拆分,每个表里面的数据记录数一般情况下是相同的,只是字段不一样,使用主键关联,如下图:

2、水平拆分

水平拆分是把单表按某个规则把数据分散到多个表的拆分方式,比如:把单表 1 亿数据按某个规则拆分,分别存储到 10 个相同结果的表,每个表的数据是 1 千万,拆分出来的表,可以分别放至到不同数据库中,即同时进行水平拆库操作,如下图:

水平拆分可以降低单表数据量,让每个单表的数据量保持在一定范围内,从而提升单表读写性能。但水平拆分后,同一业务数据分布在不同的表或库中,可能需要把单表事务改成跨表事务,需要转变数据统计方式等。

3、垂直水平拆分

垂直水平拆分,是综合了垂直和水平拆分方式的一种混合方式,垂直拆分把不同类型的数据存储到不同库中,再结合水平拆分,使单表数据量保持在合理范围内,提升总 TPS,提升性能,如下图:

垂直拆分策略

原订单库把所有订单相关的数据(订单销售、订单售后、订单任务处理等数据)都放在同一数据库中,不符合电商系统分层设计,对于订单销售数据,性能第一,需要能够在大促高峰承受每分钟几万到几十万订单的压力;而售后数据,是在订单生成以后,用于订单物流、订单客服等,性能压力不明显,只要保证数据的及时性即可;所以根据这种情况,把原订单库进行垂直拆分,拆分成订单售后数据、订单销售数据、其他数据等,如下图:

水平拆分策略

垂直拆分从业务上把订单下单数据与下单后处理数据分开,但对于订单销售数据,由于数据量仍然巨大,最大的订单销售相关表达到几十亿的数据量,如果遇到大型促销(如:店庆 128、419、618、双十一等等),数据库 TPS 达到上限,单销售库单订单表仍然无法满足需求,还需要进一步进行拆分,在这里使用水平拆分策略。

订单分表是首先考虑的,分表的目标是保证每个数据表的数量保持在 1000~5000 万左右,在这个量级下,数据表的大小与性能是最理想的。

如果几十个分表都放到一个订单库里面,运行于单组服务器上,则受限于单组服务器的处理能力,数据库的 TPS 有限,所以需要考虑分库,把分表放到分库里面,减轻单库的压力,增加总的订单 TPS。

1、用户编号 HASH 切分

使用用户编号哈希取模,根据数据量评估,把单库拆分成 n 个库,n 个库分别存放到 m 组服务器中,如下图:

每组服务器容纳 4 个库,如果将来单服务器达到性能、容量等瓶颈,可以直接把数据库水平扩展为 2 倍服务器集群,还可以继续扩展为 4 倍服务器集群。水平扩展可以支撑公司在未来 3~5 年的快速订单增长。

使用用户编号进行 sharding,可以使得创建订单的处理更简单,不需要进行跨库的事务处理,提高下单的性能与成功率。

2、订单号索引表

根据用户编号进行哈希分库分表,可以满足创建订单和通过用户编号维度进行查询操作的需求,但是根据统计,按订单号进行查询的占比达到 80% 以上,所以需要解决通过订单号进行订单的 CURD 等操作,所以需要建立订单号索引表。

订单号索引表是用于用户编号与订单号的对应关系表,根据订单号进行哈希取模,放到分库里面。根据订单号进行查询时,先查出订单号对应的用户编号,再根据用户编号取模查询去对应的库查询订单数据。

订单号与用户编号的关系在创建订单后是不会更改的,为了进一步提高性能,引入缓存,把订单号与用户编号的关系存放到缓存里面,减少查表操作,提升性能,索引不命中时再去查表,并把查询结果更新到缓存中。

3、分布式数据库集群

订单水平分库分表以后,通过用户编号,订单号的查询可以通过上面的方法快速定位到订单数据,但对于其他条件的查询、统计操作,无法简单做到,所以引入分布式数据库中间件。

下图是基本构架:

总结与思考

技术架构与业务场景息息相关,不能脱离实际的业务场景、历史架构、团队能力、数据体量等等去做架构重构,对于一家快速发展的电子商务公司,订单系统是核心,订单库是核心的核心,订单库的重构就像汽车在高速公路上跑着的过程中更换轮胎。

本文是对唯品会订单库重构——采用分库分表策略对原订单库表进行拆分的粗略总结,在订单库重构过程中遇到的问题远远超过这些,比如:历史数据的迁移、各外围系统的对接等,但这些在公司强大的技术团队面前,最终都顺利的解决,新旧订单库顺利的切换,给公司快速的业务发展提供坚实的保障。

唯品会订单分库分表的实践总结以及关键步骤相关推荐

  1. 唯品会订单分库分表的实践总结以及关键步骤--转

    原文地址:http://www.infoq.com/cn/articles/summary-and-key-steps-of-vip-orders-depots-table 随着唯品会业务的快速发展, ...

  2. (转)唯品会订单分库分表的实践总结以及关键步骤

    原文:http://www.infoq.com/cn/articles/summary-and-key-steps-of-vip-orders-depots-table 随着唯品会业务的快速发展,订单 ...

  3. 大众点评订单分库分表实践之路

    http://dbaplus.cn/news-10-264-1.html 本文是关于大众点评订单分库分表实践的一个具体分享,包含对订单库的具体切分策略,以及我个人的一些思考. 背景 订单单表早已突破两 ...

  4. 唯品会的订单分库分表实践总结以及关键步骤

     原创2016-06-27 叶明开.王鑫聊聊架构 聊聊架构 聊聊架构 微信号 archtime 功能介绍 在这里煮酒聊架构. 随着唯品会业务的快速发展,订单量的不断增长,原有的订单存储架构已经不能 ...

  5. 订单分库分表实践总结以及关键步骤

    转载地址:http://mp.weixin.qq.com/s?__biz=MzA5Nzc4OTA1Mw==&mid=2659597584&idx=1&sn=67f5327423 ...

  6. 分库分表架构实践(文末送书)

    作者介绍: 丁浪,现就职于某垂直电商平台,担任技术架构师.关注高并发.高可用的架构设计,对系统服务化.分库分表.性能调优等方面有深入研究和丰富实践经验.热衷于技术研究和分享. 来源:infoQ||聊聊 ...

  7. SQL数据库不用SQL语句能显示全表的内容_阿里巴巴数据库分库分表的实践

    在2006年阿里巴巴B2B团队以开源方式研发了Cobar这一关系型数据的分布式处理系统.该系统在很大程度上解决了最初使用Oracle数据库因为存储数据变得越来越大带来的扩展性问题,并且为开发人员提供了 ...

  8. 【干货】分库分表最佳实践

    何时分库分表 MySQL单表(innoDB)可以存储10亿级数据,只是这时候性能比较差,业界公认MySQL单表容量在1KW以下是最佳状态,因为这时它的BTREE索引树高在3~5之间. 参考阿里开发手册 ...

  9. 购物商城订单分库分表应该如何设计

    目录 1.为什么有分库分表 2.分库分表模式分类 2.1 垂直分库 2.2 垂直分表 2.3 水平分库

最新文章

  1. IT人士在职场中需要哪些Skill?
  2. 表单开发(二):获取单选按钮,多行文本框,下拉菜单,捆绑元素数据,用户注册
  3. leetcode面试题 17.15. 最长单词
  4. 超过4g的文件怎么上传到linux,怎么免费上传大于4G的文件到百度云 大于4G的文件不开会员怎么上传到百度云...
  5. “假冒hao123”“北大青鸟”被黑 钓鱼挂马两不误
  6. 【C++ Primer】第十五章 友元、异常和其他 --之一---友元和嵌套类
  7. 陆上物探测量基本理论之一---高程
  8. dw中html5快捷键,Adobe Dreamweaver(dw)常用快捷键--系统之家
  9. Outlook 点击邮箱签名没有反应卡死
  10. java异常的使用(摆脱唯唯诺诺之“干了再说”)
  11. 计算机中数值数据编码(大计基复习资料)
  12. 依靠云计算推动企业业务模式变革
  13. Unix整理笔记——Unix基础——里程碑
  14. 阿拉丁统计 2.0丨筛选?分组?聚合能力?「高级分析」精细化数据统计管理
  15. 如何写一个好checker
  16. 关于汇川PLC变量中的数组如何用到威纶通的触摸屏中
  17. d3007(d3007经过站点和时间)
  18. android 与地图互动,高德、百度和腾讯三家比拼,哪个 Android 车机地图 App 更好用?...
  19. 解决Request method 'POST' not supported问题
  20. (JAVA)仿拼多多砍价算法

热门文章

  1. static修饰符和final修饰符
  2. 最适合程序员口味的10部电影
  3. 11月编程语言排行冠军揭晓,稳
  4. Towards Ghost-free Shadow Removal via Dual Hierarchical Aggregation Network and Shadow Matting GAN
  5. 洛谷 P1948 / loj 10074 / 一本通 1496【分层图】
  6. 一款针对百某盘的神器
  7. HTTP各版本号的区别
  8. [微机原理]多点模拟量计算机数据采集实验
  9. PPT设计思维干货分享(一)
  10. Linux--系统安全及应用(一)(账号安全控制)