簡體   English   中英

ASP.NET MVC 5編輯操作-如何寫入多個數據庫表/模型

[英]ASP.NET MVC 5 Edit Action - How to write to Multiple DB Tables/Models

有沒有辦法以某種方式組合來自兩個模型的數據,然后在編輯操作的上下文中將它們映射到同一viewModel?

我從來沒有在帶有實體框架6.1.3的ASP.NET MVC中的編輯操作中一次更新過幾個表。 這是布局:

我有一個名為“地址”的數據庫表,其中具有StreetNumber,StreetName,City,State,ZipCode的字段。 它與另一個稱為Bars的表具有一對一的關系。 如圖所示,一個條只能有一個地址,而一個地址只能有一個地址。

因為我將這些數據存儲在兩個單獨的表中,所以很難成功地執行Edit操作,該操作從一種表單 (BarForm)中獲取數據,並且應該同時更新Bar和Address數據庫表。 看我的代碼:

條形控制器

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; }
    }

包含地址和欄屬性的視圖模型

{
    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模型/表。

有沒有辦法以某種方式從兩個地址和酒吧結合模型中的數據,然后將它們映射到相同的視圖模型?

在“保存”操作中,此行不斷出現“序列不包含任何元素”錯誤:

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()

刪除new BarFormViewModel()作為映射調用中的第二個參數,這是不必要的。

在您的發布操作中,在if語句中,該語句檢查ModelState是否有效以及bar.Id == 0,bar已經是視圖模型,因此無需映射。

並且,當您創建AutoMapper映射時,必須創建一個自定義屬性映射,因為Address.Id屬性不會自動映射到AddressId屬性,因為名稱不同。

AutoMapper.Mapper.CreateMap<Address, BarFormViewModel>()
.ForMember(dest => dest.AddressId, o => o.MapFrom(source => source.Id));

然后對逆映射執行相同的操作。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM