【问题标题】:Entity Framework 5 - code first array navigation property one to many with Interface TypeEntity Framework 5 - 代码优先数组导航属性一对多与接口类型
【发布时间】:2013-01-25 07:18:24
【问题描述】:

这些是我的课程:

public class Post : IPost
{
    public int Id { get; set; }
    public virtual int[] DuplicateOf { get; set; }
    public virtual ICommentInfo[] Comments { get; set; }
}

 public class CommentInfo : ICommentInfo
{
    public virtual string Author { get; set; }
    public virtual int Id { get; set; }
    public virtual string Text { get; set; }

    public virtual int PostId{ get; set; }
    [ForeignKey("PostId")]
    public virtual Post Post { get; set; }
}

将此 CommentConfiguration 添加到 OnModelCreate():

HasRequired(c => c.Post)
            .WithMany(b=>(ICollection<CommentInfo>) b.Comments)
            .HasForeignKey(b=>b.PostId)
            .WillCascadeOnDelete(true);

我真的不明白为什么属性 Comments 总是为空,以及为什么 EF 不初始化它,因为它是虚拟的。 我也尝试禁用延迟加载,但是当我尝试使用context.Post.Include("Comments") 加载导航属性时,错误告诉我“没有名为评论的导航属性”。 所以我尝试使用Entity Framework Power Tools Beta 3查看实体数据模型,我发现即使两个表之间存在关系并且也有评论表端,表“发布”也没有导航端。

我真的不知道该转向哪个方向,可能是阵列的问题?我应该使用 Icollection 属性吗? 虽然我无法更改该属性的类型,因为 Post 正在实现一个接口。

我查看的每个样本都清晰且易于制作。请帮助我..提前谢谢你。

编辑:

这是我看了昨天发的link之后的变化。

  public class Post : IPost
  {
    public int Id { get; set; }
    public virtual int[] DuplicateOf { get; set; }
    public virtual ICollection<CommentInfo> Comments { get; set; } 
    ICommentInfo[] IPost.Comments { 
      get { return Comments ; } 
      set { Comments = (CommentInfo[])value; } }
  }

例外是:System.ObjectDisposedException :The ObjectContext instance has been disposed and can no longer be used for operations that require a connection,并在应用程序尝试获取评论时引发。 如果我删除 virtual 键,异常就会消失,但属性始终保持为空,并且值不会以任何方式持续存在。

EDITv2 我已经解决了添加新属性并将旧属性映射到它的问题。

public class Post : IPost
{
    public int Id { get; set; }
    public virtual int[] DuplicateOf { get; set; }
    public ICommentInfo[] Comments
    {
        get { return ListComments.ToArray(); }

    }
    public List<CommentInfo> ListComments {get;set;}
}

在我的 PostConfiguration OnModelCreate() 中,我使用 ListComments 属性作为导航属性,如下所示:

HasMany(b => b.ListComments)
                .WithRequired(c=>c.Post)
                .HasForeignKey(c=>c.PostId)
                .WillCascadeOnDelete(true);

现在它完美运行,比我预期的要简单,当我尝试接收评论集合时,如果我包含“ListComments”属性,我会得到 Post 数组。 感谢您的帮助!

【问题讨论】:

  • 经过一段时间,我发现这可能是我的类中接口类型的问题。我尝试按照此处的示例 [antix.co.uk/Blog/EF4-Code-First-and-Interface-Property-Types] 并更改了我的实现,但现在它引发了此异常:System.ObjectDisposedException:ObjectContext 实例已被释放,不能再用于需要连接的操作。
  • 好的,但是您如何从数据库中获取帖子以及您首先在哪里访问IPost.Comments?你不能在一个声明中做到这一点。

标签: ef-code-first code-first entity-framework-5 foreign-key-relationship navigation-properties


【解决方案1】:

我无法访问您评论中的链接,但我认为您已更改

public virtual ICommentInfo[] Comments { get; set; }

进入定义导航属性的常用方法:

public virtual ICollection<CommentInfo> Comments { get; set; }

因为实体框架在其概念模型中不支持接口。

关于已释放上下文的异常意味着您在从数据库中获取Post 对象后访问此属性释放上下文。这会在与数据库的连接丢失时触发延迟加载。解决方法是使用Include:

var posts = context.Posts.Include(p => p.Comments).Where(...)

现在可以一次性获取帖子和 cmets。

【讨论】:

  • 感谢您的回答。这是Link,对不起。我知道我的问题的解决方案是更改集合属性类型,但是 Post 类实现了接口 IPost 并且我从它接收类型。我尝试了链接中的解决方案,明确实现了 Comments 属性,但引发了该异常:public CommentInfo Comments { get; set; } ICommentInfo[] IPost.Comments { get { return Comments ; } set { Comments = (CommentInfo[])value; } }
  • 您能否将这段代码添加到问题以及实际引发异常的行中?
猜你喜欢
  • 2012-08-22
  • 2013-09-23
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2013-07-10
  • 2014-12-15
相关资源
最近更新 更多