目录
[1.1 单体架构](#1.1 单体架构)
[1.2 垂直架构](#1.2 垂直架构)
[1.3 SOA架构](#1.3 SOA架构)
[1.4 微服务架构](#1.4 微服务架构)
[2.1 微服务架构下的技术挑战](#2.1 微服务架构下的技术挑战)
[2.2 微服务技术栈选型](#2.2 微服务技术栈选型)
[2.2.1 什么是Spring Cloud全家桶](#2.2.1 什么是Spring Cloud全家桶)
[2.2.2 Spring Cloud Alibaba版本选择](#2.2.2 Spring Cloud Alibaba版本选择)
一、系统架构的演变
俗话说,没有最好的架构,只有最合适的架构。微服务架构也是随着信息产业的发展而出现的最有普遍适用性的一套架构模式。通常来说,我们认为架构发展历史经历了这样一个过程:单体架构------>垂直架构 ------> SOA 面向服务架构 ------> 微服务架构。
《淘宝技术这十年》这本书详细写了淘宝架构系统在十年间的演变过程。
1.1 单体架构
互联网早期,一般的网站应用流量较小,只需一个应用,将所有功能代码都部署在一起就可以,这样可以减少开发、部署和维护的成本。比如说一个电商系统,里面会包含很多用户管理,商品管理,订单管理,物流管理等等很多模块,我们会把它们做成一个web项目,然后部署到一台tomcat服务器上。

很多传统互联网公司或者创业型公司早期基本都会采用这样的架构,因为这样的架构足够简单,能够快速开发和上线。而且对于项目初期用户量不大的情况,这样的架构足以支撑业务的正常运行。
优点:
- 项目架构简单,小型项目的话, 开发成本低
- 项目部署在一个节点上, 维护方便
缺点:
- 全部功能集成在一个工程中,对于大型项目来讲不易开发和维护
- 项目模块之间紧密耦合,单点容错率低
- 无法针对不同模块进行针对性优化和水平扩展
基于Spring Boot开发的项目都是单体项目,就是将项目生成一个war包部署到服务器上直接运行。
1.2 垂直架构
随着用户量越来越大,网站的访问量不断增大,导致后端服务器的负载越来越高。 用户量大了,产品需要满足不同用户的需求来留住用户,使得业务场景越来越多并且越来越复杂。
我们可以从两个方面进行优化:
- 通过横向增加服务器,把单台机器变成多台机器的集群。这个是最简单的一种垂直架构。
- 按照业务的垂直领域进行拆分,减少业务的耦合度,以及降低单个war包带来的伸缩性困难问题。

每一个Tomcat服务器都部署一组相同的war包。
优点:
- 系统拆分实现了流量分担,可以针对不同模块进行优化
- 方便水平扩展,负载均衡,容错率提高
- 系统间相互独立,互不影响,新的业务迭代时更加高效
缺点:
- 服务之间相互调用,如果某个服务的端口或者IP地址发生改变。调用的系统得手动变化
- 服务之间调用方式不统一,基于httpclient、webservice,接口协议不统一
- 搭建集群之后,实现负载均衡比较复杂。比如:内网负载,在迁移得时候会影响调用方的路由,导致线上故障
- 服务监控不到位
|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|
| |--------|---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| | 📓 | 笔记 一台tomcat服务器顶配的配置,能撑得住上千的并发量已经是顶天了。 Tomcat 默认配置的最大请求数是 150,也就是说同时支持 150 个并发,当然了,也可以将其改大。当某个应用拥有 250 个以上并发的时候,应考虑应用服务器的集群部署。 官方数据tomcat最多支持1000并发,这还是调优做的很好的情况下,除非你上nginx。一般tomcat都是业务服务器,单机500并发量就差不多了。 | |
1.3 SOA 架构
为了让大家更好地理解SOA,我们来看两个场景:
- 假设一个用户执行下单操作,系统的处理逻辑是先去库存子系统检查商品的库存,只有在库存足够的情况下才会提交订单,那么这个检查库存的逻辑是放在订单子系统中还是库存子系统中呢?在整个系统中,一定会存在非常多类似的共享业务的场景,这些业务场景的逻辑肯定会被重复创建,从而产生非常多冗余的业务代码,这些冗余代码的维护成本会随着时间的推移越来越高,能不能够把这些共享业务逻辑抽离出来形成可重用的服务呢?
- 在一个集团公司下有很多子公司,每个子公司都有自己的业务模式和信息沉淀,各个子公司之间不进行交互和共享。这个时候每个子公司虽然能够创造一定的价值,但是由于各个子公司之间信息不是互联互通的,彼此之间形成了信息孤岛,使得价值无法最大化。
基于这些问题,就引入了SOA(Service-Oriented Architecture),也就是面向服务的架构。在SOA中,会采用ESB(企业服务总线)来作为系统和服务之间的通信桥梁,ESB本身还提供服务地址的管理、不同系统之间的协议转化和数据格式转化等。调用端不需要关心目标服务的位置,从而使得服务之间的交互是动态的,这样做的好处是实现了服务的调用者和服务的提供者之间的高度解耦。
总的来说,SOA主要解决的问题是:
- 信息孤岛
- 共享业务的重用

不同的系统去调用自己所需要的服务,将服务从具体的某个系统上抽离出来,实现解耦。
优点:
- 使用治理中心(ESB)解决了服务间调用关系的自动调节
缺点:
- 服务间会有依赖关系,一旦某个环节出错会影响较大( 服务雪崩 )
- 服务关系复杂,运维、测试部署困难
1.4 微服务架构
微服务架构在某种程度上是面向服务的架构SOA继续发展的下一步,它更加强调服务的"彻底拆分" 。面向服务(SOA)和微服务本质上都是服务化思想的一种体现。如果SOA是面向服务开发思想的雏形,那么微服务就是针对可重用业务服务的更进一步优化,微服务就是把服务拆的更细,我们可以把SOA看成微服务的超集,也就是多个微服务可以组成一个SOA服务。伴随着服务粒度的细化,会导致原本10个服务可能拆分成了100个微服务,一旦服务规模扩大就意味着服务的构建、发布、运维的复杂度也会成倍增加,所以实施微服务的前提是软件交付链路及基础设施的成熟化。
由于SOA和微服务两者的关注点不一样,造成了这两者有非常大的区别:
- SOA关注的是服务的重用性及解决信息孤岛问题。
- 微服务关注的是解耦,虽然解耦和可重用性从特定的角度来看是一样的,但本质上是有区别的,解耦是降低业务之间的耦合度,而重用性关注的是服务的复用。
- 微服务会更多地关注在DevOps的持续交付上,因为服务粒度细化之后使得开发运维变得更加重要,因此微服务与容器化技术的结合更加紧密。微服务的部署需要借助容器化技术。
微服务架构就是将每个具体的业务服务构成可独立运行的微服务,每个微服务只关注某个特定的功能,服务之间采用轻量级通信机制REST API进行通信。
微服务介绍文档:
英文: https://martinfowler.com/articles/microservices.html
https://microservices.io/patterns/microservices.html
中文: http://blog.cuicc.com/blog/2015/07/22/microservices
单体项目和微服务项目的对比图(这个图左半边的竖列是单体项目示意图,右半边的竖列是微服务架构的示意图):

单体项目每一台服务器上的项目都是一样的,但是微服务项目会根据需要在每一台服务器上的部署内容都有所不同。也就是单体项目部署的粒度就是整个项目,而微服务项目的部署粒度就是每个微服务,可以自由组合部署。
每一个微服务其实就是一个Spring Boot项目,多个Spring Boot项目组合成了Spring Cloud微服务项目。
微服务架构图:

每一个Pod就是一个微服务(微小的服务),比如可能通过好几个微服务来组成一个大的支付服务。微服务之间可以通过一些RPC框架来进行通讯调用。
优点:
- 复杂度可控:通过对共享业务服务更细粒度的拆分,一个服务只需要关注一个特定的业务领域,并通过定义良好的接口清晰表述服务边界。由于体积小、复杂度低,开发、维护会更加简单。
- 技术选型更灵活:每个微服务都由不同的团队来维护,所以可以结合业务特性自由选择技术栈。比如每个模块甚至可以不用同一种语言开发,可能要求并发量高的服务就用GO语言,涉及到数据分析的模块就用python。
- 可扩展性更强:可以根据每个微服务的性能要求和业务特点来对服务进行灵活扩展,比如通过增加单个服务的集群规模,提升部署了该服务的节点的硬件配置。
- 独立部署:由于每个微服务都是一个独立运行的进程,所以可以实现独立部署。当某个微服务发生变更时不需要重新编译部署整个应用,并且单个微服务的代码量比较小,使得发布更加高效。
- 容错性:在微服务架构中,如果某一个服务发生故障,我们可以使故障隔离在单个服务中,再去用这个微服务的另一个节点来顶上,达到自愈的效果。其他服务可以通过重试、降级等机制来实现应用层面的容错。
缺点:
微服务架构不是银弹(银弹是指能够解决各种问题的万能武器或工具,常用来形容软件、技术或策略),它并不能解决所有的架构问题。在拥抱微服务架构的过程中,我们经常会遇到数据库的拆分、API交互、大量的微服务开发和维护、运维等问题。即便成功实现了微服务的主体,也还是会面临下面这样一些挑战。
- 故障排查:一次请求可能会经历多个不同的微服务的多次交互,交互的链路可能会比较长,每个微服务会产生自己的日志,在这种情况下如果出现一个故障,开发人员定位问题的根源会比较困难。
- 服务监控:在一个单体架构中很容易实现服务的监控,因为所有的功能都在一个服务中。在微服务架构中,服务监控开销会非常大,可以想象一下,在几百个微服务组成的架构中,我们不仅要对整个链路进行监控,还需要对每一个微服务都实现一套类似单体架构的监控。
- 分布式架构的复杂性:微服务本身构建的是一个分布式系统,分布式系统涉及服务之间的远程通信,而网络通信中网络的延迟和网络故障是无法避免的,从而增加了应用程序的复杂度。
- 服务依赖:微服务数量增加之后,各个服务之间会存在更多的依赖关系,使得系统整体更为复杂。假设你在完成一个案例,需要修改服务A、B、C,而A依赖B,B依赖C。在单体式应用中,你只需要改变相关模块,整合变化,再部署就好了。对比之下,微服务架构模式就需要考虑相关改变对不同服务的影响。比如,你需要更新服务C,然后是B,最后才是A,幸运的是,许多改变一般只影响一个服务,需要协调多服务的改变很少。
- 运维成本:在微服务中,需要保证几百个微服务的正常运行,对于运维的挑战是巨大的。比如单个服务流量激增时如何快速扩容、服务拆分之后导致故障点增多如何处理、如何快速部署和统一管理众多的服务等。
二、如何实现微服务架构
2.1 微服务架构下的技术挑战
微服务架构主要的目的是实现业务服务的解耦。随着公司业务的高速发展,微服务组件会越来越多,导致服务与服务之间的调用关系越来越复杂。同时,服务与服务之间的远程通信也会因为网络通信问题的存在变得更加复杂,比如需要考虑重试、容错、降级等情况。那么这个时候就需要进行服务治理,将服务之间的依赖转化为服务对服务中心的依赖。除此之外,还需要考虑:
- 服务的注册与发现(注册中心)
- 分布式配置中心
- 服务路由
- 负载均衡
- 熔断限流
- 分布式链路监控
这些都需要对应的技术来实现,我们是自己研发还是选择市场上比较成熟的技术拿来就用呢?如果市场上有多种相同的解决方案,应该如何做好技术选型?
2.2 微服务技术栈选型
业内比较主流的微服务解决方案进行分析,主要包括:
- Spring Cloud Netflix
- Spring Cloud Alibaba
2.2.1 什么是 Spring Cloud 全家桶
Spring Cloud提供了一些可以让开发者快速构建微服务应用的工具,比如配置管理、服务发现、熔断、智能路由等,这些服务可以在任何分布式环境下很好地工作。Spring Cloud主要致力于解决如下问题:
- Distributed configuration,分布式配置
- Service registration and discovery,服务注册与发现
- Routing,服务路由
- Service-to-service calls,服务调用
- Load balancing,负载均衡
- Circuit Breakers,断路器
- Distributed messaging,分布式消息
需要注意的是,Spring Cloud并不是Spring团队全新研发的框架,它只是把一些比较优秀的解决微服务架构中常见问题的开源框架基于Spring Cloud规范进行了整合,通过对Spring Boot这个框架进行再次封装后屏蔽掉了复杂的配置,给开发者提供良好的开箱即用的微服务开发体验。不难看出,Spring Cloud其实就是一套规范(Spring Cloud里面有一部分是实现,有一部分只是提供了接口,需要自己去实现,比如服务发现模块),而Spring Cloud Netflix、Spring Cloud Alibaba才是对Spring Cloud规范的实现。

Alibaba的开源组件在服务治理上和处理高并发的能力上有天然的优势,毕竟这些组件都经历过数次双11的考验,也在各大互联网公司大规模应用过。所以,相比Spring Cloud Netflix来说,Spring Cloud Alibaba在服务治理这块的能力更适合于国内的技术场景,同时,Spring Cloud Alibaba在功能上不仅完全覆盖了Spring Cloud Netflix原生特性,而且还提供了更加稳定和成熟的实现
早期项目国内Dubbo用的比较多,但是现在新的项目Dubbo用的不多了。
2.2.2 Spring Cloud Alibaba 版本选择
版本说明: https://github.com/alibaba/spring-cloud-alibaba/wiki/%E7%89%88%E6%9C%AC%E8%AF%B4%E6%98%8E
本次我们选择版本:Spring Cloud Alibaba 2022.0.0.0


构建Maven项目的父pom
XML
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>3.0.2</version>
<relativePath/> <!-- lookup parent from repository -->
</parent>
<properties>
<java.version>17</java.version>
<spring-cloud-alibaba.version>2022.0.0.0</spring-cloud-alibaba.version>
<spring-cloud.version>2022.0.0</spring-cloud.version>
</properties>
<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-dependencies</artifactId>
<version>${spring-cloud.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
<dependency>
<groupId>com.alibaba.cloud</groupId>
<artifactId>spring-cloud-alibaba-dependencies</artifactId>
<version>${spring-cloud-alibaba.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>