Entity Framework 7 코드를 사용하여 자체 참조 외래 키 관계 정의

ef-fluent-api entity-framework-core

문제

아래에서 볼 수있는 것처럼 ArticleComment 엔티티가 있습니다.

public class ArticleComment
 {
    public int ArticleCommentId { get; set; }
    public int? ArticleCommentParentId { get; set; }

    //[ForeignKey("ArticleCommentParentId")]
    public virtual ArticleComment Comment { get; set; }
    public DateTime ArticleDateCreated  { get; set; }
    public string ArticleCommentName { get; set; }
    public string ArticleCommentEmail { get; set; }
    public string ArticleCommentWebSite { get; set; }
    public string AricleCommentBody { get; set; }

    //[ForeignKey("UserIDfk")]   
    public virtual ApplicationUser ApplicationUser { get; set; }
    public Guid? UserIDfk { get; set; }

    public int ArticleIDfk { get; set; }
    //[ForeignKey("ArticleIDfk")]   
    public virtual Article Article { get; set; }


}

나는 하나의 주석이 많은 응답이나 자식을 가질 수있는 방식으로 외래 키 관계를 정의하고자하며 다음과 같이 유창한 API를 사용하여 관계를 만들려고했습니다.

public class ArticleComment
 {
    public int ArticleCommentId { get; set; }
    public int? ArticleCommentParentId { get; set; }

    //[ForeignKey("ArticleCommentParentId")]
    public virtual ArticleComment Comment { get; set; }
    public DateTime ArticleDateCreated  { get; set; }
    public string ArticleCommentName { get; set; }
    public string ArticleCommentEmail { get; set; }
    public string ArticleCommentWebSite { get; set; }
    public string AricleCommentBody { get; set; }

    //[ForeignKey("UserIDfk")]   
    public virtual ApplicationUser ApplicationUser { get; set; }
    public Guid? UserIDfk { get; set; }

    public int ArticleIDfk { get; set; }
    //[ForeignKey("ArticleIDfk")]   
    public virtual Article Article { get; set; }


}

나는 여기여기 에서 제안 된 해결책을 따라 갔지만 나는 메시지에 오류가있다.

FOREIGN KEY 제약 조건 'FK_ArticleComment_ArticleComment_ArticleCommentParentId'테이블 'ArticleComment'소개 사이클 또는 여러 계단식 경로가 발생할 수 있습니다. NO DELETE NO ACTION 또는 UP UP NO NO ACTION을 지정하거나 다른 FOREIGN KEY 제약 조건을 수정하십시오. 제약 조건 또는 색인을 생성 할 수 없습니다. 이전 오류를 참조하십시오.

우선은 비록 설정하여 OnDelete(DeleteBehavior.Restrict) 이 멀리 갈 것,하지만 문제를, 또한 내가 데이터 주석을 사용하려고했습니다 영속화 [ForeignKey("ArticleCommentParentId")] 당신이에 주석 코드를 볼 수 ArticleComment 정의,하지만 작동하지 않았다면, 나는 이것에 대해 감사 할 것입니다.

수락 된 답변

엔티티를 올바르게 모델링하지 않았습니다. 각 의견에는 ArticleComment 유형의 응답 집합 이 필요하며 해당 응답은 모두 해당 부모를 다시 가리키는 응답입니다 (추가 된 ICollection 응답 특성에 유의하십시오).

  public class ArticleComment
     {
        public ArticleComment()
        {
            Replies = new HashSet<ArticleComment>();
        }

        public int ArticleCommentId { get; set; }
        public int? ParentArticleCommentId { get; set; }
        public virtual ArticleComment ParentArticleComment{ get; set; }
        public virtual ICollection<ArticleComment> Replies { get; set; }

        //The rest of the properties omitted for clarity...
    }

... 그리고 유창한지도 작성 :

  public class ArticleComment
     {
        public ArticleComment()
        {
            Replies = new HashSet<ArticleComment>();
        }

        public int ArticleCommentId { get; set; }
        public int? ParentArticleCommentId { get; set; }
        public virtual ArticleComment ParentArticleComment{ get; set; }
        public virtual ICollection<ArticleComment> Replies { get; set; }

        //The rest of the properties omitted for clarity...
    }

위의 설정을 사용하면 개방형 트리 구조를 얻을 수 있습니다.

편집 : 속성을 사용하면 ParentArticleComment 속성을 장식해야합니다. 이 경우 EF는 관례에 따라 모든 관계를 해결할 것이라는 점을 고려하십시오.

  public class ArticleComment
     {
        public ArticleComment()
        {
            Replies = new HashSet<ArticleComment>();
        }

        public int ArticleCommentId { get; set; }
        public int? ParentArticleCommentId { get; set; }
        public virtual ArticleComment ParentArticleComment{ get; set; }
        public virtual ICollection<ArticleComment> Replies { get; set; }

        //The rest of the properties omitted for clarity...
    }

수집 속성의 경우 EF는 관계를 이해할 정도로 지능적입니다.


인기 답변

클래스를 단순화 (외래 키 지원 필드 제거)하고 작동합니다.
그것은 EF 버전의 문제 일 수 있습니다. (필자는 실제로 설치했으나 실제로는 rc1을 사용하고 있다고 생각합니다. 그러나 몇 가지 종속성 문제가 있었기 때문에 확실하지 않습니다) 또는 귀하의 모델이 될 수 있습니다.
어쨌든,이 소스는 잘 작동합니다.

public class ArticleComment
{
    public int ArticleCommentId { get; set; }

    public virtual ArticleComment Comment { get; set; }
    public DateTime ArticleDateCreated { get; set; }
    public string ArticleCommentName { get; set; }
    public string ArticleCommentEmail { get; set; }
    public string ArticleCommentWebSite { get; set; }
    public string AricleCommentBody { get; set; }
}

class Context : DbContext
{
    public Context(DbContextOptions dbContextOptions) : base(dbContextOptions)
    {}

    public DbSet<ArticleComment> Comments { get; set; }

    protected override void OnModelCreating(ModelBuilder modelBuilder)
    {
        modelBuilder.Entity<ArticleComment>()
            .HasOne(p => p.Comment)
            .WithMany();

    }
}

static class SampleData
{
    public static void Initialize(Context context)
    {
        if (!context.Comments.Any())
        {
            var comment1 = new ArticleComment()
            {
                AricleCommentBody = "Article 1"
            };

            var comment2 = new ArticleComment()
            {
                AricleCommentBody = "Article 2 that referes to 1",
                Comment = comment1
            };

            context.Comments.Add(comment2);
            context.Comments.Add(comment1);

            context.SaveChanges();
        }
    }
}



아래 라이선스: CC-BY-SA with attribution
와 제휴하지 않음 Stack Overflow
이 KB는 합법적입니까? 예, 이유를 알아보십시오.
아래 라이선스: CC-BY-SA with attribution
와 제휴하지 않음 Stack Overflow
이 KB는 합법적입니까? 예, 이유를 알아보십시오.