
我想在微服务的背景下重新提出这个问题.这是原始问题的引用.
I am currently creating a REST-API for a project and have been reading
article upon article about best practices. Many seem to be against
DTOs and simply just expose the domain model, while others seem to
think DTOs (or User Models or whatever you want to call it) are bad
practice. Personally, I thought that this article made a lot of sense.However, I also understand the drawbacks of DTOs with all the extra
mapping code, domain models that might be 100% identical to their
DTO-counterpart and so on.
现在,我的问题
我更倾向于在我的应用程序的所有层中使用一个Object(换句话说,只是暴露域对象而不是创建DTO并手动复制每个字段).我可以使用@JsonIgnore或@JsonProperty(access = Access.WRITE_ONLY)或@JsonView等Jackson注释来解决合同与代码之间的差异.或者,如果有一个或两个字段需要使用Jackson Annotation无法完成的转换,那么我将编写自定义逻辑来处理这个问题(相信我,在我的5年中我甚至都没有遇到过这种情况休息服务之旅)
我想知道我是否遗漏了没有将域复制到DTO的任何真正的不良影响
>不同的请求(事件)和您的数据库实体.通常情况下,您的请求/响应与您在域模型中的请求/响应不同.特别是在微服务架构中,它有很多来自其他微服务的事件.例如,您有Order实体,但是从另一个微服务获得的事件是OrderItemAdded.即使一半的事件(或请求)与实体相同,但为了避免混乱,为所有事件设置DTO仍然有意义.
>在您公开的数据库架构和API之间进行耦合.使用实体时,您基本上会揭示您在特定微服务中建模数据库的方式.在MySQL中,你可能希望让你的实体有关系,它们在组合方面会非常庞大.在其他类型的DB中,您将拥有没有大量内部对象的扁平实体.这意味着如果您使用实体来公开您的API并希望将您的数据库从MySQL改为Cassandra – 那么您也需要更改您的API,这显然是一件坏事.
> Consumer Driven Contracts.可能这与之前的子弹相关,但是DTO使得更容易确保微服务之间的通信在其演变过程中不被破坏.由于合同和数据库没有耦合,因此更容易测试.
>聚合.有时您需要返回的数量超过单个数据库实体中的数量.在这种情况下,您的DTO将只是一个聚合器.
>表现.微服务意味着通过网络传输大量数据,这可能会使您遇到性能问题.如果您的微服务客户端需要的数据少于存储在数据库中的数据 – 您应该为它们提供更少的数据.再次 – 只需制作DTO,您的网络负载就会减少.
>忘掉LazyInitializationException.与您的ORM管理的域实体相比,DTO没有任何延迟加载和代理.
>使用正确的工具并不难以支持DTO层.通常,将实体映射到DTO和向后时会出现问题 – 每次要进行转换时都需要手动设置正确的字段.在向实体和DTO添加新字段时,很容易忘记设置映射,但幸运的是,有很多工具可以为您完成此任务.例如,我们曾经在项目中使用MapStruct – 它可以在编译时自动为您生成转换.
转载注明原文:java – 微服务Restful API – DTO或不? - 乐贴网