淘宝是怎样实现高并发下抢单的锁单机制

简单说下,有空细聊:
1.丢弃订单:最早期,量太大扛不住,直接前端随机reject一些,返回给抢单失败,简单粗暴,但是有效,比如10万人抢100个iPhone,只要能提前预测有大概1万以上的人参与(通过资格确认、报名等方式收集信息),那么直接请求进来以后随机挡回去99%的流量都没有啥问题。
2.优化吞吐:中间有段时间,提前准备一大批机器,服务化、分库分表搞定后端性能,让前端业务可以加一定量的机器,然后搞稳定性,依赖关系,容量规划,做弹性,提升吞吐量。
3.异步队列:然后就是使用可堆积的消息队列或者内存消息队列了,如果抢单具有强顺序,那么先都进队列,然后拿前N(就是库存数)个出来平滑处理,剩下的所有都可以作为失败进行批处理了,甚至还可以做一个定长的队列,再往里写直接提示失败。队列把并发变成串行,从而去掉了锁。
4.内存分配:一些具体的业务,也会考虑预热,提前在每个机器节点内存分配好库存数量,然后直接在内存里处理自己的库存数即可,这样可能也会在极端情况下啊,
5.独立部署:针对不同类型、不同商家、不同来源的商品,部署不同的前端促销集群,这样就把压力分散开了。具体到每个商家,其实量就不大了,双十一销售第一名的商家,并发也不是特别高。
6.服务降级:越重要的抢单,大家越关心自己有没有抢到,而不是特别在意订单立即处理完,也就是说,下单占到位置比处理完成订单要更有价值。比如12306春运抢票,只要告诉用户你抢到了票,但是预计1个小时后订单才会处理完,用户有这个明确预期,就可以了,用户不会立马使用这张票,也不会在意1分钟内处理完还是1小时处理完。
需要注意的是其中部分模式会导致销售不足或者超卖,销售不足可以从抢购里加一些名单补发,也可以加一轮秒杀。超卖比较麻烦,所以一般会多备一点货,比如抢100个iPhone,提前准备105个之类的,也会证明在实际操作里非常有价值。

■网友
内存数据库面对这种级别没用的,三两下就CPU100%然后当机了。前边要部署一台过滤机,把绝大部分请求直接转到一台静态服务器显示:繁忙中。要怎么过滤规则自己定了,比如把请求进来的弄个随机数99%过滤掉,别说百分之一,有时要设为万分之一的几率。反正1个东西只有10个名额,有10万人抢,那其实只要几十个IP给他进去就行了,去里面再去慢慢搞SQL锁表重复订单那些东西。剩下的都不要了,这剩下的必须从物理层面把这些不要的IP转到静态服务器去,谁管它静态服务器CPU100%卡死很慢,这都无所谓。
没什么先后的,比如10:00开始,那 10:00:001前后可能会涌入10万个IP,先关心服务器会不会卡死吧。
剩下极少数请求放进去下单购买。


■网友
高并发跟高延迟又不矛盾,你们不要总是把他们当成对立的。这跟抽奖是一样的,无非就是抽奖可能要等个好几天之后才有结果,这个只要拿光了马上就告诉你结果,就这么一回事。

■网友
就互联网天天写crud的人觉得这有技术含量,实际上简单的一批。
只要你会使用线程安全的消息队列就行,这种消息队列是使用条件变量实现的,针对淘宝这种,就是每种需要抢的商品一个消息队列,性能没有问题。
性能更高的还有无锁队列,只是使用起来不是那么方便。

■网友
这是一个商业问题,而非一个技术问题:
用户对阿里很重要,但任何一个用户对阿里都不重要。
从双十一开始的时候,抢购经常404,用户能怎么样呢?下单一半,就是点不进去,你能怎么样呢?下了订单以后,数小时内确认不了,甚至显示不了,你能怎么样呢?
就算下单成功了,商家以无货为理由劝你退货,你能怎么样呢?
就算下单、交钱成功,商家发货,但你发现收到的是一瓶矿泉水的时候,你能怎么样呢?
黑眉小道:l天猫店铺吉的堡双十一铭瑄显卡变矿泉水,上百人被骗。


推荐阅读