设计一个高并发的交易型系统,可从以下7个方面来考虑。

1.1无状态

如果设计的应用是无状态的,那么应用比较容易进行水平扩展。实际生产环境可能是这样的:应用无状态,配置文件有状态。比如,不同的机房需要读取不同的数据源,此时,就需要通过配置文件或者配置中心指定。

1.2拆分

在设计一个系统的初期,我们首先要考虑是做一个大而全的系统还是按功能模块拆分系统。像京东秒杀系统,访问量是非常大的,而且投入的资源还是蛮充足的,这种情况下,就可以考虑按功能拆分系统。那么拆分的标准是什么?

系统维度:按照系统功能/业务拆分,比如商品系统、购物车、结算、订单系统等。

功能维度:对一个系统进行功能再拆分,比如,优惠券系统可以拆分后台劵创建系统、领券系统、永全系统

读写维度:根据读写比较拆分,比如,商品系统可以拆分商品写服务、商品读服务。

AOP维度:根据访问特征,按照AOP进行拆分。

模块维度:按照代码维护特征进行拆分,如基础模块分库分表,数据库连接池等。代码结构一般按照三层架构(web,service,dao)进行划分。

1.3服务化

首先,判断是不是单点远程服务调用,还是集群?在客户端注册多台机器并使用Nginx进行负载均衡是不是就可以解决问题?随着调用越来越多,还应考虑服务自动注册和发现(如Duboo使用Zookeeper)。其次,还要考虑服务的分组和隔离,有的访问量太大,会打服务打挂,因此不同的调用方提供不同的服务分组,隔离访问。

1.4消息队列

消息队列是用来解耦一些不需要同步调用的服务或者订阅一些自己系统关心的变化。使用消息队列可以实现服务解耦(一对多消费)、异步处理、流量削峰/缓冲等。比如,一些订单生产系统,定期推送系统,订单风控系统等。需要注意的是,消息推送的过程中会产生推送失败和重复推送的情况,这个时候我们需要做好数据处理工作,如持久化数据需要同时增加日志、报警、防重等。

1.5数据异构

一般情况下,订单分库分表是按照订单ID进行分,如果要查询某个用户的订单列表,则需要聚合多个表的数据后才能返回,这样会导致订单表的读性能很低。此时需要对订单表进行异构,异构一套用户订单表,按照用户ID进行分库分表。此外,还需要考虑对历史订单数据进行归档处理,以提升服务的性能和稳定性。而有些数据异构的意义不大,入库存价格,可以考虑异步加载,或者合并并发请求。

1.6缓存银弹

缓存对于都服务来说可谓抗流量的银弹,可总结为下图

1.7并发化

如果串行读取一行数据需要花60ms的话,那么如果数据之间是可以通过并发化获取,是可以提升一倍的性能的。