I'm making a EF code first MVC model to store articles.
Each article can have multiple pages, so I have made the key a composite key of an ID plus a page number.
I also want articles to have sub-articles, so I want articles to self-reference themselves with a foreign key.
As the key is a composite key I'm struggling with the self-referencing. When I scaffold the model and attempt to use the controls I get 'System.StackOverflowException'
public class Article
{
[Key, Column(Order = 0)]
public int ArticleID { get; set; }
[Key, Column(Order = 1)]
public int ArticlePageNo { get; set; }
public string ArticleTitle { get; set; }
public string ArticleBody { get; set; }
[ForeignKey("ArticleID, ArticlePageNo")]
public Article ArticleParent { get; set; }
}
I do think that you're not using EF properly, in this case. If I understand corectly your code, EF will try to reference the object to itself and, if you're using an eager loading scenario, that will result in a Stackoverflow exception. So you are actually defining a 1 to 1 relationship between the Article and Article, specifying both the primary key and the foreign key as a composite key formed from ArticleID and ArticlePageNo. Not a thing EF can digest. I would suggest you remodel your data: so you have an one to many relationship between article and page, and a one to many relationship between article and article. The code would look somehing like this:
public class Article
{
// object unique ID
public int Id { get; set; }
public string Title { get; set; }
// parent Id used as foreign key
public int? ParentArticleId { get; set; }
// navigational property for parent
public virtual Article ParentArticle { get; set; }
// navigational property for children
public virtual ICollection<Article> Articles { get; set; }
// navigational property for article pages
public virtual ICollection<ArticlePage> Pages { get; set; }
}
public class ArticlePage
{
// object unique ID
public int Id { get; set; }
public string PageBody { get; set; }
// parent Id used as foreign key
public int ArticleId { get; set; }
// navigational property for parent article
public virtual Article { get; set; }
}
This model achieves what I was attempting to do but following the feedback I may rethink my approach.
public class Article
{
[Key, Column(Order = 0)]
public int ArticleID { get; set; }
[Key, Column(Order = 1)]
public int ArticlePageNo { get; set; }
public string ArticleTitle { get; set; }
public string ArticleBody { get; set; }
public int? ParentArticleID { get; set; }
public int? ParentArticlePageNo { get; set; }
[ForeignKey("ParentArticleID,ParentArticlePageNo")]
public virtual Article ArticleParent { get; set; }
public virtual ICollection<Article> Articles { get; set; }
}
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.