放假在家,每日闲来无事总是喜欢在infoQ逛逛,看新闻总是关于春运的相关新闻,今年推出的12306.cn可谓是国内一种新兴的购票方式吧。班里很多同学都通过这个网站购得了火车票,但是仔细想想那个时候,春运还没有正式开始,所以很多同学很轻松就买到火车票,当然我没有这么体验了!记得耿同学和我说,从太原到阳泉,火车票半价4元,网上订票邮寄费35元……9倍的价格,都赶得上我坐汽车回家了。不过随着春运的到来,很多人以为只要点点鼠标就可以买到火车票的这个选择并没有为大家带来多么顺畅。听说很多人为了能买到一张火车票竟然点了上百次鼠标,其实,infoQ上说的很对:“只是把一部分人的“战场”从寒风中或者电话旁换到了互联网上,各种工具、插件齐上阵,只为买到一张票,网友将它戏称为“中国最牛电商”、“电商严冬中的一朵奇葩”。
游戏技术专家云风早些时候发表了博文《铁路订票系统的简单设计》,其中提出了一种基于排队系统的设计方案,排队是网游中比较常用的一种手段,这里将购票网站比作购票窗口,需要购票的用户必须先排队,最后排到的用户才能进行实际的购票操作。藉此提升站点稳定性,避免大量社会资源浪费在无效的网络购票流程上。在文章最后,云风认为:
因为铁路购票系统很多年前就实现了内部网络化,有成熟系统支撑,运作多年。这次做互联网版本,一定不能放弃原有系统新来一套。[..]所以要做的仅仅是怎么做一个系统和原有系统对接。
4399首席架构师曹政也撰写了一篇《铁路订票网站个人的设计浅见》,他将网站的主要需求分为三部分,即车次查询与余票显示、用户注册与登录,以及下单。文中以缓存为切入点,提出了一些建议:
- 针对查询,存储结构KV化,推荐Redis之类的NoSQL存储
- 车次及车票余量的查询结果要缓存化、静态化
- 应对10亿级别的请求,在前端也需要做缓存处理
- I/O优化
缓存化、静态化并不是不做动态更新,总之,目标就是让绝大多数的请求都落到缓存中,降低后端服务器的压力,让它们能有更多的资源处理真正的购票请求。
知名博客酷壳作者、亚马逊中国技术经理陈皓从12306.cn的性能问题入手,介绍了一些常用的性能优化技术。虽然其中的一些东西受到了质疑,不过全文还是能让读者了解到性能优化的诸多内容。首先,从业务上分析了12306.cn与QQ、网游、秒杀、奥运票务系统的区别,认为它和电子商务的订单系统比较相似,而且铁路票务中的突然放票做法非常恐怖。随后,分前端和后端两部分展开详细说明。
前端优化技术常用的有:
- 前端负载均衡,通过CDN及DNS负载均衡器分散压力
- 减少前端链接数,例如可以合并CSS、JS和图标文件
- 减少网页大小增加带宽
- 前端页面静态化
- 优化查询,可以考虑使用NoSQL技术
- 缓存动态页面和查询数据
后端优化技术主要是:
- 数据冗余
- 数据镜像,可提高可用性,便于负载均衡
- 数据分区,比如按照火车票的信息分区存放数据
- 后端系统负载均衡,建议由下游的计算服务器去任务服务器上拿任务
- 异步和批量处理,比如可以使用队列进行排队
- 限流,这是系统的一种自我保护手段
关于云风提出的排队方法,陈皓也做了一些补充,例如,如何防范攻击,队列的一致性和等待时间等等。陈皓强调
无论你怎么设计,你的系统一定要能容易地水平扩展。
上述的技术不是一朝一夕能搞定的,没有长期的积累,基本无望。
上面的一些讨论都是围绕技术展开的,在Google+上,霍矩、云风和刘新生(o6z)的讨论同样精彩,o6z指出仅从技术入手无法解决根本的问题:
做这些项目不是应该先设计,而是应该先业务,特别是应该先了解清楚他们现在的系统构件情况。[..]这不仅仅是Web的问题,而是要先从业务下手。[..]构架师不是一个技术角色,做的不是技术决策,而是业务和商业决策。