Asp.net mvc 2 使用MVC2存储库Viewmodel模式更新EF4中的外键列表
好的,我真的很难在MVC2/EF4中更新外键列表。 我在一个模板对象之间有一个一对多的关系,这个模板对象可以有很多或者没有TemplateScenario对象 本质上,我在控制器中有一个编辑方法,它正试图做到这一点:Asp.net mvc 2 使用MVC2存储库Viewmodel模式更新EF4中的外键列表,asp.net-mvc-2,entity-framework-4,Asp.net Mvc 2,Entity Framework 4,好的,我真的很难在MVC2/EF4中更新外键列表。 我在一个模板对象之间有一个一对多的关系,这个模板对象可以有很多或者没有TemplateScenario对象 本质上,我在控制器中有一个编辑方法,它正试图做到这一点: // POST: /Modes/Edit/1 [HttpPost] public ActionResult Edit(int id, FormCollection formValues) { Template
// POST: /Modes/Edit/1
[HttpPost]
public ActionResult Edit(int id, FormCollection formValues)
{
Template template = _templateRepository.GetTemplate(id);
TemplateCreateViewModel viewModel = new TemplateCreateViewModel();
viewModel.Template = template;
viewModel.TemplateScenarioList = template.TemplateScenarios.ToList();
//Update the model
UpdateModel(viewModel);
UpdateModel(viewModel.Template.TemplateScenarios, "TemplateScenarioList", new[] { "ScenarioID", "TemplateID" });
_templateRepository.Save();
return RedirectToAction("Edit", new { id = template.TemplateID });
}
此代码成功更新了“模板”对象。它还添加了“templatescenario”子对象,但前提是我第一次将“templatescenarios”添加到此特定模板。如果给定模板的任何templatescenario对象已经存在,并且我尝试根据新列表更新它们,则会出现以下错误:
“操作失败:无法更改关系,因为一个或多个
的外键属性不可为空。当对
关系,相关外键属性设置为空值。如果
外键不支持空值,必须定义新关系,
必须为外键属性分配另一个非空值,或
必须删除不相关的对象。“
_templateRepository.Save();正在调用entities.SaveChanges()EF4方法
我可以通过自定义“更新”方法将templatescenario ID列表传递给我的存储库类来解决这个问题,如下所示:
public void Update(Template template, IList<int> templateScenarios)
{
//Delete Old Entries
foreach (TemplateScenario ts in entities.TemplateScenarios)
{
if (ts.TemplateID == template.TemplateID)
{
if (templateScenarios == null)
entities.TemplateScenarios.DeleteObject(ts);
else if (!templateScenarios.Where(tsl => tsl == ts.ScenarioID).Any())
entities.TemplateScenarios.DeleteObject(ts);
}
}
//Don't need to add anything if they are null.
if (templateScenarios == null)
return;
//Add New Entries
foreach (int ts in templateScenarios)
{
if (!entities.TemplateScenarios.Where(tsc => tsc.ScenarioID == ts && tsc.TemplateID == template.TemplateID).Any())
{
TemplateScenario tempScenToAdd = new TemplateScenario();
tempScenToAdd.ScenarioID = ts;
tempScenToAdd.TemplateID = template.TemplateID;
entities.TemplateScenarios.AddObject(tempScenToAdd);
}
}
}
公共作废更新(模板模板、IList模板场景)
{
//删除旧条目
foreach(实体中的TemplateScenario ts.TemplateScenarios)
{
if(ts.TemplateID==template.TemplateID)
{
if(templateScenarios==null)
entities.TemplateScenarios.DeleteObject(ts);
如果(!templateScenarios.Where(tsl=>tsl==ts.ScenarioID).Any())
entities.TemplateScenarios.DeleteObject(ts);
}
}
//如果它们为null,则不需要添加任何内容。
if(templateScenarios==null)
返回;
//添加新条目
foreach(模板场景中的int ts)
{
如果(!entities.TemplateScenarios.Where(tsc=>tsc.ScenarioID==ts&&tsc.TemplateID==template.TemplateID).Any())
{
TemplateScenario TempsceneToAdd=新的TemplateScenario();
tempsentoadd.ScenarioID=ts;
tempScenToAdd.TemplateID=template.TemplateID;
entities.TemplateScenarios.AddObject(TempSceneToAdd);
}
}
}
但这让我感觉很肮脏,我想我已经接近了第一种更自动的方法。我在互联网上搜索了一下,在stackoverflow上找到了一些类似的帖子,但我发现很难达到那个“啊哈”的时刻
谢谢
汤姆。顺便说一句,我解决了我的问题 问题是我的联接表错误地使用了它自己的主键,而不是使用基于两个外键的复合键。这显然是错误的/糟糕的做法,EF4和UpdateModel()的效果并不好
我从一位前同事那里继承了DB设计,因此我认为DB设计是正确的,没有过多考虑它。我知道,我太笨了。你知道为什么特定的数据库设计会导致这个问题吗?为什么表在组合上使用自己的主键时会引起问题?