Linq-to-SQL和WCF服务 - 数据传输对象

时间:2011-12-22 10:14:35

标签: c# wcf linq-to-sql dto

在使用Linq-to-SQL和WCF服务开发n层应用程序时,我很好奇最佳实践。

特别是,我很感兴趣,例如,如何从两个相关表返回表示层数据。假设下一个情况(非常简化):

数据库有表格:

  • Ordersid, OrderName
  • OrderDetailsid, orderid, DetailName

中间层有OrderDetails的CRUD方法。因此,我需要有办法重建实体以附加到更新的上下文或从表示层返回时插入。

在表示层中,我需要从父表中显示OrderDetails的列表以及相应的OrderName

从服务返回的类有两种方法:

  1. 使用DTO自定义类来封装来自表和投影的数据:

    class OrderDetailDTO
    {
      public int Id { get; set; }
      public string DetailName { get; set; }
      public string OrderName { get; set; }
    }
    IEnumerable<OrderDetailDTO> GetOrderDetails()
    {
      var db = new LinqDataContext();
      return (from od in db.OrderDetails
              select new OrderDetailDTO
              {
                Id = od.id,
                DetailName = od.DetailName,
                OrderName = od.Order.OrderName
              }).ToList();
    }
    

    缺点:需要以两种方式分配每个字段,这对于表示层非常重要(当返回数据时以及创建新实体以附加到上下文时,当数据从表示层返回时)

  2. 使用自定义的Linq-to-SQL实体分部类:

    partial class OrderDetail
    {
      [DataMember]
      public string OrderName
      {
        get
        {
          return this.Order.OrderName    // return value from related entity
        }
        set {}
      }
    }
    
    IEnumerable<OrderDetail> GetOrderDetails()
    {
      var db = new LinqDataContext();
      var loadOptions = new DataLoadOptions();
      loadOptions.LoadWith<OrderDetail>(item => item.Order);
      db.LoadOptions = options;
      return (from od in db.OrderDetails
              select od).ToList();
    }
    
  3. 缺点:数据库查询将包含Orders表中的所有列,Linq-to-SQL将实现整个Order实体,尽管我只需要一个字段。

    抱歉这么长的故事。可能是我错过了什么?将不胜感激。

2 个答案:

答案 0 :(得分:3)

我想说使用DTO和Automapper,将数据库实体公开为datacontract不是一个好主意

答案 1 :(得分:1)

Linq to SQL的使用是否是您的要求,或者您仍然处于可以选择技术的设计阶段?如果是最新的,我建议使用具有自我跟踪实体(STE)的实体框架。当您从客户端返回实体时,所有客户端更改将由STE自动处理,您只需调用Save。包括相关实体也很容易:(...some query...).Orders.Include(c => c.OrderDetails)