【问题标题】:Is there a benefit to using a DTO rather than a shared reference to Entities in a common assembly?在公共程序集中使用 DTO 而不是对实体的共享引用是否有好处?
【发布时间】:2010-10-11 22:18:47
【问题描述】:

我正在努力为一个让我发疯了很长时间的问题找到一个明确的最终答案。

通常表示 BLL 应包含业务逻辑和业务对象 (BO),并具有对 DAL 的引用。另一方面,DAL 不能引用 BLL,因此它不能接受 BO 作为参数,或将 BO 作为返回值返回。

这个问题最传统的答案是:

a) 接受简单参数,并返回(最好是 Typed)DataSets 和 DataTables 以返回数据: 命名空间 DAL { 公开课联系人 公共数据表 GetContacts(){...} 公共 UpdateContacts(数据表联系人){...}

b) 第二个最推荐的解决方案是定义临时的、可序列化的数据传输对象 (DTO)(有时称为值对象 (VO)),它只有字段和属性,没有方法,仅用于短暂传输数据备份到 BLL 层,在那里用于填充新的 BO,然后将它们丢弃。

c) 使用定义 BO 的通用第三个程序集(例如称为 Entities.dll),并被所有 3 层引用:UI、BLL 和 DAL。

选项 a) 实现的工作量最少(无需构建另一个程序集),因此经常被提出,但 DataTables 有额外的布线,不需要仅用于简单的操作。

但目前还不清楚 b) 或 c) 哪个更好......

我看到 b) 有时提供,但几乎从不提供 c),尽管 c) 似乎是两者中最简单的。

我错过了什么?为什么 c) 很少提供,尽管它在逻辑上看起来是最简单的,为什么 a) 在它显然不适合所有场景(例如返回单个对象)时提供?

谢谢!

【问题讨论】:

    标签: c# architecture


    【解决方案1】:

    嗯,我几乎看不到 (b) 在实践中被使用。我大部分时间都使用 (c) 中描述的方法(其他时候是我什至没有在 BLL/DAL 之间分离或根本没有域模型)。毕竟,业务和数据组件通常在物理上位于同一位置,因此这两者共享 BO 很简单。事实上,像 Hibernate、Entity Framework、Linq2Sql 等框架实际上鼓励 (c) 通过允许对复杂的域模型执行 ORM。

    DTO 更常用于将数据从 BLL 传递到 UI,尤其是。当 UI 和 BLL 部署在不同的服务器中时。在这种情况下,UI 可能需要域模型的简化视图,以减少跨进程往返并最大限度地减少更改的影响(当域模型更改时)。

    【讨论】:

      【解决方案2】:

      如果 (c) 很常见,我不会感到惊讶。如果你的 BLL 和 UI 在不同的服务器上,如果你使用 WCF,你也可以通过网络传递实体。 看看这个例子,了解如何对实体here [zip] 进行序列化,这里是downloads page 的链接。这篇文章也可能对serializing with WCF有帮助

      【讨论】:

      • 嗨乔纳森:第一个链接需要授权。至于第二个链接,您指的是哪一个——接口或数据服务示例?
      • 对不起,我现在添加了权限,所以你应该可以通过上面的链接下载它。它被称为“DDD 和 WCF - 序列化实体”。
      • 嗨乔纳森:感谢您的链接。结论:a) DTO 可以序列化/反序列化到同一个对象,如果两个层都引用相同的 BO/BEntities 程序集:DAL
      • 我想你很困惑。或许我是。我提议的是 c),它没有 DTO,也没有 DataSet,只有 BO(业务对象)。这些 BO 可以由 DAL 序列化,然后由 UI 直接引用。这就是 CSLA.NET 的工作方式。好处:逻辑和验证保存在一个地方。
      【解决方案3】:

      原始问题的附录:

      我认为(在 Buu Nguyen 的第一次响应之后,以下参考模式是完全可以接受的,甚至可能建议使用 LINQ 等:

      BLL > 
      
       v    Business Entities Layer (BEL)
      
      DAL >
      

      除非 BLL 和 DAL 位于不同的层,并且 BLL 通过 WCF 与 DAL 通信...? 在这种情况下,它将不起作用(DAL 通过 WCF 返回的业务实体将被序列化,并且在 BLL 端将被反序列化为原始 BE 的 Proxies...并且不会映射回到 BE 自己。或者这显然是错误的,当 BLL 和 DAL 处于同一层时,上述参考模式将适用,以及 在不同的层次?

      附录#2: 找到了一个有趣的链接,说明为什么为 BO 使用外部程序集实际上很好。 He states 认为“这违反了层应该只知道紧接在下面的层的规则,但是指示列名的数据库不在 BLL 的正下方,而是在 DAL 的下方。因此,未键入的数据集不会屏蔽您来自数据库,这就是为什么我认为它们是错误的。更好的解决方案是使用在单独的项目中定义的强类型对象。例如,DTO 中将有一个具有 Name 属性但没有 Grade 的 Teacher 类方法。”

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2011-12-27
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多