【问题标题】:Reference the same entity by two different entities Ef Core两个不同的实体引用同一个实体 Ef Core
【发布时间】:2019-09-24 11:27:48
【问题描述】:

我对此有点困惑,我正在实现一个愿望清单,其中多个用户可以将相同的实体(产品)添加到他们的清单中。 我扩展了身份用户类并添加了ICollection<Product> 但我似乎无法弄清楚多个用户如何根据外键引用同一产品,因为每当用户将产品添加到他们的愿望清单时,它都会从以前的用户中删除,因为外键现在引用新用户。显然我的逻辑有缺陷,我误解了应该如何定义这种关系,你能指出我正确的方向吗?

这里是产品实体

    public class Product
    {
        [DatabaseGenerated(DatabaseGeneratedOption.Identity)]
        [Key]
        public int ProductId { get; set; }
        public string ProductName { get; set; }
        public virtual ProductType ProductType { get; set; }

        [ForeignKey("Category")]
        public int SubcategoryFK { get; set; }
        public virtual SubCategory Category { get; set; }
        public decimal Price { get; set; }
        public int NumberOfItems { get; set; }
        public string ImageUrl { get; set; }
        public string IsInStock { get; set; }
        public string ShortDescription { get; set; }
        public string LongDescription { get; set; }

        [ForeignKey("SalesUser")]
        public string SalesUserFK { get; set; }
        public virtual ApplicationUser SalesUser { get; set; }

并且关系是这样配置的

 modelBuilder.Entity<ApplicationUser>()
 .HasMany(a => a.Products)
 .WithOne(p => p.SalesUser).HasForeignKey(z => z.SalesUserFK).OnDelete(DeleteBehavior.ClientSetNull);

【问题讨论】:

  • 如果我的理解正确,一个用户可以拥有多个产品,一个产品可以与多个用户相关联。这称为多对多关系。这种关系通常通过添加表示关系的中间表/实体来建模。在您的情况下,您可能有一个 ProductUser 实体,该实体具有 Product 和 User 的外键。产品和用户都将拥有一个 ProductUser 集合。

标签: c# asp.net-core entity-framework-core


【解决方案1】:

正如 Kei 所说,ProductUser 的关系是多对多的。在 EF Core 中,尚不支持没有实体类来表示连接表的Many-to-many 关系。但是,您可以通过包含连接表的实体类并映射两个单独的一对多关系来表示多对多关系。

public class Product
{
    [DatabaseGenerated(DatabaseGeneratedOption.Identity)]
    [Key]
    public int ProductId { get; set; }
    public string ProductName { get; set; }
    public virtual ProductType ProductType { get; set; }

    [ForeignKey("Category")]
    public int SubcategoryFK { get; set; }
    public virtual SubCategory Category { get; set; }
    public decimal Price { get; set; }
    public int NumberOfItems { get; set; }
    public string ImageUrl { get; set; }
    public string IsInStock { get; set; }
    public string ShortDescription { get; set; }
    public string LongDescription { get; set; }

    public List<UserProduct> UserProducts { get; set; }
}

public class ApplicationUser:IdentityUser
{
    public List<UserProduct> UserProducts { get; set; }
}

public class UserProduct
{
    public int ProductId { get; set; }
    public Product Product { get; set; }

    public Guid ApplicationUserId { get; set; }

    public ApplicationUser ApplicationUser { get; set; }
}

数据库上下文:

protected override void OnModelCreating(ModelBuilder modelBuilder)
    {
        modelBuilder.Entity<UserProduct>()
            .HasKey(up => new { up.ProductId, up.ApplicationUserId });

        modelBuilder.Entity<UserProduct>()
            .HasOne(up => up.Product)
            .WithMany(p => p.UserProducts)
            .HasForeignKey(up => up.ProductId);

        modelBuilder.Entity<UserProduct>()
            .HasOne(up => up.ApplicationUser)
            .WithMany(au => au.UserProducts)
            .HasForeignKey(up => up.ApplicationUserId);
    }

参考:Many-to-many relationshipCascade Delete

【讨论】:

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