在EF中更新父实体时如何添加/更新子实体

这两个实体是一对多关系(由代码优先fluent api构建)。

public class Parent

{

public Parent()

{

this.Children = new List<Child>();

}

public int Id { get; set; }

public virtual ICollection<Child> Children { get; set; }

}

public class Child

{

public int Id { get; set; }

public int ParentId { get; set; }

public string Data { get; set; }

}

在我的WebApi控制器中,我可以执行一些操作来创建一个父实体(工作正常)并更新一个父实体(存在一些问题)。更新操作如下所示:

public void Update(UpdateParentModel model)

{

//what should be done here?

}

目前我有两个想法:

  1. 获得命名为跟踪父实体existingmodel.Id中,并指定值model由一个实体之一。这听起来很愚蠢。而且model.Children我不知道哪个孩子是新孩子,哪个孩子被修改(甚至删除)。

  2. 通过创建一个新的父实体model,并将其附加到DbContext并保存。但是DbContext如何知道子状态(新的添加/删除/修改)?

实施此功能的正确方法是什么?

回答:

因为要发布到WebApi控制器的模型是与任何实体框架(EF)上下文分离的,所以唯一的选择是从数据库中加载对象图(包括其子项的父项),并比较已添加,删除或添加了哪些子项。更新。(除非您认为在分离状态下(在浏览器中或任何位置)使用自己的跟踪机制来跟踪更改,我认为这比以下情况更为复杂。)它看起来像这样:

public void Update(UpdateParentModel model)

{

var existingParent = _dbContext.Parents

.Where(p => p.Id == model.Id)

.Include(p => p.Children)

.SingleOrDefault();

if (existingParent != null)

{

// Update parent

_dbContext.Entry(existingParent).CurrentValues.SetValues(model);

// Delete children

foreach (var existingChild in existingParent.Children.ToList())

{

if (!model.Children.Any(c => c.Id == existingChild.Id))

_dbContext.Children.Remove(existingChild);

}

// Update and Insert children

foreach (var childModel in model.Children)

{

var existingChild = existingParent.Children

.Where(c => c.Id == childModel.Id)

.SingleOrDefault();

if (existingChild != null)

// Update child

_dbContext.Entry(existingChild).CurrentValues.SetValues(childModel);

else

{

// Insert child

var newChild = new Child

{

Data = childModel.Data,

//...

};

existingParent.Children.Add(newChild);

}

}

_dbContext.SaveChanges();

}

}

...CurrentValues.SetValues可以接受任何对象,并根据属性名称将属性值映射到附加的实体。如果模型中的属性名称与实体中的名称不同,则不能使用此方法,必须逐个分配值。

以上是 在EF中更新父实体时如何添加/更新子实体 的全部内容, 来源链接: utcz.com/qa/409658.html

回到顶部