Reputation: 2741
I'm reading tutorials and trying to get used to using ViewModels and Validation. I'm unsure as to whether the validation goes on the main Model or the View Model, I'd assume it'd be on the ViewModel. But it doesn't seem to make sense to add the validation on the ViewModel if I'm trying to inherit a class property so I left it on the model itself but the errors aren't showing up. Perhaps the Models are inefficient and need to be rearranged a bit?
NameModel
public class name {
[StringLength(50, ErrorMessage = "The {0} must be at least {2} characters long.", MinimumLength = 3)]
public string first { get; set; }
public string middle { get; set; }
[StringLength(50, ErrorMessage = "The {0} must be at least {2} characters long.", MinimumLength = 3)]
public string last { get; set; }
public string otherstuffnotneededontheview { get; set; }
}
RegisterViewModel
public class RegisterViewModel {
public name fname { get; set; }
public name lname { get; set; }
}
View
@model Project.ViewModels.RegisterViewModel
@using (Html.BeginForm())
{
<label>
@Html.TextBoxFor(model => model.fname.first)
@Html.ValidationMessageFor(model => model.fname.first)
</label>
<label>
@Html.TextBoxFor(model => model.lname.last)
@Html.ValidationMessageFor(model => model.lname.last)
</label>
<input type="submit" />
}
Controller
public ActionResult Register()
{
RegisterViewModel model = new RegisterViewModel();
return View(model);
}
[HttpPost]
public ActionResult Register(RegisterViewModel model)
{
return View(model);
}
Upvotes: 0
Views: 2048
Reputation: 14074
All validation needs to be done on the ViewModel.
In your case the RegisterViewModel is the data representation of the View associated public ActionResult Register()
, which means, the view returns a RegisterViewModel
object not a name
object.
ModelState.IsValid
checks validates the view's input [Register.cshtml] against the type it is bound to [RegisterViewModel
not name
]
So only the attributes applied to the RegisterViewModel
will be Validated.
So you need to perform validation in the ViewModel.
This in-turn provides you additional flexibility of being able to use different validation rules for different ViewModels (though the ViewModels are bound to the same underlying Model)
EDIT: (with code suggestion)
No validation rules are applied to the Model properties
public class name {
public string first { get; set; }
public string middle { get; set; }
public string last { get; set; }
public string otherstuffnotneededontheview { get; set; }
}
They are applied in the ViewModel instead
public class RegisterViewModel {
[StringLength(50, ErrorMessage = "The {0} must be at least {2} characters long.", MinimumLength = 3)]
public string fname { get; set; }
[StringLength(50, ErrorMessage = "The {0} must be at least {2} characters long.", MinimumLength = 3)]
public string lname { get; set; }
}
This change should be pretty much enough (guessing you're properly binding RegisterViewModel
to name
)
Upvotes: 6