实体框架端口从模型优先到代码优先

时间:2012-03-20 17:33:58

标签: asp.net-mvc entity-framework entity-framework-4

我仍然在寻求从EntityFramework的Model First到Code First实现的移植。在Eranga的帮助下,我取得了重大进展。我遇到了另一个障碍,我只是无法解释什么是hapening。我有两个实体对象主题和课程

  • 主题可以有一个必需的课程
  • 课程可以包含0个或更多主题

当我执行以下linq时,它会生成奇怪的SQL

    var topics = from o in db.Topics where o.ParentTopic == null && 
            o.Course.Id == c.Id select o;

生成的SQL是

SELECT 
[Extent1].[Id] AS [Id], 
[Extent1].[Name] AS [Name], 
[Extent1].[ShortDescription] AS [ShortDescription], 
[Extent1].[LongDescription] AS [LongDescription], 
[Extent1].[Property] AS [Property], 
[Extent1].[Difficulty] AS [Difficulty], 
[Extent1].[Weight] AS [Weight], 
[Extent1].[Course_Id] AS [Course_Id], 
[Extent1].[ParentTopic_Id] AS [ParentTopic_Id], 
[Extent1].[Course_Id1] AS [Course_Id1]
FROM [dbo].[Topics] AS [Extent1]
WHERE ([Extent1].[ParentTopic_Id] IS NULL) AND ([Extent1].[Course_Id] = @p__linq__0)

请注意,有一个名为Course_Id1的添加字段不在我的对象中,并且未声明为外键。我认为在OnModelCreating()中我已经从两侧正确指定了父子关系(我原以为你只需要从任何一方做到这一点),但我不能让EntityFramework不生成显然不存在的额外字段在数据库中。记住我的数据库最初是使用ModelFirst方法创建的。

任何人都可以解释额外字段来自哪里????

    protected override void OnModelCreating(DbModelBuilder modelBuilder)
    {
        //Topic
        modelBuilder.Entity<Topic>()
            .HasRequired(m => m.Course)
            .WithMany(m=>m.Topics)
            .HasForeignKey(m => m.Course_Id);
        modelBuilder.Entity<Topic>()
            .HasOptional(m => m.ParentTopic)
            .WithMany(m => m.ChildTopics)
            .HasForeignKey(m => m.ParentTopic_Id);

        //////// lots of code removed for brevity. //////

        modelBuilder.Entity<Course>()
            .HasMany(m=>m.Topics)
            .WithRequired(m => m.Course)
            .HasForeignKey(m => m.Course_Id);
    }


public partial class Topic
{
    public int Id { get; set; }
    [Required]
    public string Name { get; set; }
    public string ShortDescription { get; set; }
    public string LongDescription { get; set; }
    public string Property { get; set; }
    public double? Difficulty { get; set; }
    public double? Weight { get; set; }

    [JsonIgnore]
    public virtual Course Course { get; set; }
    public int Course_Id { get; set; }

    [JsonIgnore]
    public virtual ICollection<Question> Questions { get; set; }

    [JsonIgnore]
    public virtual ICollection<Topic> ChildTopics { get; set; }

    [JsonIgnore]
    public virtual Topic ParentTopic { get; set; }
    public int? ParentTopic_Id { get; set; }

    [JsonIgnore]
    public virtual ICollection<RTIQueueEntryData> RTIQueueEntryData { get; set; }

    [JsonIgnore]
    public virtual ICollection<Intervention> Interventions { get; set; }

    [JsonIgnore]
    public virtual ICollection<RtiStudentGroup> RtiStudentGroups { get; set; }
}

public partial class Course
{
    public int Id { get; set; }
    [Required]
    public string Name { get; set; }
    [Required]
    public string Description { get; set; }
    public string Version { get; set; }
    public string Year { get; set; }
    public string ImportedId { get; set; }
    [Required]
    public string LocalCourseNumber { get; set; }
    [Required]
    public string NCESCourseNumber { get; set; }
    [Required]
    public string StateCourseNumber { get; set; }
    public int? Grade { get; set; }

    [JsonIgnore]
    public virtual ICollection<Topic> PerformanceIndicators { get; set; }

    [JsonIgnore]
    public virtual Department Department { get; set; }
    public int DepartmentId { get; set; }

    [JsonIgnore]
    public virtual ICollection<StudentGroup> StudentGroups { get; set; }

    [JsonIgnore]
    public virtual ICollection<CutPointTemplate> CutPointTemplates { get; set; }

    [JsonIgnore]
    public virtual School School { get; set; }
    public int School_Id { get; set; }

    [JsonIgnore]
    public virtual ICollection<Staff> RTIStaff { get; set; }

    [JsonIgnore]
    public virtual ICollection<Topic> Topics { get; set; }
}

1 个答案:

答案 0 :(得分:1)

由于此导航属性,您在约会中创建的CourseTopic之间存在另一种关系:

public virtual ICollection<Topic> PerformanceIndicators { get; set; }

EF会将关系的一个(不可见的,未暴露的)结束放入Topic类。默认情况下,关系是一对多关系。因此,您在Topics表(= Course_Id1)中获得了额外的外键属性。