使用代码优先实体框架在模型类中建立关系

Posted

技术标签:

【中文标题】使用代码优先实体框架在模型类中建立关系【英文标题】:Making Relations in a model class with code first Entiy framework 【发布时间】:2021-10-28 00:18:54 【问题描述】:

我正在使用 asp.net mvc,对于数据部分,我使用的是代码优先方法,并且我有一个名为“Comment”的模型类。我想实现嵌套的 cmets(我想要回复选项)。这是我的模型类:

 public class Comment

    [Key]
    public int CommentID  get; set; 

    public int PostID  get; set; 

    //if it is null (or zero) , it is a father comment
    //if it is not null , it is a boy comment
    public int ParentID  get; set; 
    [Display(Name = "نام")]
    [Required(ErrorMessage = "لطفا نام خود را وارد کنید")]
    [DataType(DataType.Text)]
    [MaxLength(200)]

    public string CommentName  get; set; 
    [Display(Name = "ایمیل")]
    [Required(ErrorMessage = "لطفا ایمیل خود را وارد کنید")]
    [DataType(DataType.Text)]
    [MaxLength(200)]

    public string CommentEmail  get; set; 
    [Display(Name = "متن نظر")]
    [Required(ErrorMessage = "لطفا نظر خودرا بنویسید")]
    [DataType(DataType.MultilineText)]
    public string CommentText  get; set; 
    public DateTime CommentDate  get; set; 
    public bool IsCommentOk  get; set; 

    public virtual Post Post  get; set; 
    public virtual Comment Comment1  get; set; 
    public virtual Lis<Comment> Comment2  get; set; 
    public Comment()
    

    

我想在 'ParrentID' 和 'CommentID' 之间建立关系。如果 ParentID 为 0 ,它是普通评论,但如果它不为零,它正在回复评论,它的值显示其父评论的 commentID。我使用此代码实现了这个想法:

        public virtual Comment Comment1  get; set; 
        public virtual List<Comment> Comment2  get; set; 

但这不起作用。有什么问题,解决方法是什么?

【问题讨论】:

【参考方案1】:

请看下面我试图评论并使其尽可能简单,以便您理解。

我这样做的原因是你不需要像@Serge 那样添加额外的配置。这就是 ORM 最有用的原因

public class Comment

    [Key]
    public int CommentID  get; set; 
    
    // here to you dont need this, as long as you have post, post_Id will be created 
    // public int PostID  get; set; 
    
    // As long as it has children then this is a parent of children
    // Parent_Id will be automaticly created in the db, 
    // so you dont need to add it here
    // so when you save an item with children, those children will automaticly inherit 
    // the current id.
    public virtual List<Comment> Children  get; set; 
    
    public virtual Comment Parent  get; set; 
    [Display(Name = "نام")]
    [Required(ErrorMessage = "لطفا نام خود را وارد کنید")]
    [DataType(DataType.Text)]
    [MaxLength(200)]

    public string CommentName  get; set; 
    [Display(Name = "ایمیل")]
    [Required(ErrorMessage = "لطفا ایمیل خود را وارد کنید")]
    [DataType(DataType.Text)]
    [MaxLength(200)]

    public string CommentEmail  get; set; 
    [Display(Name = "متن نظر")]
    [Required(ErrorMessage = "لطفا نظر خودرا بنویسید")]
    [DataType(DataType.MultilineText)]
    public string CommentText  get; set; 
    public DateTime CommentDate  get; set; 
    public bool IsCommentOk  get; set; 
    public virtual Post Post  get; set; 
    public Comment()
    

    

【讨论】:

我不明白您为什么要删除 postID 。当您不知道特定评论属于哪个帖子时,您如何处理?你能再解释一下吗? 我已经工作并建立了一个库EntityWorker.Core所以我对ORM非常了解。这一切都取决于你真正想要什么以及你希望你的班级是什么样子。这些 ForgenKey 是自动创建的,不需要添加。但如果你愿意,你也可以添加它们,但你必须使用 @Serge 解决方案。在此处阅读有关 EntityFramework 的更多信息,docs.microsoft.com/en-us/ef/core/modeling/…【参考方案2】:

试试这个

 public class Comment

    [Key]
    public int CommentID  get; set; 

    .....

    public int? ParentID  get; set; 
    
     public virtual Comment Parent  get; set; 

     public virtual ICollection<Comment> Children  get; set; 

并将其添加到您的数据库上下文中

public class Context: DbContext 


    public DbSet<Comment> Comments  get; set; 
        
    protected override void OnModelCreating(DbModelBuilder modelBuilder)
    
       modelBuilder.Entity<Comment>()
            .HasOne(s => s.Parent)
            .WithMany(m => m.Children)
            .HasForeignKey(e => e.ParentID);
    

  

【讨论】:

我应该如何将代码的第二部分添加到我的数据库上下文中?没有功能! @MohammadYoosefiyan 检查我的更新答案

以上是关于使用代码优先实体框架在模型类中建立关系的主要内容,如果未能解决你的问题,请参考以下文章

使用实体框架 4.1 代码优先方法将一对一的表关系映射到单个实体

实体框架代码优先:关系约束中的从属角色和主体角色中的属性数量必须相同

实体框架核心关系问题(代码优先) - 重复列

实体框架代码首先使用现有数据库

PHP中的代码优先实体框架模型

如何在实体框架中定义存储过程(代码优先)?