views:

44

answers:

1

I have written a class which implements IModelBinder (see below). This class handles a form which has 3 inputs each representing parts of a date value (day, month, year). I have also written a corresponding HtmlHelper extension method to print out three fields on the form.

When the day, month, year inputs are given values which can be parsed, but a seperate value fails validation, all is fine - the fields are repopulated and the page served to the user as expected.

however when an invalid values are supplied and a DateTime cannot be parsed, i return an arbitrary DateTime so that the fields will be repopulated when returned to the user.

I read up on similar problems people have had and they all seemed to be due to lack of calling SetModelValue(). I wasn't doing this, but even after adding the problem has not been resolved.

public object BindModel(ControllerContext controllerContext, ModelBindingContext bindingContext)
{
   string modelName = bindingContext.ModelName;
   string monthKey = modelName + ".Month";
   string dayKey = modelName + ".Day";
   string yearKey = modelName + ".Year";

   //get values submitted on form
   string year = bindingContext.ValueProvider[yearKey].AttemptedValue;
   string month = bindingContext.ValueProvider[monthKey].AttemptedValue;
   string day = bindingContext.ValueProvider[dayKey].AttemptedValue;

   DateTime parsedDate;
   if (DateTime.TryParse(string.Format(DateFormat, year, month, day), out parsedDate))
        return parsedDate;

   //could not parse date time report error, return current date
   bindingContext.ModelState.AddModelError(yearKey, ValidationErrorMessages.DateInvalid);

   //added this after reading similar problems, does not fix!
   bindingContext.ModelState.SetModelValue(yearKey, bindingContext.ValueProvider[modelName]);
   return DateTime.Today;
}

the null reference exception is thrown when i attempt to create a textbox for the Year property of the date, but strangely not for Day or Month! Can anyone offer an explanation as to why this is?

Thanks :-)

A: 

This should fix it:

bindingContext.ModelState.AddModelError(
    yearKey, 
    ValidationErrorMessages.DateInvalid
);

bindingContext.ModelState.SetModelValue(
    yearKey, 
    bindingContext.ValueProvider[modelName]
);

Notice that the same key must be used (yearKey).

Darin Dimitrov
my mistake, think i copied and pasted while i was halfway through editing the code. i had it as you recommended before i posted the quesiton
mr.nicksta
edited snippet to reflect this..
mr.nicksta