EF6可选1:1包括不工作

时间:2016-10-09 06:39:18

标签: c# entity-framework linq eager-loading

尝试设置基本EF6可选1:1。非常令人沮丧。我看过很多帖子。

我有两个实体,宾客和座位,每个都可以独立存在,一个座位不需要客人,客人不需要座位。

嘉宾模特:

        public int ID { get; set; }

        public int? SeatID { get; set; }

        [Required]
        public string FirstName { get; set; }

        //Link to Seat
        public Seat Seat { get; set; }

座位模型:

        public int ID { get; set; }

        public int? GuestID { get; set; }

        [Required]
        public string SeatNumber { get; set; }

        public bool Occupied { get { return (GuestID == null ? true : false); } }

        //Link to Guest
        public Guest Guest{ get; set; }

到目前为止我遇到了很多问题。我必须将此添加到我的模型创建中才能使关系正常工作:

       modelBuilder.Entity<Seat>()
            .HasOptional(g => g.Guest)
            .WithOptionalDependent(s => s.Seat);

现在我的应用程序正在运行但是当我尝试使用include方法加载相关数据时,它只是空白,没有任何内容。

var seats = db.Seats.Include(s => s.Guest);
            return View(seats.ToList());

在我的观点中,我使用

@Html.DisplayFor(modelItem => item.Guest.FirstName)

我想知道如何使include语句工作,最好不要延迟加载(或者甚至如果必须的话)。另外,我不想有一个SeatAssignment表,我考虑过这条路。

我可以使用Viewmodel来实现这一点,但我不明白为什么1:1可选项不会加载相关数据。

根据要求,这里是生成的架构......绝对是奇怪的事情。作为旁注,我可以使用视图模型,但我不想。

Schema

2 个答案:

答案 0 :(得分:1)

1-0..1关系配置与您想要的方式不同。

  1. 1-0..1 X和Y之间的关系意味着XId是X中的主键,而且XId也是Y中的主键,也是外键
  2. 您要求的是m-n关系,m = 1且n = 1,因此配置应该不同。
  3. 根据上述规则,您的代码应如下

    来宾班

    public class Guest
    {
        public int ID { get; set; }
        [Required]
        public string FirstName { get; set; }
    
        public IList<Seat> Seats { get; set; }
    }
    

    座位等级

    public class Seat
    {
        public int ID { get; set; }
        [Required]
        public string SeatNumber{ get; set; }
    
        public IList<Guest> Guests { get; set; }
    }
    

    加入表格

    public GuestSeat
    {
         public int GuestID{get;set;}
         public int SeatID{get;set;}
    
         public DateTime ReservedDate{get;set;}
         // other fields goes here
    }
    

    <强>配置

    modelBuilder.Entity<GuestSeat>()
                .HasKey(gs => new {gs.GuestID,gs.SeatID})
                .ToTable("GuestSeats");
    modelBuilder.Entity<GuestSeat>()
                .HasRequired(g=>g.Guest)
                .WithMany(g=>g.Seats)
                .HasForeignKey(gs =>gs.GuestID)
                .DeleteOnCascade(false);
    modelBuilder.Entity<GuestSeat>()
                .HasRequired(s=>s.Seat)
                .WithMany(s=>s.Guests)
                .HasForeignKey(gs =>gs.SeatID)
                .DeleteOnCascade(false);
    

    此解决方案提供以下内容

    1. 作为嘉宾,在今天的活动中,我可以预订座位A,明天的活动,我可以保留座位B.
    2. 座位A可由Guest X占用,明天由Guest Y
    3. 占用
    4. 为了确保在指定日期某个人可以占用座位,您可以在SeatIDReservedDate上创建唯一索引。
    5. 希望这会对你有所帮助

答案 1 :(得分:1)

您必须如下所示构建模型。

public class Guest
{
        public int GuestId { get; set; }

        [Required]
        public string FirstName { get; set; }

        //Link to Seat
        public virtual Seat Seat { get; set; }
}

public class Seat
{
        public int SeatId { get; set; }

        [Required]
        public string SeatNumber { get; set; }

        public bool Occupied { get { return (GuestID == null ? true : false); }}

        //Link to Guest
        public virtual Guest Guest{ get; set; }
}

Fluent API映射:

  modelBuilder.Entity<Seat>()
            .HasOptional(g => g.Guest)
            .WithOptionalDependent(s => s.Seat);

然后:

var seats = db.Seats.Include(s => s.Guest).ToList();