年关将至,是抢票的高峰期。领导还记得大学时每次和舍友对着12306大吼大叫的场景。基本上这个时候全国至少有几亿人会像领导一样加入“骂军”的行列。

今天老板闲着没事瞎逛起来,无意中看到一篇前淘宝工程师写的热门文章,名为《代码狗》。文章中的内容让不是培训班出身的老板一眼就知道了12306的运行机制。老板看完,只能感慨地说:12306,神奇的网站。

以前干你,现在干你!

值得注意的是,“代码狗”在12306系统刚上线的时候有很多负面评论。为了证明12306系统易于构建,“代码狗”甚至发起了一个名为“为12306设计系统”的开源项目。通过工作实践,“代码狗”对12306系统有了新的认识。

本文转载以供类人猿参考。

全文如下:

我是淘宝技术专家。2012年,我在一家百强民营企业担任电子商务副总裁。当时我带领团队在极其困难的条件下开发了一个B2C网站,走了支付宝和银联支付渠道,年营业额几千万。

当时我对12306嗤之以鼻,认为他们做得很糟糕,认为我可以带领团队花上百万年半的时间把工作做好。所以我傲慢地想为他们做一个开源的预订系统。我花了一个星期的时间思考建立一个数据模型,当我思考库存步骤的时候,我发现12306的库存复杂度比淘宝和JD.COM高很多倍,计算量也大很多倍。传统的分布式数据库、缓存和负载平衡技术不能满足12306的要求。

平时12306只是一个普通的电商网站。但黄金周一来,12306是全站所有商品的尖峰,所有SKU都是动态库存的异常情况。

即使不考虑现有的线下电话和销售网点,也要实现一个12306的硬件投入,至少是几千万。软件和人力分开算。那些嚷嚷着只要40台服务器,只要2个架构师,4个程序员,说什么子数据库,子表,前端CDN,都只是纸上谈兵。

所谓初生牛犊不怕虎。三年的CMS和BBS,用这种经历喷12306,太幼稚了。

媒体人喷12306是因为不懂技术,没有能力和耐心去分析背后的难度。

技师喷,是因为大部分技师在短时间思考时容易陷入过于乐观的误区。经典的例子就是估算工作量。程序员倾向于估计一个超短的时间限制,乐观地把写程序的工作想象成按照稿子打字的工作。

知乎的文章,我觉得不是洗地。第一个和第二个回答都很客观。淘宝技术比12306强大很多倍,淘宝现在的系统花的钱、时间、人才是12306的10倍。根本原因是铁路运力无法满足春运高峰的需求,淘宝无法解决这个问题。

12306这一年进步很大。从前台动画验证码,按时间抢票,到后端小型机、虚拟化、内存数据库的应用。可以说12306是中国政府机构做的最强大的网站。短短一两年就能做出这样的改变,几乎是奇迹。连一些市场化的民营企业都比不上,连一些上市公司都比不上!

很难知道发生了什么。网上批评12306的人大多还是形成了“国企=垄断+腐败+低效”的心态。少数确实贬低了它的难度。

至于12306一期3亿元贵不贵,我只提供一个数字供参考。百度每年研发费用10亿元,来自百度财报。可以在网上找到。3亿看起来是个大数字,确实用在超大型电商系统和搜索引擎系统上,但也不是真的天文数字。

再解释一下为什么尖峰压力高,为什么12306的动态库存复杂。

先说秒杀。

2013年12月25日左右,天猫举办了圣诞季积分兑换活动,持续了好几天。25日上午10点12分,天猫魔盒1.5万个发售。根据交易记录,19秒内全部被抢。

其实我也参加了二杀。那天的题目很简单。我应该在5秒内完成回答并提交订单。结果告诉我排队的人太多挤不进去,14秒后提示我再试一次。人太多是因为题目太简单,门槛越低,五秒钟挤进来的人就越多。如果话题换成,五分钟就没有15000人和我竞争了。

