【发布时间】:2016-12-19 01:25:02
【问题描述】:
有没有办法以某种方式组合来自两个模型的数据,然后在编辑操作的上下文中将它们 both 映射到同一个 viewModel?
在 ASP.NET MVC 中使用 Entity Framework 6.1.3 进行编辑操作时,我从未需要一次更新多个表。这是布局:
我有一个名为“Address”的数据库表,其中包含 StreetNumber、StreetName、City、State、ZipCode 的字段。它与另一个名为 Bars 的表具有 一对一 关系。如,一个栏只能有一个地址,一个地址只能有一个栏。
因为我将这些数据存储在两个单独的表中,所以我很难成功地实现一个编辑操作,该操作从 一个表单 (BarForm) 获取数据并且应该同时更新 Bar和地址数据库表。查看我的代码:
条形控制器
public ActionResult Edit(int id)
{
var bar = _context.Bars.SingleOrDefault(m => m.Id == id);
var address = _context.Addresses.SingleOrDefault(a => a.BarId == id);
//Make sure that the id actually exists:
if (bar == null)
{
return HttpNotFound();
}
var viewModel = Mapper.Map<Bar, BarFormViewModel>(bar, new BarFormViewModel());
if (address == null)
{
address = new Address();
}
Mapper.Map<Address, BarFormViewModel>(address, viewModel);
viewModel.IsNew = false;
return View("BarForm", viewModel);
}
[ValidateAntiForgeryToken]
public ActionResult Save(BarFormViewModel bar)
{
if (!ModelState.IsValid)
{
var viewModel = Mapper.Map<BarFormViewModel, BarFormViewModel>(bar, new BarFormViewModel());
viewModel.IsNew = false;
return View("BarForm", viewModel);
}
if (bar.Id == 0)
{
var newbar = Mapper.Map<BarFormViewModel, Bar>(bar);
newbar.LastUpdated = DateTime.UtcNow;
_context.Bars.Add(newbar);
var addressToAdd = Mapper.Map<BarFormViewModel, Address>(bar);
_context.Addresses.Add(addressToAdd);
}
else
{
var barInDb = _context.Bars.Single(b => b.Id == bar.Id);
var addressInDb = _context.Addresses.Single(a => a.BarId == bar.Id);
Mapper.Map<BarFormViewModel, Bar>(bar, barInDb);
Mapper.Map<BarFormViewModel, Address>(bar, addressInDb);
}
_context.SaveChanges();
return RedirectToAction("Index", "Bar");
}
领域模型:
public class Bar
{
public int Id { get; set; }
public string Name { get; set; }
[Required]
public string GooglePlaceId { get; set; }
public string SundayDiscounts { get; set; }
public string MondayDiscounts { get; set; }
public string TuesdayDiscounts { get; set; }
public string WednesdayDiscounts { get; set; }
public string ThursdayDiscounts { get; set; }
public string FridayDiscounts { get; set; }
public string SaturdayDiscounts { get; set; }
[Display(Name = "Last Updated")]
public DateTime LastUpdated { get; set; }
}
public class Address
{
public int Id { get; set; }
public int? Number { get; set; }
public string StreetName { get; set; }
public string City { get; set; }
public string State { get; set; }
[Required]
public int ZipCode { get; set; }
public Bar Bar { get; set; }
public int BarId { get; set; }
}
包含 Address 和 Bar 属性的视图模型:
{
public class BarFormViewModel
{
public int? Id { get; set; }
public string Name { get; set; }
[Required]
[Display(Name = "Google Place ID")]
public string GooglePlaceId { get; set; }
[Display(Name = "Sunday Happy Hour Info:")]
public string SundayDiscounts { get; set; }
[Display(Name = "Monday Happy Hour Info:")]
public string MondayDiscounts { get; set; }
[Display(Name = "Tuesday Happy Hour Info:")]
public string TuesdayDiscounts { get; set; }
[Display(Name = "Wednesday Happy Hour Info:")]
public string WednesdayDiscounts { get; set; }
[Display(Name = "Thursday Happy Hour Info:")]
public string ThursdayDiscounts { get; set; }
[Display(Name = "Friday Happy Hour Info:")]
public string FridayDiscounts { get; set; }
[Display(Name = "Saturday Happy Hour Info:")]
public string SaturdayDiscounts { get; set; }
[Display(Name = "Last Updated")]
public DateTime? LastUpdated { get; set; }
//Address Model Info
public Address Address { get; set; }
public int? AddressId { get; set; }
[RegularExpression("([1-9][0-9]*)", ErrorMessage = "Must be a number")]
public int? Number { get; set; }
public string StreetName { get; set; }
public string City { get; set; }
public string State { get; set; }
[Required]
public int? ZipCode { get; set; }
public bool IsNew { get; set; }
}
这里的问题是我在此设置中得到了一个空的 AddressId,这会在运行 Save 操作时导致异常。这是因为 BarForm 视图传递了一个从 Bar 对象映射的 ViewModel,而 Bar 域模型实际上没有 Address 信息,因为它不是 Address 模型/表。
有没有办法以某种方式组合来自 Address 和 Bar 模型的数据,然后将它们 both 映射到同一个 viewModel?
我在保存操作中不断收到此行的序列不包含元素错误:
var addressInDb = _context.Addresses.Single(a => a.Id == bar.AddressId);
我也试过了:
var addressInDb = _context.Addresses.Single(a => a.BarId == bar.Id);
都不行。我明白错误在说什么,并且还检查了我隐藏的 Addressid 字段的实际 HTML,它是空白的......请参阅我的 BarForm 视图中的代码:
@Html.HiddenFor(m => m.Id)
@Html.HiddenFor(m => m.AddressId)
@Html.AntiForgeryToken()
【问题讨论】:
标签: c# asp.net-mvc entity-framework mapping