如何在使用多层体系结构实现的服务中减少冗余,同时保持整个系统的一致性



目前我们的服务是使用多层架构实现的,将整个服务分为三个部分:

    API
  • 业务
  • 持久性

然而,这在我们的系统中引入了很多冗余。在这个行业里有一句谚语叫"DRY"(不要重复自己)。冗余增加了开发时间,使系统更加脆弱,并使我们的代码与"复制"方法混淆。

为了更好地说明,假设我们有一个Person服务。这将需要以下内容:

  • Person实体- JPA注释类用于ORM
  • 存储库服务请求——包含Person域对象要持久化的字段值,并带有其他持久化选项
  • 存储库服务响应——包含Person实体的字段值
  • Person -类与业务逻辑,域字段和计算字段
  • 域服务请求—包含Person资源的字段值和附加业务选项
  • 域服务响应——包含Person业务对象的字段值,不包括那些不应该对API用户可见的字段值
  • Person资源类,表示API用户可以看到的内容

当考虑嵌套对象时,情况会变得更糟。

当前的设计促进了关注点(业务、API、持久性)之间的区别,但是:

  • 目前,差异非常小。这导致我们有非常相似的类,只有微小的差异
  • 服务返回带有字段的服务响应对象,而不仅仅是对象本身阻碍了其他服务依赖其他服务

问题:

  • 这个设计值得吗?
  • 我们有什么替代方案?
  • 我们可以改变什么来改善我们的状况?

我知道你是从哪里来的。我的简短建议是:阅读Eric Evans的《领域驱动设计——解决软件核心的复杂性》。

DDD的中心部分是包含大多数业务逻辑的域pojo。构建模块或多或少是你已经提到过的。

有三种服务:

  • 负责编排、事务管理和授权的应用程序服务
  • 域服务包含不适合其他域构建块的业务逻辑:实体、策略、工厂、值对象。如果不能使用其他域机制,只创建
  • 基础设施服务。最常见的是负责根聚合持久化的存储库(这个角色扮演一些实体),并且它们。这与为任何实体创建的dao形成对比。其他基础设施服务可能是应用程序正在使用的Web服务的客户端。

由于域中的逻辑是最容易重用的,所以这种不同类型服务的丰富性以及将逻辑尽可能向下推的想法,为开发人员提供了构建全面且可维护的复杂软件所需的工具。注意,对于简单的CRUD应用程序来说,DDD可能太重了。

系统的入口点要么是Web服务端点,要么是控制器(对于UI在后端生成的Web应用程序,比如jsp或jsf的情况)。

对于中等规模的系统,我喜欢使用受CQRS启发的方法,也就是说,为了避免在加载多个根聚合用于显示目的(读端)时不可避免的缓慢,我编写了专门的查询服务,直接从DB返回dto,在JPA使用select new机制的情况下。

最新更新