软件架构的发展经历了由单体架构、垂直架构、SOA架构到微服务架构的演进过程
1.单体架构
架构说明:
全部功能集中在一个项目内(All in one)
架构优点:
架构简单,前期开发成本低、开发周期短、适合小型项目
架构缺点:
全部功能集成在一个工程中,对于大型项目不易开发、扩展和维护
技术栈受限,只能使用一种语言开发
系统性能扩展只能扩展集群节点,成本高
2.垂直架构
架构说明:
按照业务进行切割,形成小的单体项目
架构优点:
技术栈可扩展(不同的系统可以用不同的编程语言编写)
架构缺点:
功能集中在一个项目中,不利于开发、扩展、维护
系统扩张只能通过集群的方式
项目之间功能冗余、数据冗余、耦合性强
3.SOA架构
SOA全称Service-Oriented Architecture,即面向服务架构。它可以根据需求通过网络对松散耦合的粗粒度应用组件(服务)进行分布式部署、组合和使用。一个服务通常以独立的形式存在于操作系统进程中
站在功能的角度,把业务逻辑抽象成可复用的服务,通过服务的编排实现业务的快速再生,目的:把原先固有的业务功能转变为通用的业务服务,实现业务逻辑的快速复用
分布式架构模块间通讯:
Dubbo -- RPC
SpringCloud -- HTTP
使用分布式架构后,服务之间的通讯都是同步的,实现服务之间的异步通讯MQ -- RabbitMQ(消息队列)
只需要将消息发送到MQ中,另外一个模块去监听记录这个消息
服务之间通讯地址的维护
由于服务越来越多,每个服务的访问地址都是不一样的,协议://地址:端口号,模块繁多,并且模块搭建的集群数量增加,会导致其他模块需要维护各种ip地址等信息,导致项目的维护性极低,耦合性变高,并且也无法实现负载均衡的功能
需要使用一个技术解决当前问题:
Eureka注册中心帮助我们管理服务信息,实现通讯地址维护
Robbin实现服务间的负载均衡
服务降级
在上述的架构中,如果说订单模块出现了问题,只要是涉及到订单模块的功能,全部都无法使用,可能会导致服务器提供的线程池耗尽,给用户友好的提示都无法做到。
为了解决上述的问题,使用Hystrix处理。Hystrix提供了线程池隔离的方式,避免服务器线程池耗尽,在一个服务无法使用时,可以提供断路器的方式来解决。
Eureka,Robbin,Hystrix都是SpringCloud的组件
海量数据
海量数据会导致数据库无法存储全部的内容。即便数据库可以存储海量的数据,在查询数据时,数据库的响应也会及其缓慢的。在用户高并发的情况下,数据库也是无法承受住的。为了解决上述的问题,可以基于MyCat实现数据库的分库分表。
下面就是基于MyCat实现数据库的分库分表
架构说明:
将重复功能或模块抽取组成组件的形式,对外通过服务,在项目与服务之间使用ESB(企业服务总线)的形式作为通信的桥梁。
服务分别独立部署,独立运行的,如上图,用户服务单独运行在一台服务器上,订单服务单独运行在另一台服务器上,单独对外发布
架构优点:
重复功能或模块抽取为服务,提高开发效率
可重用性高
可维护性高
架构缺点:
各系统之间业务不同,很难确认功能或模块是重复的。
抽取服务的粒度大
系统和服务之间耦合度高
4.微服务架构
服务层每个服务都是单独部署,独立运行的
每一个服务都有自己的一台服务器,运行在一个单独的Tomcat中,UI层需要数据的时候,直接通过网关,请求相应的微服务来获得数据。
微服务的“微”字体现在这些服务抽取的粒度是比较细的,把每个功能模块抽取成非常细小的微服务
架构说明:
将系统服务层完全独立出来,抽取为一个一个的微服务
抽取的粒度更细,遵循单一原则(每个微服务职责单一,如上图中的用户服务,订单服务,物流服务)
采用轻量级的框架协议传输(http协议)
架构优点:
服务拆分粒度更细,有利于提高开发效率
可以针对不同服务制定对应的优化方案
适用于互联网时代,产品迭代周期更短(因为这些服务都已经进行了很细的拆分了,迭代的时候,只要针对相应的微服务迭代,其他的微服务不受影响)
架构缺点:
粒度太细导致服务太多,维护成本高
分布式系统开发的技术成本高,对团队的挑战大
微服务也是属于分布式架构的,只不过,将一个模块再拆分,拆的更细,一个服务只做一件事。如一个项目只做商品的查询
上面的模块过多,运维成本也会增加,为了解决这一问题,采用Docker容器化技术来帮助我们管理。
(1)Java Webapp
Java Webapp是运行在web容器中的小程序,编译打包后是以".war"结尾的程序包,在我们微服务中,service模块就是一个webapp项目,在我们的微服务中,service模块就是一个webapp项目,典型的特征是存在web.xml文件。
(2)Tomcat
Tomcat是一个Servlet容器,实现类Servlet规范。简单的说,Tomcat就是作为一个容器,用来运行Java编写的Webapp的。
对于Java来说,每个Main函数启动的是一个进程。
微服务的代码是没有Main函数的,Main函数是在Tomcat中。Tomcat启动后,会读取规范目录下的所有web.xml,然后根据web.xml中的配置内容,初始化Spring等。
一个Tomcat进程监听一个端口;
一个Tomcat进程可以容纳多个Webapp,当请求进入端口时,根据URL的path不同,转给相应的Webapp;
每接收到一个请求,Tomcat都会为它创建一个新的线程来处理这个请求
(3)微服务
我们每一个微服务都是一个Tomcat进程,但是这个Tomcat里只运行了一个Webapp
Nginx在这里是一个Proxy Server,起到的是路由的作用。
打个比方,在物流中,假设每个服务器都是一个省,每个微服务是一个城市,那么Nginx就是这个省的中转中心,该省物流的出入都会经过它,省和省之间都是通过它给转运的。
5 总结
SOA与微服务架构都属于分布式架构
分布式架构下的其他问题
分布式架构帮助我们解决了很多的问题,但是随之也带来了很多问题:
(1)分布式事务:
最传统的操作事务的方式,是通过Connection链接对象的方式来操作,Spring也提供了声明式事务的操作
为了解决事务的问题,后续会使用到RabbitMQ 或 LCN方式来解决
(2)分布式锁:
传统的锁方式,synchronized 或 Lock锁,在分布式环境下,传统的锁是没有效果的。
为了解决锁的问题,会使用到Redis 或 Zookeeper来解决
(3)分布式任务:
在传统定时任务下,由于分布式环境的问题,可能会造成任务重复执行,一个比较大的任务,需要可以拆分。
为了解决这个问题,使用Redis + Quartz 或 Elastic-Job