实体框架 - 父母有子女和对一个孩子的引用

时间:2017-03-08 17:08:57

标签: entity-framework ef-code-first

我有一个非常简单的对象结构......一个有很多子节点的父对象......但它也有一个对这些子节点的引用。

public class History
{
    [Key]
    public int Id { get; set; }

    public virtual HistoryEvent ActiveEvent { get; set; }

    public virtual List<HistoryEvent> Events { get; set; }
}

public class HistoryEvent
{
    [Key]
    public int Id { get; set; }

    public string Name { get; set; }
}

    static void Main(string[] args)
    {
        using (var context = new EfTest())
        {
            var history = new History
            {
                Events = new List<HistoryEvent>
                {
                    new HistoryEvent { Name = "a" },
                    new HistoryEvent { Name = "b" },
                    new HistoryEvent { Name = "c" }
                }
            };

            history.ActiveEvent = history.Events.First();

            context.History.Add(history);

            context.SaveChanges();
        }
    }

数据库创建并展示我期望的......

Tables

但它不会保存......内部异常会给出这个......

Exception

请帮忙!

1 个答案:

答案 0 :(得分:0)

无法使用循环引用保存复杂对象,这会导致EF首先要保存哪个对象(如果错误则纠正我)

解决这种困惑只需在另一个之前插入一个

尝试这样做

        var history = new History
        {
            Events = new List<HistoryEvent>
            {
                new HistoryEvent { Name = "a" },
                new HistoryEvent { Name = "b" },
                new HistoryEvent { Name = "c" }
            }
        };

        //history.ActiveEvent = history.Events.First();

        context.History.Add(history);
        context.SaveChanges();//now every object has an Id

        history.ActiveEvent = history.Events.First();
        context.SaveChanges();

如果以上操作不起作用,您需要更改模型以手动包含外键(这可能有助于您进行更多控制)

public class History
{
[Key]
public int Id { get; set; }
public int? ActiveEventId { get; set; }
[ForeignKey("ActiveEventId")]
public virtual HistoryEvent ActiveEvent { get; set; }

public virtual List<HistoryEvent> Events { get; set; }
}

和HistoryEvent类相同

public class HistoryEvent
{
    [Key]
    public int Id { get; set; }

    public string Name { get; set; }
    public int? HistoryId {get; set; }
    [ForeignKey("HistoryId ")]
    public virtual History history { get; set; }
}

然后

  1. 插入包含空历史事件的历史记录

  2. 追加历史记录。手动记录

    等历史事件
    var Events = new List<HistoryEvent> {
                new HistoryEvent { Name = "a" ,HistoryId = history.Id},
                new HistoryEvent { Name = "b" ,HistoryId = history.Id},
                new HistoryEvent { Name = "c" ,HistoryId = history.Id}
               }
    
  3. 保存活动

  4. 获取Active eventId并更新历史记录

  5. 希望这会有所帮助