绿茶成立初期时,需要快速实现最基本的数据下发功能,早期的架构采用最简单的模式,如下图所示:
基于该架构,可以实现很多功能,如:
* 网址导航(可区分城市)
* 数据下发(各种数据接口)
* 运营接口(支持IP授权认证)
在数据量没有上来之前,该架构是非常好用的
随着业务的扩充和用户的上升同时为了容灾,我们将架构调整为:
该架构在很长一段时间内支持了绿茶绝大多数服务,并运行良好,同时我们发现了一些问题:
* 数据库主从使用率不高,基本都走主库;
* Redis的key分配策略由PHP框架控制,因此其它语言要想用Redis集群需要通过PHP的Redis接口,会有一定的性能损耗;
* 当流量抖动时,偶尔会有nginx连接php报502 bad gateway的现象;
后来,我们压测了Nginx、PHP、Mysql、Redis得出如下现象:
然后,我们就想,有没有办法进一步提升框架的性能,这时就去伟大的Google上寻找答案,忽然就发现了OpenResty及相关的开源社区,经过初步的调研和性能测试发现,ngx_lua的性能几乎等同于Nginx而且非常好用,然后我们就基于OpenResty开发了数据下发框架Luant,经过压力测试,发现Luant的性能和Nginx相当,比原PHP框架并发能力提升了3倍。这时,我就准备将原有的服务依紧急程度逐渐迁移并在迁移的过程中不断优化新的架构。然后,我就遇到了一个问题,如何实现Redis集群和Mysql集群?是不是把集群调度策略在Lua里再实现一次?这时,我想起了当年流传在架构组的一句话:
计算机科学领域的所有问题都可以通过引入中间件来解决。
无独有偶,我又去万能的Google和开源社区找轮子去了,经过对相关解决方案的调研和性能测试,最终选择了Codis和Atlas来作为我们的数据中间件,后来,我们的架构就演化成:
该架构属于初次搭建,还没有经过时间的检验,但就目前来看,还是靠谱的。
* Reids和Mysql集群提供Http接口,无语言限制
* 开发了Lua和PHP的RPC调用插件(随机轮询算法),使上层开发者无需关心使用细节
* Lua和PHP框架均可用于数据下发,对于高并发的服务,会尽量用Lua实现
以上就是绿茶后台架构到目前为止的演化过程,之后一定还会再发生变化。对于像绿茶这样的小团队来说,人力是最贵的资源,要知道:
永远都不要重复造轮子,除非非造不可
还有:
当你只需要一个针时,千万不要去磨铁棒
除非,有的是资源或者只是为了好玩。
谢谢观赏。