我以为,14秒后,对我来说就什么都没有了,于是我重新回答了问题,服务器的错误页面出现了。刷新几次,告诉尖峰结束。

我问了群里的同事,不到10个人回答我,说秒不到。

淘宝的技术水平如何?淘宝至少有4000名技术人员,至少有4万台服务器。2013年11月11日,营业额351亿,2012年全年营业额突破1万亿。

淘宝有各种独立的R&D团队:服务器和交换机;操作系统,Web服务器,Java语言虚拟机,数据库,负载均衡器,Java running container 。

淘宝还有无数的开源项目和中间件,比如高性能的Java通信中间件HSF,分布式数据库中间件TDDL,异步消息系统notify等等。

以淘宝的技术水平,不可能让每个用户杀人的时候都觉得拥挤。为什么?

首先,我们必须尊重物理原理

服务器一秒钟可以承受的计算量是有限制的。无论你怎么优化,算法和编程语言有多高效,都突破不了某个极限。比如汽车发动机驱动的F1赛车至今无法突破时速400公里。再深入,就不容易理解了。有兴趣可以从著名的C10K问题入手。

二是考虑经济效益

十一黄金周期间,从北京主城到八达岭长城的道路被完全封锁,但不能仅仅因为黄金周高峰期就建成长安街那样的10车道高速公路。否则要花费天文数字。修完一段路,黄金周可以飙到80 km/h,但平时是给两边居民干小米用的。

淘宝目前的硬件和带宽已经超出了日常运营的需要,也就是预留了相当大的利润用于大促销。亚马逊为了应对黑色星期五的大促销,购买了大量服务器。通常,订单量不会很大,所以亚马逊将剩余的服务器用于云计算。对了,阿里巴巴云是中国第一世界最好的云计算服务提供商之一,有点像亚马逊。

先说动态库存。

淘宝杀天猫盒子的时候,只有一种商品,库存15000。如果一个人杀了,库存会在1,19秒内售完,1秒内成功生成789单。想象你在广场上卖火车票。一秒钟,八万人拿钱对你喊:卖给我!

上过大学的人都知道,小于秒的时间单位是毫秒、皮秒、飞秒。然而,在交易系统中注册一个交易并不像原子绕着原子核运行那么简单。它必须做这些事情:检查是否被恶意访问,获取系统时间,获取客户的默认交付地址,检查客户的spike资格,生成订单号,将客户ID系统时间订单号的发货地址写入订单系统,扣除客户天猫积分,减一个库存,标记客户等。一切都需要毫秒,这些操作的总时间可能接近一秒。但是因为淘宝的服务器比较强,采用分布式和集群技术,结果要好于一秒。但是,即使有10000台服务器,这个时间也不能稀释到万分之一秒,因为只有一种商品,有15000个库存,只有一行对应的数据库记录,所有的交易请求都要在这里处理。

你能把这15,000个项目分成5,000个项目,分发给5,000个服务器吗?5000台服务器不能同时处理吗?答案是否定的,首先5000个产品意味着5000个产品详情页,5000个购买按钮,对于前期的营销引流来说是一场灾难。基本上不能作为引流门户,明显违背了业务管理的原则,人为增加了信息混乱的程度。其次,天猫盒子穗也不是什么大不了的事情,就算按照官方399元的价格计算,也就是600万的交易量。如果600万英镑的交易需要这么大的支持成本,那就不划算了。第三,淘宝有十几亿的商品,这十几亿商品的展示、交易、管理,原本是分发给几万个服务器的。不再需要根据库存将每种商品拆分成多种商品。

这789人不一定会付费,于是就带来了取消订单,重新恢复库存的问题。想要的消费者会觉得还有机会,继续在前台刷一会。最终这个尖峰会被热情的消费者刷30秒到1分钟。

