写点什么

架构师训练营 10 周 -- 学习总结

用户头像
骏马
关注
发布于: 2020 年 11 月 27 日

微服务:服务本身的设计、维护和治理

 

  1. 单体巨无霸应用带的痛点:

  • 编译部署困难

  • 代码分支管理困难:多个团队共同维护,merge 冲突严重

  • 数据库连接耗尽:集群部署应用,建立了大量的连接

  • 新增业务困难:维护旧功能和添加新业务一样困难

 

  1. 解决方案:拆分--模块独立,降低耦合

  • 横向拆分:拆分出复用的业务,独立部署成微服务

  • 纵向拆分:大应用拆分成小应用

 

  1. 微服务框架

a. Web service 与企业级分布式服务

缺点:总之,不适用于大型的网站

  • 臃肿的注册与发现机制

  • 低效的 XML 序列化手段

  • 相对高昂的 http 远程通信

  • 复杂的服务和维护



1)服务提供者使用 WSDL 描述自身的服务,并行服务中心注册

2)服务中心使用 UDDI 对外发布服务

3)服务请求者通过服务中心得到服务信息,通过 SOAP 协议和服务提供者通信

 

b. 微服务框架需求

  1. 服务注册和发现

  2. 失效转移 fail over:集群部署,以实现服务高可用

  3. 负载均衡:平衡集群内机器的负载

  4. 高效的远程通信:不要让服务调用成为系统性能瓶颈

  5. 对应用最少侵入:微服务是手段,不是目标。过程会有反复,根据业务要求,可能退回集中式部署,微服务框架需要支持这种变化

  6. 版本管理:服务升级对使用者透明。接口升级需要提供历史版本的服务,直到请求都转向访问新接口。

 

c. 微服务框架(Dubbo)架构


d. Service Mesh 服务网格

  1. 轻量级的网格代理,和应用服务一起部署,负责服务发现和服务间的通信

  2. 边车模式 side car

服务请求者不再和注册中心通信,由 service mesh 负责缓存服务信息,请求者直接调用 service mesh 即可



微服务:落地实践的策略和思路

  1. 微服务架构落地的指导原则:

  2. 业务先行,先理顺业务边界和依赖,技术是为业务服务的

  3. 从单体应用中,先分离独立模块,在形成分布式服务,一步步演进

  4. 业务严重耦合,逻辑复杂的系统,重构成微服务需要谨慎

  5. 明确实施微服务的目的:业务复用 or 分布式提升性能 or 清晰划分开发边界 等


  1. 具体落地的实现手段:

  2. 命令与查询职责分离(CQRS)

  3. 读写服务分离,分别优化,实现更好的性能

  4. 更清晰的领域模型

  5. 查询服务不会修改数据,更好的保护数据

  6. 事件溯源

  7. 记录用户请求处理过程中的状态变化,并按照时间序列进行持久化存储

  8. 可以复现用户的状态

  9. 可以监控用户状态的变化,并在此基础上实现分布式事务

  10. 断路器:

  11. 防止对失效服务的大量请求,造成资源消耗

  12. 三个状态:关闭、打开、半开

  13. 当某个服务器失效的时候,当失败请求超过阈值,断路器打开,对请求直接返回调用失败信息。

  14. 当断路器打开一段时间后,进入半开状态,尝试调用服务,如果成功次数超过阈值,则进入关闭状态;如果失败次数超过阈值,则进入打开状态。

  15. 服务重试以及调用超时

  16. 上游服务调用的超时时间,要大于下游调用者超时时间之和

  17. 否则,下游服务还在等待返回结果,上游服务已经超时,这样没有意义

 

微服务网关

 

  1. 基于网关的微服务架构

  • 对外:是提供服务的唯一入口

  • 对内:鉴权,防护,协议适配,限流、降级等

 


  1. 网关管道技术

  • 网关本身没有业务,可以通过管道技术串联各种校验和拦截



  • 主要使用责任链模式实现



  1. 开放平台网关

  • API 接口:多种形式的接口,供合作者使用

  • 协议转换:转换外部请求的协议;封装内部服务的响应

  • 安全:身份识别、鉴权、访问带宽限制、限流

  • 审计:记录访问日志、监控、计费

  • 路由:将 API 请求路由到具体服务

  • 流程:将一组服务组织成完整的新服务,向调用者屏蔽其中的服务细节



  1. 开发授权协议 OAuth2.0

a. 服务本身不提供用户注册功能,依赖第三方的应用(比如微信)来认证用户,或者需要用户授权访问第三方应用的某些资源



