架构师训练营 - 第十周总结
巨无霸应用带来的问题
编译部署困难
代码分支管理困难
数据库连接耗尽
新增或变更业务困难
解决方案:
横向拆分:抽出公用模块用以复用
纵向拆分:大材小,根据业务划分进行拆分
微服务框架需求
失效转移(Fail Over)
负载均衡
高效的远程通讯
对应用的最小入侵:能拆能合
版本管理:老接口必须等待调用者升级后才能关闭
微服务框架Dubbo
Service Mesh网络服务:Sidecar模式,一组轻量级网络代理
微服务架构落地
业务先行,先理清业务边界和依赖,技术是手段而不是目的
先有独立模块,后有分布式的服务
业务耦合严重,逻辑复杂多变的系统进行微服务重构要谨慎
搞清楚实施微服务的目的是什么,业务复用?开发边界清晰?分布式集群性能提升
命令与查询职责隔离(CQRS):在服务接口层面将查询和命令隔离,实现服务层的读写分离
更清晰的领域模型
针对读写分别优化,实现更好的性能
查询服务不会修改数据,更好的保护数据
事件溯源:将用户请求的每次状态变化记录持久化
精确复现任何用户的状态,进行复核审计
有效监控用户状态变化,并以此实现分布式事务
断路器(打开、半开、关闭)
服务重试及调用超时:上游调用超时时间要大于下游超时时间之和
最重要的是需求、其次是价值、原则、实践、工具
微服务网关
统一接入:高性能、高并发、高可靠、负载均衡
协议适配:http、dubbo、jsf
流量管控与容错:限流、降级、熔断
安全防护:校验拦截、防刷控制、黑白名单
开发平台网关
开放授权协议OAuth2.0:授权码、隐式授权、资源所有者密码、凭据与客户端凭据。互联网常用授权码
审计(日志、计费)
领域驱动设计DDD
需要一个统一的领域模型维护内在的逻辑一致性
领域模型(贫血模型&充血模型)是合并了行为和数据的领域的对象模型
领域是一个组织所做的事情以及其包含的一切,就是组织的业务方位和做事的方式,也是软件开发的目标范围
子域:领域太大就需要拆分为多个子域
界限上下文:一个子域中会创建一个概念上的领域边界,任何领域对象都只表示特定于该边界内部的确定含义。
上下文映射图:不同子系统或模块之间的交互合作
实体:每个实体都是唯一的,具有有唯一标识,可能发生变化
值对象:不变性,创建后就不能再改变,DDD推荐尽可能将对象设计为值对象
聚合是一个关联对象的集合,我们将其作为一个单元来处理数据更改
DDD分层:用户层、应用层、领域层
DDD战略设计与战术设计
领域、子域、界限上下文、上下文映射图是DDD的战略设计
实体、值对象、聚合、CQRS、事件溯源是DDD的战术设计
通过战略设计划分模块和服务的边界及依赖关系,对微服务架构的设计至关重要
DDD总结:
经过多年发展依然落地困难,但在设计中我们仍然可以在战略设计上采用DDD思想,理清模块职责边界
资深程序员真正的优势是他在一个业务领域的多年积累而不是CRUD,对业务领域有更深刻的理解和认知。
把握好领域模型在不断的需求变更中的演进,是系统保持更好的活力,并以此实现自己真正的价值
组件设计原则
软件复杂度和它的规模成指数关系
组件内聚原则:讨论组件内应该包含哪些功能和类,以便提供相对完整的功能,又不至于太过庞大
复用发布原则:软件复用的最小粒度应该等于其发布的最小粒度。
共同封闭原则:将那些会同时修改、并且为了相同目的而修改的类放到同一个组件
共同复用原则:不要强迫一个组件的用户依赖他们不需要的东西
组件耦合:讨论组件间的耦合关系应该如何设计
无限循环依赖原则:避免循环依赖
稳定依赖原则:组件依赖必须指向更稳定的方向,不稳定的组件应该依赖于稳定的组件
稳定抽象原则:一个组件的抽象化程度应该与其稳定性程度一致。一个稳定的组件应该是抽象的,而不稳定的组件是具体的。
组件的边界与依赖关系,不仅仅是技术问题:要考虑人、部门、政治问题
评论