I'd like to use the data validation attributes in a library assembly, so that any consumer of the data can validate it without using a ModelBinder (in a console application, for instance). How can I do it?
I'd like to use the data validation attributes in a library assembly, so that any consumer of the data can validate it without using a ModelBinder (in a console application, for instance). How can I do it?
TryValidateProperty is just badly written - you have to jump through hoops to get it to work outside a Controller, and even then, if you use it twice, it will end up quietly setting ModelState to valid/invalid and stop alterring that state, and stop returning accurate results from then on.
I gave up on it and just wrote my own validator. This'll loop over any set of objects in any context and tell you if they're valid:
bool isValid = true;
var invalidFields = new List<string>();
foreach (var o in viewModels)
{
var properties = o.GetType()
.GetProperties(BindingFlags.Public | BindingFlags.Instance);
foreach(var prop in properties)
{
var attrs = prop.GetCustomAttributes(true);
if (attrs != null)
{
var val = prop.GetValue(o);
ValidationAttribute[] validatorAttrs = attrs
.Where(a => a is ValidationAttribute)
.Select(a => (ValidationAttribute)a).ToArray();
foreach(var attr in validatorAttrs)
{
bool thisFieldIsValid = attr.IsValid(val);
if (!thisFieldIsValid)
invalidFields.Add(prop.Name);
isValid = isValid && thisFieldIsValid;
}
}
}
}