b. OAuth2.0

  • 有四种授权方式:授权码、隐式授权、资源所有者密码凭据、客户端凭据

  • 最安全的是 授权码 方式:先获得 Authentication Code, 再换取 Access Token



领域驱动设计 DDD

 

  1. 事务脚本 -- 通常使用贫血模型

  • 典型的 spring 框架下的业务开发

  • 可以应对不复杂的业务

  • Controller,server,dao 对象只有业务方法,少有成员变量

  • 业务对象只有成员变量,和简单的 set,get 方法。业务对象作为参数在方法调用中传递

 


  1. 领域模型 -- 使用充血模型

  • 领域对象中包括数据(成员变量)和计算逻辑(方法)

  • 采用了面向对象的设计理念

  • 可以应对复杂的业务



  1. 领域驱动设计

a. 战略设计 -- 划分模块,梳理服务的边界和依赖关系

  • 领域:组织的业务范围,也是软件开发的目标范围

  • 子域:领域太大,拆分成多个子域,子域内业务高内聚

  • 限界上下文:概念上的领域边界,任何领域对象在这个边界内表示的含义是明确的。通常限界上下文和子域是一一对应的,用来控制子域的边界。

  • 通常限界上下文对应一个组件,模块,微服务,子系统。

  • 上下文映射图:描述不同限界上下文之间的交互合作



b. 战术设计

  • 实体:具有唯一标识的领域对象。实体属性发生了改变,只要标识未变,实体就没有改变。

  •     实体是 DDD 的核心所在,需要通过业务分析,识别出实体对象,然后在限界上下文中设计实体的属性和方法。

  • 值对象:具有不变性的特点。对象属性发生了改变,值对象就不在是原先的那个值对象,是一个新的值对象

  • 聚合:一个实体作为聚合根,将其他实体和值对象关联起来。聚合是数据修改和持久化的基本单元。一个限界上下文内,可以有多个聚合根。

  • 分层架构:实体的组合调用和事务应该控制在应用层

  • 六边形架构:

  • 领域模型是核心

  • 应用程序是封装领域模型的独立模块

  • 与外部系统通过适配器通信



c. 用限界上下文识别微服务的边界和依赖关系

 


组件设计原则

 

  1. 组件的内聚原则 -- 组件包含的功能和类

a. 复用发布等同原则

  • 你希望别人以怎样的粒度复用你的软件,你就应该以怎样的粒度发布你的软件。这个粒度就是组件的最小粒度

  • 版本号约定:三位数字版本号,<主版本>.<次版本>.<修订版本>

b. 共同封闭原则

  • 应该将那些会同时修改,并且为了相同目的而修改的类放到同一个组件中

  • 当变更发生时,修改将限定在组件内,只要重新发布这个组件。

c. 共同复用原则

  • 不要强迫一个组件的用户依赖他们不需要的东西

  • 将相互依赖,共同复用的类放入一个组件中。比如,hashmap 等数据容器类和对数据遍历的类就应该放入同一个组件中。

  • 不是相互依赖的类,不要放入同一个组件。如果不被依赖的类发生变化,会引起组件重新发布,导致调用程序也需要改变,造成了组件复用困难。

 

  1. 组件耦合原则 -- 组件间的关系

a. 无循环依赖原则

  • 组件的依赖关系中不应该出现环

  • 通常,循环依赖是在组件变更的过程中逐渐形成的。避免的方法是,组件设计边界清晰,组件依赖管理有统一的规则

b. 稳定依赖原则

  • 不稳定(变更多)的组件应该依赖稳定(变更少)的组件,而不是反过来

  • 如果一个组件依赖了很多的组件,那它是相对不稳定的组件,因为它依赖的任何组件发生了变更,都可能导致它自己变更

c. 稳定抽象原则

  • 一个稳定的组件应该是抽象的,而不稳定的组件应该是具体的

  • 可以为组件对外服务的类设计一组接口,并将这组接口放入专门的组件中,这个接口组件就是比较抽象和稳定的,而实现了具体服务的组件就是具体的,不稳定的

  • 比如 jdbc 的接口,和 mysql,oracle 的具体实现类

 

  1. 组件的边界与依赖关系

  • 不仅仅是技术问题,也关系到业务、人、组织部门的问题

  • 康威定律

 

发布于: 2020 年 11 月 27 日阅读数: 29
用户头像

骏马

关注

还未添加个人签名 2020.01.15 加入

还未添加个人简介

评论

发布
暂无评论
架构师训练营10周 -- 学习总结