一.简介
当今应用多是类微服务架构,每个服务解耦,只处理一种逻辑,服务之间的调用为了实现异步和解耦,通过提交事件后再由服务分发消费的形式完成。
本文从最开始思想设计,慢慢演化,目前常用的架构思想,根据一些示例,说明消费架构在服务内部作用。
二.发展
2.1 串行
最开始服务内部调用基于串行,同步进行。
优点
容易实现,快速做业务功能。
可以在某些功能分发到独立线程去运行,但是整个编程模型还是串行化。
缺点
无法充分利用资源,多任务并发不支持。
扩展性不好,整个链路是函数化的编程模型。
例如:Map Reduce V1 版本系列就是基于此编程模型,分发任务,调度整个工作流程。
2.2 并行
基于上述,为了满足分布式系统的一些需求。
2.2.1 分布式系统复杂度
高性能
单机为了高性能带来复杂度,虽然引进了进程和线程,但是本质还是分时系统,并不能做到真正并行,需要结合实际情况,结合业务选择合适编程模型。
例如:Nginx 可以用多进程也可以用多线程,JBoss 采用的是多线程;Redis 采用的是单进程,Memcache 采用的是多线程,这些系统都实现了高性能,但内部实现差异却很大。
集群为了高性能带来复杂度,虽然增多了一些机器,但带来更大的复杂性,如何任务分配,网关服务分发,分布式存储等等,任务分解能带来性能很大的提升,用并行的编程让任务流转,无论异步还是同步提高性能。
高可用
系统无中断地执行其功能的能力,代表系统的可用性程度,是进行系统设计时的准则之一(参考维基百科)。
高性能增加机器目的为了扩展性能,高可用增加机器目的为了冗余处理单元(备份节点)。
计算高可用:任务分配
存储高可用:异地多活,存储分发。
高可用的状态决策,这个其实很重要,无论研究任意分布式源码,都会有一个状态机模块,这个是为了系统需要能够判断当前的状态是正常还是异常,因为网络的世界是现实世界的虚拟,现实世界判断一个流程的走向,有很多细节被忽略,因为人脑智能化,快速判断,但是网络世界,无法做到,需要状态机判断模块/任务走向,类似动态规划的过程,这样就衍生了一些算法:
- 独裁式(有个最高的管理者,分配决策)
- 协商式(主/备)
- 民主式(选举,例如:ZooKeeper)
可扩展
正确预测变化,完美封装变化。这句话其实意思很深远,很多技术大牛都是按照这个方向扩展服务,这句话其实也是设计模式的核心。
低成本
设计“高可用”,“高性能”架构时,通常考虑水平扩展,增加机器,那样的话与低成本相矛盾,所以往往“创新”才能达到低成本的目标。
安全
安全本身是一个庞大和复杂的技术领域,只有千日做贼,那有千日防贼,所以需要考量的事情比较多,软件层面(业务功能,架构),硬件层面。
规模
有些经验的朋友肯定知道,规模带来复杂度的主要原因就是“量变引起质变”。
2.2.2 模型
基于上述的复杂度,提供很好的理论思想,基于此更好的设计。
目前常见的模型,事件模型,分组消费模型,相似的地方很多,不同的地方面向业务不同。
都是为了更好的提升性能,监控完整的链路,更加适合分布式系统。
事件模型
这种模型是一种思想,无限制任何编程语言,为了将组件解耦,生产者和消费者实现逻辑分离,其实也在延续微服务的分离耦合的思想,后续有专门的内容模块详细介绍,在此不赘述了。
分组消费模型
这种模型与事件模型相似,但是不同点因为面向业务不同,这种方式是为了面向大数据Hadoop多租户的思想,延伸而来,分组的概念,根据不同的引擎,不同的队列,延伸出来组的概念,为了更好的管理事件,这方面很像我在上述提到的高可用的思想形态。
三.事件模型
事件模型被很多开源组件所应用,例如:Hadoop、Kafka。基本所有消息队列都有这个模型的身影,在设计模式中也有类似的思想,观察者模式/发布-订阅式编程模式。
事件
已经发生的事情,暗含状态变化,串行化一些Task,不可改变,例如我在以前的Chat(开源数据交换 https://github.com/dlimeng/exchange-parent) 就用到这种模型,每个数据源就是一个Job,这里面暗含事件的流转,感兴趣的可以看看。
架构
开源数据交换(https://github.com/dlimeng/exchange-parent),示例讲解,数据流转。
角色:有两个,生产者,消费者。
状态机:INITED,STARTED,STOPPED,NOTINITED
- 这个是有中央处理器(AsyncDispatcher),把所有事件(Job/Task)都注册到EventHandler容器中。
- 初始化serviceInit,翻转状态INITED。
- 中央处理器(AsyncDispatcher)注册到服务列表中。
- 生产者根据事件请求类型,注册到队列中。
- 消费者启动(长连接)轮询消费的事件(状态翻转STARTED)。
- 停止队列(状态翻转STOP)
优势
- 生产者与消费者解耦。
- 扩展容易,只关注业务开发,不用像以前耦合度很高。
- 消费者快速响应。
- 链路可监控,快速反应状态。
挑战
- 消息有序性。
- 消息不丢失。
四.原理
讲了这么多,其实最根本是根据并发的设计模型(生产-消费模型),也是通信中常见的经典模型,通过根本思想不断演化出很多种类。
jms
jms是一套技术规范。
实现:生产消费者模式(生产者、服务器、消费者)。
传输方式
点对点模式(一对一,消费者主动拉取数据,消息收到后消息清除)。
发布/订阅模式(一对多,数据生产后,推送给所有订阅者)。
优点
- 解耦。
- 支持异步。
- 平衡生产者和消费者的速度差异,假设生产者很慢,消费速率很快。
- 支持批量执行以提升性能(Beam中DoFn方法就是这个机制.)。
- 支持分阶段提交以提升性能(可以查看Log4j2 中Appender )。
小结
有兴趣研究jms可以看(https://blog.csdn.net/qq_19968255/article/details/82803805)。