INotifyDataErrorInfo and binding exceptions

I'm using the INotifyDataErrorInfo interface to implement a general MVVM validation mechanism. I'm implementing the interface by calling OnValidate instead of OnPropertyChanged:

public void OnValidate(dynamic value, [CallerMemberName] string propertyName = null)
{
        if (PropertyChanged != null)
                PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
        Validate(propertyName, value);
}

In the Validate Method I'm generating the validation errors, add them to a Dictionary and raise the ErrorsChanged event if a validation error was found or cleared:

if (entry.Validate(strValue, out errorNumber, out errorString) == false)
{
      _validationErrors[propertyName] = new List<string> {errorString};
      RaiseErrorsChanged(propertyName);
}
else if (_validationErrors.ContainsKey(propertyName))
{
      _validationErrors.Remove(propertyName);
      RaiseErrorsChanged(propertyName);
}

The HasErrors property is implemented by looking at the errors dictionary:

    public bool HasErrors
    {
         get { return _validationErrors.Any(kv => kv.Value != null 
                   && kv.Value.Count > 0); }
    }

To prevent the save button from being enabled when there is a validation error - The save command canExecuteMethod looks at the HasErrors property:

private bool IsSaveEnabled()
{
    return HasErrors == false;
}

Everything works fine except the case where I'm having binding errors - if the binded value is (for example) an integer a non integer is entered - the textbox's ErrorContent is updated with an error string: "Value 'something' could not be converted". But the INotifyDataErrorInfo mechanism is not updated about this. The HasErrors remains false and Save is enabled although there is an error in the view. I would like to find a way to propagate the binding exception to the INotifyDataErrorInfo mechanism so I would be able to:

  1. Disable the Save button (must).
  2. Change the validation error message to a more meaningful error string (nice to have).

I would like to find a general MVVM solution without adding code behind in the view.

Thank you for the help

Answers


the string int case doesn't work with MVVM because your viewmodel doesn't get any information because of the binding exception.

I see two ways to get the validation you want:

  1. Just use string properties in your viewmodel and when you have to go to your model just convert the string to your model type.
  2. Create behaviors or "special" controls so the the input in your view is always "convertible" to your viewmodel type.

Btw I use the second approach because I have to :) but the first will always work and seems easier to me.


Need Your Help

Do WCF 3.5 REST endpoints call associated methods asynchronously?

c# .net wcf rest asynchronous-wcf-call

When a WCF 3.5 REST endpoint (via WebServiceHost) handles a URI request, does it invoke the associated procedure asynchronously?

About UNIX Resources Network

Original, collect and organize Developers related documents, information and materials, contains jQuery, Html, CSS, MySQL, .NET, ASP.NET, SQL, objective-c, iPhone, Ruby on Rails, C, SQL Server, Ruby, Arrays, Regex, ASP.NET MVC, WPF, XML, Ajax, DataBase, and so on.