一对一关系代码首先不遵循EF约定

时间:2016-05-08 23:17:19

标签: sql-server ef-code-first one-to-one

我尝试使用EF Code First为以下类组织一对一的关系。公共汽车是一个主要类别,附表是一个从属的。

public class Bus
{
    public int Id { get; set; }
    public virtual Schedule Schedule { get; set; }
}

public class Schedule
{
    public int Id { get; set; }
    public string Name { get; set; }
    public DateTime BusRouteStartTime { get; set; }
    public DateTime BusRouteEndTime { get; set; }
    public DateTime ArrivalTime { get; set; }
    public DateTime DepartureTime { get; set; }

    [ForeignKey("Bus")]
    public int BusId { get; set; }
    public virtual Bus Bus { get; set; }
}

我使用this教程制作了这个课程。当我在PCM中执行启用迁移时,我收到此错误:

  

Bus_Schedule_Target ::多重性在角色' Bus_Schedule_Target'在关系' Bus_Schedule'。由于Dependent Role属性不是关键属性,因此Dependent Role的多重性的上限必须为' *'。

我谷歌此错误并找到this解决方案。我修改了OnModelCreating():

modelBuilder.Entity<Schedule>().HasKey(s => s.Id);
modelBuilder.Entity<Bus>()
            .HasRequired(s => s.Schedule)
            .WithRequiredPrincipal(b => b.Bus);

不幸的是它没有帮助。当我理解默认依赖类的ID必须同时是主键和外键时,我继续谷歌。它不适合我,因为它可能导致以后丢弃表的问题,例如在级联删除中。

请帮助我,我知道这是一个重复的问题,但如果可以这样做的话会更好。

1 个答案:

答案 0 :(得分:0)

你可以执行一个技巧 - 创建一对多关系,但将其作为一对一掩饰:

public class Bus
{
    public int Id { get; set; }        
    [Obsolete]
    public virtual ICollection<Schedule> Schedules { get; set; }

    //Here I implemented primitive logic, you should expand it by your own.
    [NotMapped]
    public Schedule Schedule {
        get {
            return Schedules.FirstOrDefault();
        }
        set {                
            Schedules.Add(value);
        }
    }
}

public class Schedule
{
    //other stuff...

    [Index(IsUnique = true)]//This index will prevent from inserting duplicates
    public int BusId { get; set; }
    public virtual Bus Bus { get; set; }
} 

现在你可以按照你想要的那样使用这个类,所有你应该做的就是忽略Schedules属性,这就是为什么我用Obsolete属性标记它以提醒它。