一、单体架构
1.什么是单体架构?
一个归档包(例如war格式)包含了应用所有功能的应用程序,我们通常称之为单体应用。架构单体应用的方法论,我们称之为单体应用架构。(就是一个war包打天下)
单体架构示意图:
优点:
1: 架构简单明了,没有”花里胡哨“的问题需要解决,排查问题时只需要排查这个应用就可以了,更有针对性。
2:在系统功能不是很臃肿下,代码文件小的情况下,部署简单(尤其是运维人员 睡着都会笑醒)
3.成本低,节约了服务器资源,在公司业务处刚开始阶段且团队人数不大的情况下比较适合。
2.单体架构的痛点
缺点一:项目过于臃肿,耦合严重
当大大小小的功能模块都集中在同一项目的时候,整个项目必然会变得臃肿,让开发者难以维护,即项目的复杂性将不断扩大。
业务复杂度增加,一个项目即会设计到订单,支付,用户,商品等模块的业务开发维护起来简单,还是只做订单模块的开发维护简单不言而喻。
迭代更新速度慢,因为可能牵一发而动全身,所以测试困难,在团队人数大的情况下无法快速迭代
缺点二:资源无法隔离
整个单体系统的各个功能模块都依赖于同样的数据库、内存等资源,一旦某个功能模块对资源使用不当,整个系统都会被拖垮如某个线程一直占着数据库连接不释放,将耗尽连接池。或者对cpu消耗过高将影响其他线程的处理性能。且多个模块共用一个jvm进程,进程资源紧张。
缺点三:无法灵活扩展
当系统的访问量越来越大的时候,单体系统固然可以进行水平扩展,部署在多台机器上组成集群:
但是这种扩展并非灵活的扩展。比如我们现在的性能瓶颈是支付模块,希望只针对支付模块做水平扩展,这一点在单体系统是做不到的。
缺点四:部署困难
能想像下一个来自200W+代码部署的速度(15分钟)。
如果只对某一个模块做了修改,那么其他模块也要对应上线,测试回归量大。
缺点五:只能用一种语言开发
1.单体应用编程语言都是一样的,某些服务可能用其他语言开发可能会更好
2.阻碍了新技术的发展。比如我们的web架构模块 从struts2迁移到springboot,那么就会成为灾难
二、微服务架构
2.1 什么是微服务?
微服务(Microservice Architecture)是近几年流行的一种架构思想,关于它的概念很难一言以蔽之。
究竟什么是微服务呢?我们在此引用 ThoughtWorks 公司的首席科学家 Martin Fowler 的一段话:
- 简而言之,微服务架构风格是一种将单个应用程序作为一套小型服务开发的方法,每种应用程序都在自己的进程中运行,并与轻量级机制(通常是HTTP资源API)进行通信。这些服务是围绕业务功能构建的,可以通过全自动部署机制独立部署。 这些服务的集中管理最少,可以用不同的编程语言编写,并使用不同的数据存储技术。
自己理解:
简单说就是将一个完整的应用(单体应用)按照一定的拆分规则(业务领域拆)拆分成多个不同的服务,每个服务都能独立地进行开发、部署、扩展。服务与服务之间通过http,消息,rpc等方式进行调用和通信。
2.2 微服务特点
1.独立部署,灵活扩展
传统的单体架构是以整个系统为单位进行部署,而微服务则是以每一个独立组件(例如用户服务,商品服务)为单位进行部署。
故微服务可以适用于快速迭代,快速交付需求场景。
2.资源的有效隔离
微服务设计的原则之一,就是每一个微服务拥有独立的数据源,假如微服务A想要读写微服务B的数据库,只能调用微服务B对外暴露的接口来完成。这样有效避免了服务之间争用数据库和缓存资源所带来的问题。
3.团队组织架构的调整
微服务设计的思想也改变了原有的企业研发团队组织架构。传统的研发组织架构是水平架构,前端有前端的团队,后端有后端的团队,DBA有DBA的团队,测试有测试的团队。
而微服务的设计思想对团队的划分有着一定的影响,使得团队组织架构的划分更倾向于垂直架构,比如用户业务是一个团队来负责,支付业务是一个团队来负责,所以对服务的拆分意味着也是对团队的拆分,一般适合中型或者大型企业。
这种团队拆分也间接的提升了团队内的沟通效率,因为都是做同样业务的,沟通理解更快,而大团队人数越多,沟通的效率越低。
微服务与面向服务架构SOA的区别
SOA架构强调的是异构系统之间的通信和解耦合,是一种粗粒度的拆分。而微服务架构强调的是系统按业务边界做细粒度的拆分和部署。
2.3 微服务架构的优缺点
1.优点
1:每个服务足够小,足够内聚,代码更加容易理解,专注一个业务功能点(对比传统应用,可能改几行代码 需要了解整个系统)。微服务能够被2-5个人的小团队开发,提高效率
2: 需求更加内聚, 开发上手更快,测试覆盖率更高。一个服务只干一个事情。(假如你做支付服务,你只要了解支付相关代码就可以了)
3.对应底层业务如商品,用户等,可以解决重复造轮子的问题。
4: 按需伸缩,服务松耦合,每个服务都能够开发部署弹性扩容
5:资源隔离保护,一个服务可用拥有自己的数据库,防止多个服务连接同一个数据库造成数据库资源紧张和便于管理。
6: 前后端分离, 作为java开发人员,我们只要关系后端接口的安全性以及性能,不要去关注页面的人机交互(H5工程师)根据前后端接口协议,根据入参,返回json的回参。
7.技术栈分离,服务之间无需关注对方是用什么语言开发的,不同技术栈可以一起协作完成整个大系统。
2 缺点
1.数据一致性
将会涉及到分布式事务,分布式锁,分布式session等。
同时更新多个业务主体的事务很普遍。这种事务对于单体式应用来说很容易,因为只有一个数据库。
在微服务架构应用中,需要更新不同服务所使用的不同的数据库。使用分布式事务并不一定是好的选择,不仅仅是因为 CAP 理论,还因为当前高扩展性的 NoSQL 数据库和消息传递中间件并不支持这一需求。
最终你不得不使用一个最终一致性的方法,从而对开发者提出了更高的要求和挑战。
2.可用性
1.依赖的底层服务不可用,将导致整个链路不可用。而如果为单体运用,对可用性的控制将简单得多,比如直接可以通过异常捕获等方式进行降级,而在分布式系统中,将会依赖服务降级中间件Hystrix,系统架构又将变得极其复杂。
2.性能问题,原来可以通过调用SQL查询数据,现在需要通过RPC调用的方式查询数据。
2.4 微服务架拆分过细陷阱
1.服务划分过细,服务间关系复杂
如果边界分析不够清晰,导致微服务拆分的不好,耦合将一样严重,且因为分布式的特点一致性的保障也将更加复杂。性能监控,问题定位等也变得更加复杂。
服务拆分的极限情况是服务之间互不依赖。
服务划分过细,单个服务的复杂度确实下降了,但整个系统的复杂度却上升了,因为微服务将系统内的复杂度转移为系统间的复杂度了。
从理论的角度来计算,n 个服务的复杂度是 n×(n-1)/2,整体系统的复杂度是随着微服务数量的增加呈指数级增加的。下图形象了说明了整体复杂度:
粗粒度划分服务时,系统被划分为 3 个服务,虽然单个服务较大,但服务间的关系很简单;细粒度划分服务时,虽然单个服务小了一些,但服务间的关系却复杂了很多。
2.服务划分过细,团队效率急剧下降(相对的,拆分太粗也会存在测试,部署等效率问题)
微服务的“微”字,本身就是一个陷阱,很多团队看到“微”字后,就想到必须将服务拆分得很细,有的团队人员规模是 5 ~ 6 个人,然而却拆分出 30 多个微服务,平均每个人要维护 5 个以上的微服务。
这样做给工作效率带来了明显的影响,一个简单的需求开发就需要涉及多个微服务,光是微服务之间的接口就有 6 ~ 7 个,无论是设计、开发、测试、部署,都需要工程师不停地在不同的服务间切换。
- 开发工程师要设计多个接口,打开多个工程,调试时要部署多个程序,提测时打多个包。
- 测试工程师要部署多个环境,准备多个微服务的数据,测试多个接口。
- 运维工程师每次上线都要操作多个微服务,并且微服务之间可能还有依赖关系。增加了运维人员的工作量,以前只要部署一个war包,现在可能需要部署成百上千个war包 (k8s+docker+jenkins )
3.服务划分过细-调用链太长,导致性能下降和问题定位困难
1.性能下降
由于微服务之间都是通过 HTTP 或者 RPC 调用的,每次调用必须经过网络。一般线上的业务接口之间的调用,平均响应时间大约为 50 毫秒,如果用户的一起请求需要经过 6 次微服务调用,则性能消耗就是 300 毫秒,这在很多高性能业务场景下是难以满足需求的。为了支撑业务请求,可能需要大幅增加硬件,这就导致了硬件成本的大幅上升。
rpc:
性能远没有本地方法调用好。
mq:
维护一套中间件本身架构将变得复杂。
2.问题定位困难
系统拆分为微服务后,一次用户请求需要多个微服务协同处理,任意微服务的故障都将导致整个业务失败。然而由于微服务数量较多,且故障存在扩散现象,快速定位到底是哪个微服务故障是一件复杂的事情。下面是一个典型样例。
Service C 的数据库出现慢查询,导致 Service C 给 Service B 的响应错误,Service B 给 Service A 的响应错误,Service A 给用户的响应错误。我们在实际定位时是不会有样例图中这么清晰的,还可能需要涉及到跨团的之间的合作。最开始是用户报错,这时我们首先会去查 Service A。导致 Service A 故障的原因有很多,我们可能要花半个小时甚至 1 个小时才能发现是 Service B 返回错误导致的。于是我们又去查 Service B,这相当于重复 Service A 故障定位的步骤……如此循环下去,最后可能花费了几个小时才能定位到是 Service C 的数据库慢查询导致了错误。
如果多个微服务同时发生不同类型的故障,则定位故障更加复杂,如下图所示。
Service C 的数据库发生慢查询故障,同时 Service C 到 Service D 的网络出现故障,此时到底是哪个原因导致了 Service C 返回 Error 给 Service B,需要大量的信息和人力去排查。
3.cap理论数据一致性问题
单机系统为了保障一致性,可以用事务解决,但分布式系统要保障一致性,就只有引入分布式事务了,而分布式事务的两阶段提交等方式,也非常的耗性能和增加了系统的复杂度
4.服务划分过细-成本问题
多部署一套系统,将多增加对应的机器,在公司的资金不足有时候是致命的,所以原则上除非你能明确的说明拆分的好处,否则能不拆分,尽量不拆分。
5.服务划分过细-服务治理带来了巨大的挑战
信奉微服务理念的设计人员总是强调微服务的 lightweight 特性,并举出 ESB 的反例来证明微服务的优越之处。但具体实践后就会发现,随着微服务种类和数量越来越多,如果没有服务治理系统进行支撑,微服务提倡的 lightweight 就会变成问题。主要问题有:
- 服务路由:假设某个微服务有 60 个节点,部署在 20 台机器上,那么其他依赖的微服务如何知道这个部署情况呢?
- 服务故障隔离:假设上述例子中的 60 个节点有 5 个节点发生故障了,依赖的微服务如何处理这种情况呢?
- 服务注册和发现:同样是上述的例子,现在我们决定从 60 个节点扩容到 80 个节点,或者将 60 个节点缩减为 40个节点,新增或者减少的节点如何让依赖的服务知道呢?
如果以上场景都依赖人工去管理,整个系统将陷入一片混乱,最终的解决方案必须依赖自动化的服务管理系统,这时就会发现,微服务所推崇的“lightweight”,最终也发展成和 ESB 几乎一样的复杂程度。
2.5 微服务架拆基础设施不足带来的隐患
1.没有自动化支撑,无法快速交付
如果没有相应的自动化系统进行支撑,都是靠人工去操作,那么微服务不但达不到快速交付的目的,甚至还不如一个大而全的系统效率高。例如:
- 没有自动化测试支撑,每次测试时需要测试大量接口----拆分成微服务测试后,单个服务的测试量相对较少,自动化测试并不是必须条件,对于中小团队来说非必需的。
- 没有自动化部署支撑,每次部署 6 ~ 7 个服务,几十台机器,运维人员敲 shell 命令逐台部署,手都要敲麻。
- 没有自动化监控,每次故障定位都需要人工查几十台机器几百个微服务的各种状态和各种日志文件,需要自动告警机制和监控机制。
2.4 微服务的适用场景
合适
1:大型复杂的项目…(来自单体架构200W行代码的恐惧)
2:快速迭代的项目…(来自一天一版的恐惧)
3:并发高的项目…(考虑弹性伸缩扩容的恐惧)
4.比较底层的业务如用户平台,组织机构,SSO单点登录等,这些业务都是一劳永逸的,其他业务可以直接拿来使用
不合适
1:业务稳定,就是修修bug ,改改数据
2:迭代周期长 发版频率 一二个月一次.
3:公司资金不充裕的情况
三、微服务架构设计理念
1.微服务架构设计的重点和难点
1.业务架构的第一个难点就是服务拆分,拆分的过粗过细都有他的对应的坏处,要掌握最合适的度,同时保障既能拆分出去,又能够少成本的组合回去,达到拆分风险降到最低
2.微服务第二个难点就是服务治理,比如服务雪崩,对应的手段有超时,降级,熔断,限流等。链路追踪,监控预警,接口调用看板等
3.第三个难点是分布式带来的问题如分布式事务,分布式日志,cap协议的取舍等等。
2.服务拆分理论
基于“三个火枪手”的理论,我们可以计算出拆分后合适的服务数量,但具体怎么拆也是有技巧的,并不是快刀砍乱麻随便拆分成指定数量的微服务就可以了,也不是只能按照业务来进行拆分,而是可以根据目的的不同灵活地选取不同的拆分方式。
服务拆分并不是不可逆的,既然能够拆分,也要设计时考虑可以进行组合,这也是保障一旦拆分不合理还能够低成本重构的关键点。
接下来我一一介绍常见的拆分方式。以下几种拆分方式不是多选一,而是可以根据实际情况自由排列组合,例如可以基于可靠性拆分出服务 A,基于性能拆分出服务 B,基于可扩展拆分出 C/D/F 三个服务,加上原有的服务 X,最后总共拆分出 6 个服务(A/B/C/D/F/X)。
1. 基于业务逻辑拆分
这是最常见的一种拆分方式,将系统中的业务模块按照职责范围识别出来,每个单独的业务模块拆分为一个独立的服务。
基于业务逻辑拆分虽然看起来很直观,但在实践过程中最常见的一个问题就是团队成员对于“职责范围”的理解差异很大,所以极限情况下,服务之间完全独立不存在依赖关系。
同时有一些拆分场景,从已有单体架构中逐步拆分服务,如提取公共基础服务(如单点登录),不断从老系统抽取服务,这也是一种持续演讲的一种方案。
2. 基于可扩展拆分
将系统中的业务模块按照稳定性排序,将已经成熟和改动不大的服务拆分为稳定服务,将经常变化和迭代的服务拆分为变动服务。
一般比较底层的业务会下层到服务中如用户中心,商品中心等,他基本不依赖于任何服务,且复用性高。越是上层的服务,变动频率越高。
3. 基于可靠性拆分
将系统中的业务模块按照优先级排序,将可靠性要求高的核心服务和可靠性要求低的非核心服务拆分开来,然后重点保证核心服务的高可用。
具体拆分的时候,核心服务可以是一个也可以是多个,只要最终的服务数量满足“三个火枪手”的原则就可以。
这样拆分带来下面几个好处:
避免非核心服务故障影响核心服务
例如,日志上报一般都属于非核心服务,但是在某些场景下可能有大量的日志上报,如果系统没有拆分,那么日志上报可能导致核心服务故障;拆分后即使日志上报有问题,也不会影响核心服务。
核心服务高可用方案可以更简单
核心服务的功能逻辑更加简单,存储的数据可能更少,用到的组件也会更少,设计高可用方案大部分情况下要比不拆分简单很多。
能够降低高可用成本
将核心服务拆分出来后,核心服务占用的机器、带宽等资源比不拆分要少很多。因此,只针对核心服务做高可用方案,机器、带宽等成本比不拆分要节省较多。
4. 基于性能拆分
基于性能拆分和基于可靠性拆分类似,将性能要求高或者性能压力大的模块拆分出来,避免性能压力大的服务影响其他服务。
常见的拆分方式和具体的性能瓶颈有关,可以拆分 Web 服务、数据库、缓存等。例如电商的抢购,性能压力最大的是入口的排队功能,可以将排队功能独立为一个服务。
3.服务拆分实战
1.iot设备接入拆分
1.背景
公司各个业务系统混杂着各个不同业务设备的数据接入,从架构上来说,设备的数据接入不依赖于任何实际业务,在设计层是偏底层的,耦合到业务系统是不合理的,应该独立开来。从开发效率上讲,如果其他业务系统也要设备的基础数据,那么将要由业务系统来提供数据同步或者rpc开放接口,这样系统架构讲会变得十分的复杂。所以需要将设备数据接入独立出来。
2.代码工程架构
首先建立一个父子工程,每一个业务设备独立一个端口,他们可以共享一些公用逻辑。
详细的业务架构,请参考我的飞书文档。
2.积分业务拆分
1.背景
积分是一个非常独立的业务,不依赖其他除用户以外的业务系统。
2.实战
详细的业务架构,请参考我的飞书文档。
3.服务拆分好坏的评判
1.评判标准
1.服务之间相互调用,那么一定是拆分得极其糟糕的,既然要相互调用彼此依赖,那么为什么还要拆分出去勒。
最典型的就是环形依赖与双向依赖
存在这种情况说明我们的功能边界没有化分清楚或者有通用的功能没有下沉下来。
2.数据一致性难以保证或者需要花费大量的精力保证一致性,那么这种情况还是别拆了。
2.服务拆分时机
何时进行微服务的拆分:
-
业务规模:业务模式得到市场的验证,需要进一步加快脚步快速占领市场,这时业务的规模变得越来越大,按产品生命周期来划分(导入期、成长期、成熟期、衰退期)这时一般在成长期阶段。如果是导入期,尽量采用单体架构。此时如果不拆分可能会出现
- 代码维护困难,几百人同时开发一个模块,提交代码频繁出现大量冲突;
- 模块耦合严重,互相依赖,小功能修改也必须累计到大版本才能上线,上线还需要总监协调各个团队开会确定;
- 横向扩展流程复杂,主要业务和次要业务耦合。 例如下单和支付业务需要扩容,而注册不需要扩容
-
团队规模:一般是团队达到百人的时候,主要还是要结合业务复杂度
-
技术储备:领域驱动设计、注册中心、配置中心、日志系统、持续交付、
-
监控系统、分布式定时任务、CAP 理论、分布式调用链、API 网关等等。
四、微服务基础设施
微服务基础设施如下图所示:
虽然建设完善的微服务基础设施是一项庞大的工程,但也不用太过灰心,认为自己团队小或者公司规模不大就不能实施微服务了。第一个原因是已经有开源的微服务基础设施全家桶了,例如大名鼎鼎的 Spring Cloud 项目,涵盖了服务发现、服务路由、网关、配置中心等功能;第二个原因是如果微服务的数量并不是很多的话,并不是每个基础设施都是必须的。通常情况下,我建议按照下面优先级来搭建基础设施:
-
服务发现、服务路由、服务容错:这是最基本的微服务基础设施。
-
接口框架、API 网关:主要是为了提升开发效率,接口框架是提升内部服务的开发效率,API 网关是为了提升与外部服务对接的效率。
-
自动化部署、自动化测试、配置中心:主要是为了提升测试和运维效率。
-
服务监控、服务跟踪、服务安全:主要是为了进一步提升运维效率。
以上 3 和 4 两类基础设施,其重要性会随着微服务节点数量增加而越来越重要,但在微服务节点数量较少的时候,可以通过人工的方式支撑,虽然效率不高,但也基本能够顶住。
1.微服务技术栈
1.服务注册和发现
代表框架:zk,nacos,Eureka
微服务种类和数量很多,如果这些信息全部通过手工配置的方式写入各个微服务节点,首先配置工作量很大,配置文件可能要配几百上千行,几十个节点加起来后配置项就是几万几十万行了,人工维护这么大数量的配置项是一项灾难;其次是微服务节点经常变化,可能是由于扩容导致节点增加,也可能是故障处理时隔离掉一部分节点,还可能是采用灰度升级,先将一部分节点升级到新版本,然后让新老版本同时运行。不管哪种情况,我们都希望节点的变化能够及时同步到所有其他依赖的微服务。如果采用手工配置,是不可能做到实时更改生效的。因此,需要一套服务发现的系统来支撑微服务的自动注册和发现。
2.服务容错
代表框架:Hystrix
系统拆分为微服务后,单个微服务故障的概率变小,故障影响范围也减少,但是微服务的节点数量大大增加。从整体上来看,系统中某个微服务出故障的概率会大大增加。我在分析微服务陷阱时提到微服务具有故障扩散的特点,如果不及时处理故障,故障扩散开来就会导致看起来系统中很多服务节点都故障了,因此需要微服务能够自动应对这种出错场景,及时进行处理。否则,如果节点一故障就需要人工处理,投入人力大,处理速度慢;而一旦处理速度慢,则故障就很快扩散,所以我们需要服务容错的能力。
常见的服务容错包括请求重试、流控和服务隔离。通常情况下,服务容错会集成在服务发现和服务路由系统中。
3.配置中心
代表框架:nacos,spring cloud config
微服务的节点数量非常多,通过人工登录每台机器手工修改,效率低,容易出错。特别是在部署或者排障时,需要快速增删改查配置,人工操作的方式显然是不行的。除此以外,有的运行期配置需要动态修改并且所有节点即时生效,人工操作是无法做到的。综合上面的分析,微服务需要一个统一的配置中心来管理所有微服务节点的配置。
配置中心包括配置版本管理(例如,同样的微服务,有 10 个节点是给移动用户服务的,有 20 个节点给联通用户服务的,配置项都一样,配置值不一样)、增删改查配置、节点管理、配置同步、配置推送等功能。
4.API 网关
代表框架:zuul,spring cloud gateway
系统拆分为微服务后,内部的微服务之间是互联互通的,相互之间的访问都是点对点的。如果外部系统想调用系统的某个功能,也采取点对点的方式,则外部系统会非常“头大”。因为在外部系统看来,它不需要也没办法理解这么多微服务的职责分工和边界,它只会关注它需要的能力,而不会关注这个能力应该由哪个微服务提供。
除此以外,外部系统访问系统还涉及安全和权限相关的限制,如果外部系统直接访问某个微服务,则意味着每个微服务都要自己实现安全和权限的功能,这样做不但工作量大,而且都是重复工作。
综合上面的分析,微服务需要一个统一的 API 网关,负责外部系统的访问操作。
API 网关是外部系统访问的接口,所有的外部系统接⼊系统都需要通过 API 网关,主要包括接入鉴权(是否允许接入)、权限控制(可以访问哪些功能)、传输加密、请求路由、流量控制等功能。
5.服务监控和告警
系统拆分为微服务后,节点数量大大增加,导致需要监控的机器、网络、进程、接口调用数等监控对象的数量大大增加;同时,一旦发生故障,我们需要快速根据各类信息来定位故障。这两个目标如果靠人力去完成是不现实的。举个简单例子:我们收到用户投诉说业务有问题,如果此时采取人工的方式去搜集、分析信息,可能把几十个节点的日志打开一遍就需要十几分钟了,因此需要服务监控系统来完成微服务节点的监控。
服务监控的主要作用有:
实时搜集信息并进行分析,避免故障后再来分析,减少了处理时间。
服务监控可以在实时分析的基础上进行预警,在问题萌芽的阶段发觉并预警,降低了问题影响的范围和时间。
通常情况下,服务监控需要搜集并分析大量的数据,因此建议做成独立的系统,而不要集成到服务发现、API 网关等系统中。
6.服务链路跟踪
代表框架:skywalking
服务监控可以做到微服务节点级的监控和信息收集,但如果我们需要跟踪某一个请求在微服务中的完整路径,服务监控是难以实现的。因为如果每个服务的完整请求链信息都实时发送给服务监控系统,数据量会大到无法处理。
服务监控和服务跟踪的区别可以简单概括为宏观和微观的区别。
例如,A 服务通过 HTTP 协议请求 B 服务 10 次,B 通过 HTTP 返回 JSON 对象,服务监控会记录请求次数、响应时间平均值、响应时间最高值、错误码分布这些信息;而服务跟踪会记录其中某次请求的发起时间、响应时间、响应错误码、请求参数、返回的 JSON 对象等信息。
目前无论是分布式跟踪还是微服务的服务跟踪,绝大部分请求跟踪的实现技术都基于 Google 的 Dapper 论文《Dapper, a Large-Scale Distributed Systems Tracing Infrastructure》。
7.服务安全
系统拆分为微服务后,数据分散在各个微服务节点上。从系统连接的角度来说,任意微服务都可以访问所有其他微服务节点;但从业务的角度来说,部分敏感数据或者操作,只能部分微服务可以访问,而不是所有的微服务都可以访问,因此需要设计服务安全机制来保证业务和数据的安全性。
服务安全主要分为三部分:接入安全、数据安全、传输安全。通常情况下,服务安全可以集成到配置中心系统中进行实现,即配置中心配置微服务的接入安全策略和数据安全策略,微服务节点从配置中心获取这些配置信息,然后在处理具体的微服务调用请求时根据安全策略进行处理。由于这些策略是通用的,一般会把策略封装成通用的库提供给各个微服务调用。
基本架构如下:
8.分布式日志
采集同一个服务下各个节点的日志信息,并由统一的存储数据库进行存储,典型的分布式日志架构就是ELK
9. 自动化测试
微服务将原本大一统的系统拆分为多个独立运行的“微”服务,微服务之间的接口数量大大增加,并且微服务提倡快速交付,版本周期短,版本更新频繁。如果每次更新都靠人工回归整个系统,则工作量大,效率低下,达不到“快速交付”的目的,因此必须通过自动化测试系统来完成绝大部分测试回归的工作。
自动化测试涵盖的范围包括代码级的单元测试、单个系统级的集成测试、系统间的接口测试,理想情况是每类测试都自动化。如果因为团队规模和人力的原因无法全面覆盖,至少要做到接口测试自动化。
一般的中小团队能保证单个服务的单元自动化测试能100%通过就不错了。
10自动化部署
相比大一统的系统,微服务需要部署的节点增加了几倍甚至十几倍,微服务部署的频率也会大幅提升(例如,我们的业务系统 70% 的工作日都有部署操作),综合计算下来,微服务部署的次数是大一统系统部署次数的几十倍。
这么大量的部署操作,如果继续采用人工手工处理,需要投入大量的人力,且容易出错,因此需要自动化部署的系统来完成部署操作。
自动化部署系统包括版本管理、资源管理(例如,机器管理、虚拟机管理)、部署操作、回退操作等功能。
目前市面上主流的自动化部署形式就是CI/CD
参考资料
1.漫画:什么是微服务?https://blog.csdn.net/bjweimengshu/article/details/79061742
2.微服务架构的优势与不足https://blog.csdn.net/albenxie/article/details/73478306