0

I have read many by many solution but i can't understand deeply about what or when i use View Model? For example, when i have a Register form for User to register, i want to hava an field Confirm Password, but i don't think should add it into the User entity. So i have this ViewModel:

public class RegisterViewModel
{
    public User User { get; set; }
    public IEnumerable<SelectListItem> City { get; set; }
    public IEnumerable<SelectListItem> Ward { get; set; }
    [Required(ErrorMessage = "Bạn chưa nhập lại mật khẩu.")]
    [StringLength(100, ErrorMessage = "Mật khẩu phải có ít nhất {2} ký tự.", MinimumLength = 6)]
    [DataType(DataType.Password)]
    [System.Web.Mvc.Compare("User.Password", ErrorMessage = "Mật khẩu không khớp.")]
    public string ConfimPass { get; set; }
}

So after read this link How to properly implement "Confirm Password" in ASP.NET MVC 3? . I don't know why they should replace the Password field which is already in User entity. I'm using unobstrusive client validation so it does work if i use this Model View. In my View, i must use m=> m.User.Username but not m=>m.Username, etc... Because of this, my validation such as compare password, or just remote validation not work well with the name in my View like m=>m.User.Username. What is wrong with my structure or my Model View in my thinking?

Community
  • 1
  • 1
Luffy
  • 63
  • 2
  • 9
  • 1
    possible duplicate of [ViewModel Best Practices](http://stackoverflow.com/questions/664205/viewmodel-best-practices) – Erik Philips Aug 13 '13 at 08:15

1 Answers1

0

There is no single rule and you need to stay pragmatic, having said that ViewModel and a Model (or Domain Model) are 2 different things. No you don't pollute your entities by placing properties that don't belong to them. The idea is that your UI should be interchangeable and your domain should not in any way depend on it. The dependencies should be inverted. Maybe tomorrow you'd switch (or extend) your UI layer to WPF (for example) ? Where your current ViewModels (with their attributes) wouldn't make much sense. In your case, yes you should be creating a view model and keep everything relevant to the view in them, after which you map/pass values back to your domain model. I hope I'm making sense, let me know if you need clarifications.

In your case I'd probably create a flattened RegisterViewModel that would include only the information needed to register a user, for example:

public class RegisterViewModel
{
    [Required]
    public string DisplayName { get; set; }
    [Required]
    public string FirstName { get; set; }

    // etc ...

    public IEnumerable<SelectListItem> City { get; set; }
    public IEnumerable<SelectListItem> Ward { get; set; }
    [Required(ErrorMessage = "Bạn chưa nhập lại mật khẩu.")]
    [StringLength(100, ErrorMessage = "Mật khẩu phải có ít nhất {2} ký tự.", MinimumLength = 6)]
    [DataType(DataType.Password)]
    [System.Web.Mvc.Compare("User.Password", ErrorMessage = "Mật khẩu không khớp.")]
    public string ConfimPass { get; set; }
}
Dimitar Dimitrov
  • 14,868
  • 8
  • 51
  • 79
  • But how about my validation rule? If i don't `pollute entities by placing properties that don't belong to them`. My view has the same column (field) with `User` table? Why i should add the same properties and validation again in my Model View? – Luffy Aug 13 '13 at 08:35
  • Again, it's not a rule, but it's what I would do, in my domain model I don't have validation rules the same way I have them in my UI layer. I don't want my domain model to even know what I'm using as a front end. -> `System.Web.Mvc.Compare` is no-where to be found in my domain. – Dimitar Dimitrov Aug 13 '13 at 08:45
  • Basically, i just create View Model and add the properties belong to my View, also add Validation rule here? I always confused about why i have to replace all prop in `User` entity even if i can use `public User User {get;set;}`. How can i pass the value if my view things like `Html.EditorFor(m=>m.Username)` but not `Html.EditorFor(m=>m.User.Username)` – Luffy Aug 13 '13 at 08:56