Dmitry Shechtman's Blog

December 19, 2009

IDataErrorInfo with Validation Application Block and Unity Interception AOP

Filed under: PropertyChange — Tags: , , , , , , , , , , , , — Dmitry Shechtman @ 12:40

This is the second article in a planned series of articles concerning AOP with Unity Interception and Policy Injection:

  1. INotifyPropertyChanged AOP
  2. IDataErrorInfo AOP
  3. Policy Injection
  4. Performance and optimizations
  5. The final solution

I hope you will find this useful in your work; all feedback will be greatly appreciated.

The previous article discussed an implementation of the INotifyPropertyChanged aspect using Unity Interception AOP. Today we will see how a similar approach can be applied to another interface commonly used by WPF (as well as by ASP.NET MVC).

The IDataErrorInfo interface consists of two methods:

  1. an indexer accepting a property name (columnName) parameter and
  2. an Error property.

We will solely focus on the indexer, which returns error messages on a per-property basis.

The Validation Application Block allows developers to easily incorporate input validation via property attributes and/or application configuration, supporting a variety of provided validators, as well as custom ones.

IDataErrorInfo and VAB seem to be a perfect match, and have indeed been integrated. Adding Unity Interception will further simplify input validation, so that (presentation) models could be specified in the following manner:

[NotifyPropertyChanged, DataErrorInfo]
public class Contact : MarshalByRefObject, INotifyPropertyChanged, IDataErrorInfo
{
    [StringLengthValidator(1, 20, MessageTemplate = "First name length must be between {3} and {5}.")]
    [ContainsCharactersValidator("0123456789", Negated = true, MessageTemplate = "First name cannot contain digits")]
    public string FirstName { get; set; }

    [StringLengthValidator(1, 20, MessageTemplate = "Last name length must be between {3} and {5}.")]
    [ContainsCharactersValidator("0123456789", Negated = true, MessageTemplate = "Last name cannot contain digits.")]
    public string LastName { get; set; }

    public event PropertyChangedEventHandler PropertyChanged = delegate { };

    public string Error
    {
        get { return null; }
    }

    public string this[string columnName]
    {
        get { return null; }
    }
}

Note: The implementation presented below is limited to classes derived (possibly indirectly) from MarshalByRefObject.

(more…)

Advertisements

Create a free website or blog at WordPress.com.