我正在尝试与供应商,经销商和零售商定义供应链。此实体由Contract类绑定,该类还定义ProductLine及其将使用的产品。 对于给定的ProductLine,供应商(该ProductLine的唯一所有者)与经销商之间将签订合同,然后是该经销商与零售商之间的另一份合同。
问题是两个经销商之间还有合同,所以我尝试创建两个接口(ISeller和IBuyer)。供应商实施ISeller,零售商实施IBuyer和Dealer实现两个接口:
public class Supplier : ISeller
{
public int Id { get; set; }
public virtual ICollection<Contract> Contracts { get; set; }
}
public class Dealer : ISeller, IBuyer
{
public int Id { get; set; }
public virtual ICollection<Contract> Contracts { get; set; }
}
public class Retailer : IBuyer
{
public int Id { get; set; }
public virtual ICollection<Contract> Contracts { get; set; }
}
然后,合同将ISeller绑定到IBuyer,如下所示:
public class Contract
{
public int Id { get; set; }
public virtual ISeller Seller { get; set; }
public virtual IBuyer Buyer { get; set; }
}
在供应商/经销商或经销商/零售商之间创建合同按预期工作,但在尝试创建经销商/经销商合同时,我得到'违反多重性约束'。
答案 0 :(得分:6)
这段代码的问题似乎是接口。正如Slauma在评论中所说,Contract类的接口成员根本没有映射,因为EF不知道,例如,哪些实体 - 供应商,经销商或两者 - 映射到卖方成员。
从另一个方向来看,我们认为每个供应链参与者都有多个合同。这会在“合同”表中生成Supplier_id,Dealer_id,Reseller_id列。从EF的角度来看,供应商和经销商没有任何共同之处,零售商和经销商也没有。
您需要做的是拥有实体继承。经销商既可以是卖方也可以是买方,因此您不能拥有2个单独的类,因为C#不允许多重继承。定义ContractParticipant基础实体并让供应商,经销商和零售商继承该实体。然后你的数据模型看起来像:
public abstract class ContractParticipant
{
public int Id { get; set; }
[InverseProperty("Seller")]
public virtual ICollection<Contract> SellerContracts { get; set; }
[InverseProperty("Buyer")]
public virtual ICollection<Contract> BuyerContracts { get; set; }
}
public class Supplier : ContractParticipant
{
<...other properties here...>
}
public class Dealer : ContractParticipant
{
<...other properties here...>
}
public class Retailer : ContractParticipant
{
<...other properties here...>
}
public class Contract
{
public int Id { get; set; }
public virtual ContractParticipant Seller { get; set; }
public virtual ContractParticipant Buyer { get; set; }
}
此模型应生成无需任何其他配置即可支持您的方案的数据库结构。但是它也允许任何类型的参与者之间的合同但是如果你试图在数据模型中映射多重继承,你最终会得到类似this的东西 - 考虑是否要使数据模型复杂化以保留这些约束。 / p>
答案 1 :(得分:0)
尝试使用这个:
public class Contract
{
public int Id { get; set; }
public virtual Seller Sellers { get; set; }
public virtual Buyer Buyers { get; set; }
}