Bri*_*lis 72 .net asp.net design-patterns dto
我已经看到很多关于将DTO映射到Domain Objects的问题,但我觉得他们没有回答我的问题.我之前使用过很多方法并有自己的看法,但我正在寻找一些更具体的东西.
情况:
我们有很多域对象.我们使用CSLA模型,因此我们的域对象可能非常复杂,并且包含自己的数据访问.你不想在线上传递这些.我们将编写一些新服务,以多种格式(.Net,JSON等)返回数据.出于这个(以及其他原因),我们还创建了一个精简的数据传输对象,以便在线路上传递.
我的问题是如何连接DTO和Domain对象?
我的第一反应是使用Fowler,DTO模式类型的解决方案.我已经多次看过这件事了,对我来说感觉很对.域对象不包含对DTO的引用.调用外部实体("映射器"或"汇编器")以从域对象创建DTO.通常在域对象端有一个ORM.这样做的缺点是"映射器"在任何真实情况下都会变得非常复杂,并且可能非常脆弱.
提出的另一个想法是域对象"包含"DTO,因为它只是一个精益数据对象.域对象属性将在内部引用DTO属性,如果需要,可以返回DTO.我可以看到没有问题,但感觉不对.我看过一些使用NHibernate的人似乎使用这种方法的文章.
还有其他方法吗?以上是值得使用的方式之一吗?如果是,如果没有,为什么?
感谢您提前了解任何信息.
Jos*_*rke 38
当您仅支持单个映射时,拥有位于域和DTO之间的映射器的好处并不明显,但随着映射数量的增加,将该代码与域隔离有助于使域更简单和更精简.你不会因为额外的重量而混乱你的域名.
就个人而言,我尝试将映射保留在我的域实体之外,并将责任放在我称之为"管理器/服务层"的内容中.这是位于应用程序和存储库之间的层,并提供业务逻辑,例如工作流协调(如果修改A,则可能还必须修改B,因此服务A将与服务B一起使用).
如果我有很多可能的结尾格式,我可能会考虑创建一个可以使用访问者模式的可插入格式化程序,例如转换我的实体,但我还没有找到任何这种复杂的需求.
Gar*_*ler 24
您可以使用自动化程序,例如Jimmy Bogard编写的自动程序,它在对象之间没有连接,并依赖于遵循的命名约定.
将映射逻辑保留在您的实体中意味着您的域对象现在知道它不需要知道的“实现细节”。通常,DTO 是您通往外部世界的网关(来自传入请求或通过从外部服务/数据库读取)。由于实体是您的业务逻辑的一部分,因此最好将这些详细信息保留在实体之外。
将映射保留在其他地方将是唯一的选择 - 但它应该去哪里?我曾尝试引入映射对象/服务,但毕竟说完了,这似乎是过度设计(可能是)。我在使用 Automapper 等较小的项目时取得了一些成功,但像 Automapper 这样的工具也有自己的缺陷。我有一些很难找到与映射相关的问题,因为 Automapper 的映射是隐式的,并且与代码的其余部分完全分离(不像“关注点分离”,而更像是“上帝遗弃的映射在哪里存在”),所以他们有时很难追踪。并不是说 Automapper 没有它的用途,因为它有。我只是认为映射应该是尽可能明显和透明的东西,以避免出现问题。
我没有创建映射服务层,而是成功地将我的映射保存在我的 DTO 中。由于 DTO 始终位于应用程序的边界,因此它们可以了解业务对象并找出如何从它们映射到它们。即使映射的数量缩放到合理的数量,它也能正常工作。所有映射都在一个地方,您不必在数据层、反腐败层或表示层中管理一堆映射服务。相反,映射只是委托给与请求/响应相关的 DTO 的实现细节。由于序列化程序通常仅在您通过网络发送时序列化属性和字段,因此您不会遇到任何问题。就个人而言,我发现这是最干净的选择,我可以说,根据我的经验,
我们使用T4模板来创建映射类.
Pro - 在编译时可用的人类可读代码,比运行时映射器更快.100%控制代码(可以使用部分方法/模板模式在ad-hoc基础上扩展功能)
Con's - 排除某些属性,域对象集合等,学习T4语法.
归档时间: |
|
查看次数: |
51285 次 |
最近记录: |