views:

34

answers:

1

Does the ASP.NET MVC 2 model validation includes subobjects?

I have an instance "Filter", from this class:

public class Filter
{
    [StringLength(5)]
    String Text { get; set; }
}

in my main object:

public class MainObject
{
    public Filter filter;
}

However, when I do TryValidateModel(mainObject) the validation still works out even if "Text" in MainObject.Filter.Text is longer than 5 characters.

Is this intended, or am I doing something wrong?

+1  A: 

Two remarks:

  • Use public properties and not fields on your models
  • The instance you are trying to validate needs to go through the model binder for this to work

I think that the first remark needs not much explanation:

public class Filter
{
    [StringLength(5)]
    public String Text { get; set; }
}

public class MainObject
{
    public Filter Filter { get; set; }
}

As for the second, here's when it does not work:

public ActionResult Index()
{
    // Here the instantiation of the model didn't go through the model binder
    MainObject mo = GoFetchMainObjectSomewhere();
    bool isValid = TryValidateModel(mo); // This will always be true
    return View();
}

And here's when it will work:

public ActionResult Index(MainObject mo)
{
    bool isValid = TryValidateModel(mo);
    return View();
}

Of course in this case your code could be simplified to:

public ActionResult Index(MainObject mo)
{
    bool isValid = ModelState.IsValid;
    return View();
}

Conclusion: you rarely need TryValidateModel.

Darin Dimitrov
Great explanation!
Aros