【SpringCloud】设计原则之CQRS与基础设施自动化

一、设计原则之CQRS

CQRS 是命令查询责任分离。

CQRS 架构由于本身只是一个读写分离的思想,实现方式多种多样。 比如数据存储不分离,仅仅只是代码层面读写分离,也是 CQRS 的体现;数据存储的读写分离,C 端负责数据存储,Q 端负责数据查询,Q 端的数据通过 C 端产生的 Event 来同步,这种也是 CQRS 架构的一种实现。

传统架构的数据一般是强一致性的,通常会使用数据库事务保证一次操作得所有数据修改都在一个数据库事务里,从而保证了数据的强一致性。在分布式的场景中,同样也希望数据的强一致性,就是使用分布式事务。众所周知,分布式事务的难度、成本是非常高的,而且采用分布式事务的系统的吞吐量都会比较低,系统的可用性也会比较低。所以,很多时候,也会放弃数据的强一致性,而采用最终一致性;从 CAP 定理的角度来说,就是放弃一致性,选择可用性。

CQRS 架构完全秉持最终一致性理念。这种架构基于一个很重要的假设,就是用户看到的数据总是旧的。对于一个多用户操作得系统,这种现象很普遍。比如秒杀的场景,下单前,也许页面显示的商品数量是有的,但是当你下单时,系统提示商品卖完了。其实我们只要仔细想想,也确实如此。因为我们在界面上看到的数据是从数据库取出来的,一旦显示到界面上就不会变了。但是很可能其他人已经修改了数据库中的数据。这种现象在大部分系统中,尤其是高并发的 Web 系统很常见。所以,基于这样的假设,我们知道,即便系统做到了数据的强一致性,用户还是很可能会看到旧的数据。这就给我们设计架构提供了一个新的思路。我们能否这样做:只需要确保系统的一切添加、删除和修改操作所基于的数据是最新的,而查询的数据不必是最新的。

将一个微服务分为命令端、查询端和事件处理器,这三个部分可以互相独立地部署。

  • 命令端

请求采取命令的形式,可以驱动对微服务所拥有的领域数据的状态更改。

  • 事件处理器

事件处理器可通过很多有用的方式对新的领域事件做出响应。一个领域事件可以生成多个事件,这些事件可以发送到其他微服务。

  • 查询端

查询端将提供一个 REST API,允许 HTTP 客户端读取从已处理事件生成的实体化视图。

二、设计原则之基础设施自动化

微服务准备和架构的基础设施也是一个非常重要的需求。

基础设施应该包括提供给业务相关的应用所有基础保障的服务和设施,比如:

  • DNS / CND
  • 防火墙 / Load Balancer
  • 应用服务器、数据库(物理机 / 虚拟机)
  • 日志、监控、报警服务

一个服务应当被独立部署,并且包含所有的依赖、环境等物理资源。

服务足够小,功能单一,可以独立打包、部署、升级,不依赖其他服务,实现局部自治,这就是我们应用架构的演进,从耦合到微服务,便于管理和服务的治理。

在传统的开发中,我们构建一个 WAR 包或 EAR 包,然后把它们部署在容器上。

而在一个规范的微服务中,每个微服务应该被构建成 fat JAR,其中内置了所有的依赖,然后作为一个单独的 Java 进程存在。

这里要单独说明一下,很多团队已经习惯了使用 WAR 包的方式发布,理所当然地认为发布就必须使用 WAR 包的方式,其实这完全取决与团队的自动化程度,当自动化程度非常高的时候,使用 JAR 包的方式发布是没有问题的,但是前提是整个团队的规范必须统一,有统一的标准。

自动化的原则包括:

  • 能够毫不费力且可靠地重建基础设施中的任何元素
  • 可任意处理系统。可以轻松创建、销毁、替换、更改和移动资源
  • 一致的系统。假设两个基础设施元素提供相似的服务,比如同一个集群中有两个应用程序服务器,这些服务器应该几乎完全相同。它们的系统软件和配置应该是一样的,除了极少的用于区分彼此的配置(比如 IP 地址)
  • 可重复的过程。基于可再生原则,对基础设施执行的任何行为都是可以重复的
  • 变化的设计。确保系统能够安全的改变,迅速地做出变化

参考资料:《微服务架构实战》------ 张锋

一 叶 知 秋,奥 妙 玄 心

相关推荐
Hanson Huang1 小时前
【Spring AI 1.0.0】Spring AI 1.0.0框架快速入门(2)——Prompt(提示词)
java·人工智能·spring·spring ai
.生产的驴2 小时前
SpringBoot 服务器监控 监控系统开销 获取服务器系统的信息用户信息 运行信息 保持稳定
服务器·spring boot·分布式·后端·spring·spring cloud·信息可视化
没有烦恼的猫猫3 小时前
有关Spring事务的传播机制
spring·事务
magic 2453 小时前
事务传播行为详解
spring
考虑考虑4 小时前
@MockitoBean注解使用
spring boot·后端·spring
Dkodak5 小时前
Could not initialize Logback logging from classpath:logback-spring.xml
xml·spring·logback
hqxstudying5 小时前
Kafka
java·spring cloud·kafka
悟能不能悟5 小时前
Logback-spring.xml 配置屏蔽特定路径的日志
xml·java·spring
康小庄6 小时前
AQS独占模式——资源获取和释放源码分析
java·开发语言·jvm·spring boot·spring·spring cloud·nio
码不停蹄的玄黓7 小时前
通关JUC:Java并发工具包从入门到精通 | 深度源码解析
java·jvm·spring boot·spring·spring cloud