【问题标题】:JHipster VMs vs DTOsJHipster VM 与 DTO
【发布时间】:2017-04-15 22:41:25
【问题描述】:

我想了解更多关于 JHipster 选择生成 DTO 的决定。我有几个关于它的问题。

  1. 为什么叫 DTO?在release notes of JHipster 3.6.0 中有描述,它可以用来在这些对象上执行业务逻辑。如果这真的是它的意图,那么它不仅仅是一个DTO(数据传输对象)。更重要的是,在我看来,它是一个域对象。好吧,也许这也不是一个理想的术语,因为域对象也被解释为 DTO、实体等的父术语。从 DDD 的角度来看,它也可能被称为聚合,因为它结合了多个域对象。

  2. 基于 1.,我认为,当前的 DTO 脚手架并不适合 DTO 组合多个实体的意图。在这种情况下,它不会与某个特定实体相关,因此不应在该实体的上下文中生成。

  3. 我认为当前的 DTO 脚手架更符合 JHipster 对 VM(视图模型)的定义。如果您有一个具有很多关系的复杂实体,并且可能还有一些 blob 或 clob 数据,您不想将所有这些数据提交到前端。您需要一个 VM 来切断 UI 不需要的依赖对象。这非常适合当前的 DTO 脚手架,因为关系仅由 ID 表示。这也是在 JHipster 网站上为DTOs 描述的内容。我认为这种描述已被弃用并且非常适合 VM,但不再适合 DTO。以下是来自 JHipster 网站的引述:

这些对象在域对象之上添加了一个额外的层,并专门针对 REST 层进行了调整

是否没有完全考虑 DTO 和 VM 的概念,还是我遗漏了一些重要方面?

【问题讨论】:

    标签: jhipster dto


    【解决方案1】:

    虽然我不能说为什么团队会做出这个决定,但我绝对同意 DTO/VM 的概念不是很清楚。

    我认为,基本思想类似于 MVP/MVC 模式,其中经常引入新的视图模型来获得 MVVM 模式。因此,不影响任何视图的 DTO 被“推送”到实际的模型/控制器层中。没关系,如果您说 DTO 是服务之间的传输对象。

    但是,我们也遇到了“麻烦”,并与旧 jhipster-app 中的层和 DTO、VM 等进行了大量讨论。我们是在 jhipster 引入 DTO 和 Mapstruct 的同时开始的。在我们使用 Jhipster 的新项目中,我们总是删除所有 DTO 和 VM。首先:(托管)UserVM/DTO 的东西,这非常令人困惑。这有几个原因:

    我们的应用程序的服务器端从来没有虚拟机。在视图完全基于 javascript/angular 的 jhipster 应用程序中,视图模型必须存在。我们经常有其他使用 REST-API 的应用程序,这些应用程序不是视图。因此,尤其是在微服务架构中,我永远不会在 REST-API“视图”甚至“视图模型”中调用某些东西。 因此,在没有用 Java 编写视图(使用 JSP 左右)的此类应用程序中,您永远不会在我们的 Java 代码中找到术语“VM”。此外,可能有不同类型的视图(例如 Angular Web 应用程序、iOS 应用程序、桌面客户端或其他东西),它们中的每一个都有其他视图、视图部件、小部件,因此需要其他视图模型。最后,有人说 REST-API 可能不会提供任何不是真正资源/实体的东西......

    所以,您说 jhipster 中的虚拟机实际上是 DTO 是绝对正确的。但是,正如您也所说,“DTO”存在问题,因为通常 DTO 只是一个无状态传输对象,用于封装两个或多个服务(或系统)之间的公共值,没有任何逻辑。我们认为这也是自上而下(REST)API 驱动和自下而上领域驱动设计之间的架构问题,它们以某种方式混合在 JHipster 应用程序中。与您的观点类似,我认为 JHipster 在它应该是域对象(或实体)的地方使用 DTO。例如。托管用户不是 VM 或 DTO,它是一个实体。我认为,这里的问题是,有些人认为只有基于 JPA 的实体才是领域对象,不可能有其他领域对象(实体)。

    最后,我们决定引入一种称为 ADO(API 数据对象或访问数据对象)的新类型,因为我们没有找到合适的术语。 ADO 被比作 jhipster 一个 VM、一个 DTO 甚至一个没有任何逻辑的实体。一个普通的“API 层”只读写 ADO。该层用于 REST API 控制器以及可供插件使用的 Java API。这使我们能够在不添加任何特定内部实体或域对象的情况下使用 client-API-jar 发送所有 ADO。由于 REST-API 和每个插件使用相同的 ADO(因此具有相同的描述和结构),因此开发人员不会感到困惑,并且面向资源的外部层与使用另一种业务逻辑的内部层适当分离,而不仅仅是资源-基于。

    作为内部层一部分的其他所有内容,例如实体、派生实体、实体的子集或超集,大部分都是域对象。因此,我们从这个内部层、业务逻辑等中删除了所有 VM 和 DTO。

    总而言之:为了从外部访问封装内部 (JPA) 实体,我们使用 ADO,因为除了视图之外可能还有其他实体。这些 ADO 就 jhipster VM 和 DTO 而言。但是在公共 API 层的内部,我们从不使用任何 DTO 或 VM 甚至 ADO,因为这些实体大多是域对象。

    【讨论】:

    • 感谢您如此详细地描述您处理 VM/DTO 的方法。我可以理解您的决定,并认为 ADO 是一种非常好的方法。尤其是当您不仅拥有作为客户的视图时。
    • 由于 JHipster 通常用于应用程序的完整支架,包括 UI,我认为 VM 是一个非常适合此的术语。但无论如何,我认为特别是新的 DTO 部分需要在文档中更加清晰,或者在 JHipster 本身中进一步调整。如果参与 DTO/VM 重构的 JHipster 团队的某个人能提供一些见解,那就太好了:)
    • 我认为他们在这个链接中解释了他们的观点,尽管我认为 ADO 是一个更成熟的解决方案:jhipster.github.io/2016/08/17/jhipster-release-3.6.0.html
    • 你的 ADO 不只是 DTO 吗?
    猜你喜欢
    • 2018-07-09
    • 2020-05-20
    • 1970-01-01
    • 2016-12-14
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2012-06-16
    相关资源
    最近更新 更多