Validation of nested models in view model in ASP.Net MVC

不羁的心 提交于 2020-01-03 18:34:11

问题


I have an application with a Company model. The Company model has a navigation property to an Address model (one-to-one relationship):

Company.cs

public class Company
{
    public int CompanyID { get; set; }
    public string Name { get; set; }

    // Snip...

    public virtual Address Address { get; set; }
}

I've created a view model to handle the edit, detail, and create actions:

CompanyViewModel.cs

public class CompanyViewModel
{
    public int CompanyID { get; set; }

    [Required]
    [StringLength(75, ErrorMessage = "Company Name cannot exceed 75 characters")]
    public string Name { get; set; }

    // Snip...

    public Address Address { get; set; }
}

I'm using AutoMapper in my controller to map back and forth between the model and view model, and everything is working properly. However, I now want to use validation on the address object - I do not want a company to be created without an address being present.

My first thought was the simple route - I tried putting a '[Required]' annotation on the Address property. This didn't do anything.

I then thought it would be better to do away with the Address property and abstract that data in the view model, so I added properties to the view model for all the properties in my Address class:

public string Address1 { get; set; }
public string Address2 { get; set; }
public string City { get; set; }
public string PostalCode { get; set; }
// etc....

This seemed like good practice, but now my AutoMapper can't map these properties to the Company class' Address object, so I had to manually map in the controller:

public ActionResult Details(int id = 0)
{
    // Snip code retrieving company from DB

    CompanyViewModel viewModel = new CompanyViewModel();
    viewModel.Name = company.Name;
    viewModel.Address1 = company.Address.Address1;

    // Snip...    

    return View(viewModel);
}

This leads to a lot of extra code in my controller instead of a nice one-line AutoMapper statement...so what's the right way to deal with this (validation of nested models in a view model)?

Is it good practice to expose the Address property directly in the view model, or better to abstract it out with separate properties like I have done?

Can AutoMapper work in a situation where source and destination are not exact matches?


回答1:


if you want automapper to be able to map your properties from model to your viewmodel without specifying the mappings explicitly, you've got to use the "flattenting convention" : means that you must concatenate the navigation property's name with its property names.

So your ViewModel should contain

public int CompanyID { get; set; }

    [Required]
    [StringLength(75, ErrorMessage = "Company Name cannot exceed 75 characters")]
    public string Name { get; set; }

    // Snip...
    //Address is the navigation property in Company, Address1 is the desired property from Address
    public string AddressAddress1 { get; set; }
    public string AddressAddress2 { get; set; }
    public string AddressCity { get; set; }
    public string AddressPostalCode { get; set; }
}

by the way, you can also tell AutoMapper to map properties which don't respect the naming convention explicitly :

Mapper.CreateMap<Company, CompanyViewModel>()
.ForMember(dest => dest.Address1, opt => opt.MapFrom(src => src.Address.Address1));


来源:https://stackoverflow.com/questions/19162593/validation-of-nested-models-in-view-model-in-asp-net-mvc

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!