一分钟过去了,服务器终于可以喘口气了吗?等等,还有超卖。最初,两台服务器都在同一毫秒内获得锁定,这使它们的库存减少了15,000,下了15,500个订单,并且不得不取消一些订单。。。如果采用单线程排他锁,同一时间只减少一个服务器线程的库存是可能的,但是并发峰值的能力差很多。8万人拿钱,只有8个人能下单成功。这种拥挤和疯狂的高峰将持续10多分钟。通常如果你每秒有一个天猫盒子,10分钟10分钟,双十一就惨了。收银台一下子就降了90%,你还想达到350亿,要么做梦,要么多加10倍的服务器和带宽。所以业务是不完美的,要在绝对正确和绝对快速之间做出取舍,保证相对快速和极端正确,允许一定的库存误差和超卖。

好了,说了半天淘宝,能不能说12306?

我以北京西到深圳北的G71高铁为例。它有17个车站和3个座位。表面上看,这三种不是商品吗?G71业务块、G71一级块和G71二级块。大部分轻松喷12306的技术人员最先在这里栽跟头。

其实G71有136*3=408种商品。怎么算的?请看:

如果从京西卖,有16种卖法,京西去保定、石家庄、郑州、武汉、长沙、广州、虎门、深圳。。。。是一种独立的商品,

同理,石家庄下车有15种,类比一下,有136种票:16+15+14...+2+1 = 136.每张票有三种座位,共408项。

好了,我们来看看出票时如何减少库存。由于商务舱、头等舱和二等舱的座位数是独立的,所以库存操作是一样的。座位的区别我就不提了,只讨论始发站和到站。另外,接下来是理论世界的模型,而不是12306数据库就是这样设计的。

乘客A买了一张北京西到保定东的票,这个商品的库存会减少一个。同时,北京西至石家庄、郑州、武汉、长沙、广州、虎门、深圳15个站点的库存也将减少一个。换句话说,实际上会发一张北京西到保定东的票。

这还不是最复杂的。如果乘客B购买北京西到深圳北的车票,除外,该商品库存将减少一个,北京西到保定东、石家庄、郑州、武汉、长沙、广州、虎门的商品库存也将减少一个,保定东去石家庄、郑州、武汉。。减少的商品总数为16+15+14+...+1 = 120.

当然,并不是每张票的库存都是这样实时计算的。黄金周等高峰期可根据往年运营情况提前定票。比如北京到武汉的长途稍微多一点,保定到石家庄的短途稍微少一点。我没有证据证明铁道部有这样做,但我相信铁道部在12306网站开通之前就有这个手动预配策略。

想象一下,8万人拿着钱冲你喊:卖给我。你终于在钱堆里找到了一只手,拿了他的钱,转身去找120个同事,叫他们减少库存,这120个同事就被你这样的8万人包围了;和你一样,每卖出一件商品,就需要找几十个人来降低库存……这就是12306动态库存的变态。你平时买东西的任何网站的库存机制都要复杂几十倍甚至几百倍。

先说抢票插件。机器总是比人快。当你终于突破8万人的包围圈来到柜台时,你发现,操,绑着钱的竹竿有10万根,一退就要穿过三层人肉才能靠近柜台。竹竿伸到八个人后面,钱就到了柜台。低头看手机,票没了,竹竿却一直伸在那里,不曾低头,不曾眨眼。没有这十万根竹竿,虽然你很可能抢不到票,但也不会抑郁成这样:为什么我TM总是最慢的?!!

防止机器人抢票不是加个图片验证码那么简单。我写过一篇文章,系统分析过。机器暴力破解图片验证码有六种方法,抢票插件使用第三种,OCR识别。谷歌采用的波浪字母已经能够更好地防止机器的光学字符识别,ems.com.cn的验证码就是一个反面例子。机器的OCR成功率接近100%,12306的成功率比ems的图片验证码稍强。但是验证码应该设置的比较复杂。大家要喷:就是便宜大学生和办公室白领。农民工连26个字母都认不出来。他们怎么做到的?做动画验证码。有人喷。视力不好的人怎么办?最后验证码太简单了,大家都很开心。其实开发抢票插件的公司最开心。

即使采用机器无法识别的验证码,也无法抵抗社会工程的破解方法。招一堆在网吧打游戏的年轻朋友。每次你成功输入50个验证码到1元,或者等值的虚拟货币和游戏装备,我保证有无数人想赚到这笔钱。这笔钱对于倒卖门票的利润来说是一个可以接受的成本。有什么技术可以防止社会工程的破解?网吧能防青少年的验证码只有。

上面的讨论只是把12306当成一个从零开始,没有淘宝那样历史包袱的交易系统。其实不是。有电话售票、火车站售票、销售点售票等多种传统渠道服务。除了客运服务,12306还有中国最大的散货运输系统。

frame 空政策讲技术,不可能解决春运高峰抢票的困境。如果想让大家在春运高峰12306抢票,没有拥堵感。那就是逼12306买很多服务器来应对春运高峰。春节旅游高峰过去后,它变成了像亚马逊一样强大的云计算。和强制北京修建10车道高速公路到八达岭长城是一个道理。

目前12306还存在技术问题,比如抢票高峰期,一个身份证号和一个图片验证码的输入卡死,服务器忙,你的浏览器卡什么?

但是人们在进步。相信在2014年春运热潮中,技术将不再是一票难求的主要问题。在铁路运力不能快速增长的情况下,为了在春运高峰期更公平地购票,有必要调整停车政策。

以下是针对春节和国庆节的暑假。其他时期大部分线路保持现状就够了,问题不大。很少有票源紧张的线路可以按照春运高峰办理:

1.拍卖法,出价最高者得之

硬座票是机票价格的时候,相信买票不难,黄牛没那么多。要说淘宝能一下子帮12306解决技术问题,淘宝的拍卖系统能帮上忙。浙江高院拍卖淘宝一年多,成交额26亿。

不幸的是,这种方法是不可能的。什么样的高铁票价被媒体和舆论领袖喷过,更别说拍卖了。况且火车票毕竟只是生存需要。由于票价在过去20年里没有上涨,其中已经有护理补贴的组成部分,全面拍卖可能不合适。

2.彩票法,幸运的人得到它

报名在开车前2个月开放,开车前7天抽签,中途可以取消。预付车费,无法退款。上传身份证和面对面自拍,用机器检查。

这样拦截黄牛的成功率会高很多。黄牛可以预售票,找到大量真实身份证号。你们黄牛会让每个给你身份证号的人给你身份证照片和人脸自拍?就算真的有人想找黄牛,也会犹豫要不要给身份证照片。而且中间人工操作多,牛的成本增加,可能拿不到票。反正都是机会。我觉得真正的消费者会选择先碰运气。

这个方法也很难实现。无论彩票规则怎么设计,都会有人喊“有黑幕,不要相信政府”。

开车前7天,抽签。改行程的要在开车前7天决定是否改。还有时间想别的办法。当然不一定是7天,15天,10天,但是需要一个数据模型来计算具体的天数。

3.拍卖+抽奖

软卧、高铁商务座等高价物品拍卖。反正买这个东西的人经济能力比较强。我们来拼一下谁的经济能力更强。

硬座和站票抽签。

4.凭身份证进站,车票和发票一样,是报销凭证,不是进站凭证;退款后,款项进入12306账户,不能兑现,只能由乘客下次使用;黄金周期间,个人账户最多可以订购10张门票。

这种方法可以打击黄牛,倒卖;跑了一段时间后,根据账户余额拿到排名表,就知道黄牛是谁了。可惜这需要站内设备改造的配合。

1.《12306网 12306,一个神奇的网站》援引自互联网,旨在传递更多网络信息知识,仅代表作者本人观点,与本网站无关,侵删请联系页脚下方联系方式。

2.《12306网 12306,一个神奇的网站》仅供读者参考,本网站未对该内容进行证实,对其原创性、真实性、完整性、及时性不作任何保证。

3.文章转载时请保留本站内容来源地址,https://www.lu-xu.com/junshi/1745221.html