如何从实体框架中的详细信息部分检索主细节关系的主部分中的字段值

时间:2013-01-09 13:22:04

标签: vb.net entity-framework

我的实体模型中有一个主要的详细信息关系(以便轻松想到经典的Northwind Orders-OrderDetails)最终用户将在网格中输入主要部件的详细信息,然后向下移动到较低的网格输入“相关”详细信息。

在实体模型本身内,我希望每次创建与该订单相关的新OrderDetail记录并使用它来检索某些特定信息时,能够从订单表中检索“CustomerId”值的等效值需要在每个细节记录中。

在实体模型本身中是否有一种简单的方法可以做到这一点。我将在vb中这样做,但我可以阅读C#。

附加信息澄清:

Jeric在他的回答中提出了一个有趣的观点,我感谢他,这表明该表可能没有正确归一化。在任何正常情况下我都会同意,但在这里,我受到了我无法控制的限制。这是一个记录商业渔民捕鱼的应用程序。每次着陆可能包括几种不同种类的鱼类,所有着陆细节必须依法向政府机构报告,政府机构将信息传递给使用它来计算鱼类种群的科学家,从而计算渔获量的配额限制。

为此,捕获鱼的确切位置非常重要,因此每条线细节(着陆细节线)必须记录物品被捕获的区域和区域。对于大多数小型船只来说,这些信息几乎总是相同的(但是出海数月的大型船只可以捕获几个地区和区域的鱼类(因此需要)。)

为了尝试让应用程序的最终用户更容易,我觉得记录船只记录中的默认区域和区域的详细信息(相当于Northwind客户)是有意义的。在着陆标题表(Northwind Order)中,我有一个对vesselId的引用。因此,当输入着陆细节线时,我想引用登陆标题并检索船只ID,然后将其用作函数中的参数,以检索与该船只相关联的默认区域和区域。

当我使用实体框架执行此操作时,我还不知道着陆的最终ID是什么(它尚未提交,实体框架的优点在于它使得这种类型数据输入容易)所以我试图从登陆标题中获取船只ID,但尚未为其创建“官方”ID。

我希望这对于在大多数情况下(包括我自己)提示人们认为这是数据库规范化问题的问题更有意义。

我正在尝试做的是在登陆详细信息实体的一个On PropertyChanging事件中找到一种方法来检索其关联的登陆标头实体的vesselId,该实体尚未提交给数据库。它位于clientcache中,但尚未存在于数据库中。

非常感谢

1 个答案:

答案 0 :(得分:0)

如果我的问题是正确的,那么您说您的OrderDetail实体中有一些属性是根据您的客户实体填充的。我发现这很奇怪,因为您应该能够通过遍历从OrderDetail到Order to Customer的链接从OrderDetail实体查询任何Customer详细信息。您不需要在OrderDetail表下保留Customer属性(例如Gender)。您可能需要考虑尝试更好地规范化架构。

无论如何,假设你有这些实体:

public class Customer {
    [Key]
    public int Id {get; set;}
    public string Name {get; set;}
    public string Gender {get; set;}
    public virtual ICollection<Order> Orders {get; set;} //<-- I'm also assuming you have a 1 Customer to Many Order relationship
}


public class Order {
    [Key]
    public int Id {get; set;}
    [Required]
    public int CustomerId {get; set;}
    public virtual Customer Customer {get; set;} //<-- assumes a Customer Entity also exists
    public virtual ICollection<OrderDetail> OrderDetails {get; set;} //<-- I'm also assuming you have a 1 Order to Many Order Detail relationship
}

public class OrderDetail {
     [Key]
     public int Id {get;set;}
     [Required]
     public int OrderId {get; set;} //<-- each Order Detail *must* be linked to an order
     public virtual Order Order {get; set;}
     public string CustomerGender {get; set;} //<-- property that gets populated based on the customer that is related to the parent Order of this detail
     //other properties
 }

构建OrderDetail实例时,您应该知道它与哪个订单相关联,但在这种情况下可以看出客户不一定:

var orderDetail = new OrderDetail {OrderId = 1};

在insert方法中,您希望确保获取Customer详细信息并在插入之前填充orderDetail中的相关字段。由于您了解OrderId,因此可以使用LINQ查询相关的客户详细信息。在此示例中,我们希望获取Customer.Gender并将其分配给OrderDetail.CustomerGender。您可以在一个声明中写出来,但我会将其分解以便于阅读。

//step 1, get the Customer object based on the OrderId
var cust = context.Set<Order>().Include(o => o.Customer)
                  .Where(o => o.Id == orderDetail.OrderId)
                  .Select(o => o.Customer).SingleOrDefault();

//step 2, assign the Customer object property to the OrderDetail instance
orderDetail.CustomerGender = customer.Gender;

//step 3, persist the orderDetail entity
context.Set<OrderDetail>().Add(orderDetail);
context.SaveChanges();