programming4us
programming4us
ENTERPRISE

Microsoft Enterprise Library : Banishing Validation Complication - How Do I Use The Validation Block?

- How To Install Windows Server 2012 On VirtualBox
- How To Bypass Torrent Connection Blocking By Your ISP
- How To Install Actual Facebook App On Kindle Fire
11/15/2013 6:51:14 PM

In this section, we cover three topics that you should be familiar with when you start to use the block in your applications: preparing your application to use the block, choosing a suitable approach for validation, the options available for creating validators, accessing and displaying validation errors, and understanding how you can use template tokens in validation messages.

Preparing Your Application

To use the Validation block, you must reference the required assemblies. In addition to the assemblies required in every application that uses Enterprise LibraryYou require the main Validation block assembly, Microsoft.Practices.EnterpriseLibrary.Validation.dll. If you intend to use the integration features for ASP.NET, Windows Forms, WPF, or WCF, you must also reference the relevant assembly that contains these features.

Then you can edit your code to specify the namespaces used by the Validation block and, optionally, the integration features if you need to integrate with WCF or a UI technology.

Note

If you are using WCF integration, you should add a reference to the System.Service Model namespace.

Choosing a Validation Approach

Before you start to use the Validation block, you should consider how you want to perform validation. As you've seen, there are several approaches you can follow. Table 1 summarizes these, and will help you to choose one, or a combination, most suited to your requirements.

Table 1. Validation approaches

Validation approach

Advantages

Considerations

Rule sets in configuration

Supports the full capabilities of the Validation block validators.

Validation rules can be changed without requiring recompilation and redeployment.

Validation rules are more visible and easier to manage.

Rules are visible in configuration files unless the content is encrypted.

May be open to unauthorized alteration if not properly protected.

Type definitions and validation rule definitions are stored in different files and accessed using different tools, which can be confusing.

Validation block attributes

Supports the full capabilities of the Validation block validators.

Validation attributes may be defined in separate metadata classes.

Rules can be extracted from the metadata for a type by using reflection.

Requires modification of the source code of the types to validate.

Some complex rule combinations may not be possible—only a single And or Or combination is available for multiple rules.

Hides validation rules from administrators and operators.

Data annotation attributes

Allows you to apply validation rules defined by .NET data annotation attributes, which may be defined in separate metadata classes.

Typically used with technologies such as LINQ, for which supporting tools might be used to generate code.

Technologies such as ASP.NET Dynamic Data that use these attributes can perform partial client-side validation.

Rules can be extracted from the metadata for a type by using reflection.

Requires modification of the source code.

Does not support all of the powerful validation capabilities of the Validation block.

Self-validation

Allows you to create custom validation rules that may combine values of different members of the class.

Requires modification of the source code.

Hides validation rules from administrators and operators.

Rules cannot be extracted from the metadata for a type by using reflection.

Validators created programmatically

A simple way to validate individual values as well as entire objects.

Useful if you only need to perform small and specific validation tasks, especially on value types held in variables.

Requires additional code and is generally more difficult to manage for complex validation scenarios.

Hides validation rules from administrators and operators.

More difficult to administer and manage.

If you decide to use attributes to define your validation rules within classes but are finding it difficult to choose between using the Validation block attributes and the Microsoft .NET data annotation attributes, you should consider using the Validation block attributes approach as this provides more powerful capabilities and supports a far wider range of validation operations. However, you should consider the data annotations approach in the following scenarios:

  • When you are working with existing applications that already use data annotations.

  • When you require validation to take place on the client.

  • When you are building a Web application where you will use the ASP.NET Data Annotation Model Binder, or you are using ASP.NET Dynamic Data to create data-driven user interfaces.

  • When you are using a framework such as the Microsoft Entity Framework, or another object/relational mapping (O/RM) technology that auto-generates classes that include data annotations.

Options for Creating Validators Programmatically

There are several ways that you can create the validators you require, whether you are creating a type validator that will validate an instance of your class using a rule set or attributes, or you are creating individual value validators:

  • Use the ValidatorFactory facade to create validators. This approach makes it easy to create type validators that you can use, in conjunction with rule sets, to validate multiple members of an object instance. This is generally the recommended approach. You also use this approach to create validators that use only validation attributes or data annotations within the classes you want to validate, or only rule sets defined in configuration. You can resolve an instance of the ValidatorFactory using a single line of code.

  • Create individual validators programmatically by calling their constructor. The constructor parameters allow you to specify most of the properties you require for the validator. You can then set additional properties, such as the Tag or the resource name and type if you want to use a resource file to provide the message template. You can also build combinations of validators using this approach to implement complex validation rules.

  • Resolve individual validators through the Enterprise Library Container. This approach allows you to obtain a validator instance using dependency injection; for example, by simply specifying the type of validator you require in the constructor of a class that you resolve through the container. If you specify a name when you resolve the instance, this is interpreted as the name of the rule set for that validator to use when validating objects.

Note

Previous versions of Enterprise Library used static facades named Validation and ValidationFactory (as opposed to ValidatorFactory described above) to create validators and perform validation. While these facades are still available for backwards compatibility, you should use the approaches described above for creating validators as you write new code.

Performing Validation and Displaying Validation Errors

To initiate validation, you call the Validate method of your validator. There are two overloads of this method: one that creates and returns a populated ValidationResults instance, and one that accepts an existing ValidationResults instance as a parameter. The second overload allows you to perform several validation operations, and collect all of the errors in one ValidationResults instance.

You can check if validation succeeded, or if any validation errors were detected, by examining the IsValid property of a ValidationResults instance, and displaying details of any validation errors that occurred. The following code shows a simple example of how you can display the most relevant details of each validation error.

// Check if the ValidationResults detected any validation errors.
if (results.IsValid)
{
Console.WriteLine("There were no validation errors.");
}
else
{
Console.WriteLine("The following {0} validation errors were detected:",
results.Count);
// Iterate through the collection of validation results.
foreach (ValidationResult item in results)
{
// Show the target member name and current value.
Console.WriteLine("Target:'{0}' Key:'{1}' Tag:'{2}' Message:'{3}'",
item.Target, item.Key, item.Tag, item.Message);
}
}

Alternatively, you can extract more information about the validation result for each individual validator where an error occurred. The example application we provide demonstrates how you can do this.

Understanding Message Template Tokens

One specific and very useful feature of the individual validators you define in your configuration or attributes is the capability to include tokens in the message to automatically insert values of the validator's properties. This applies no matter how you create your validator—in rule sets defined in configuration, as validation attributes, or when you create validators programmatically.

The Message property of a validator is actually a template, not just a simple text string that is displayable. When the block adds an individual ValidationResult to the ValidationResults instance for each validation error it detects, it parses the value of the Message property looking for tokens that it will replace with the value of specific properties of the validator that detected the error.

The value injected into the placeholder tokens, and the number of tokens used, depends on the type of validator—although there are three tokens that are common to all validators. The token {0} will be replaced by the value of the object being validated (ensure that you escape this value before you display or use it in order to guard against injection attacks). The token {1} will contain the name of the member that was being validated, if available, and is equivalent to the Key property of the validator. The token {2) will contain the value of the Tag property of the validator.

The remaining tokens depend the on the individual validator type. For example, in the case of the Contains Characters validator, the tokens {3} and {4} will contain the characters to check for and the ContainsCharacters value (All or Any). In the case of a range validator, such as the String Length validator, the tokens {3} to {6} will contain the values and bound types (Inclusive, Exclusive, or Ignore) for the lower and upper bounds you specify for the validator. For example, you may define a String Length validator like this:

[StringLengthValidator(5, RangeBoundaryType.Inclusive, 20,
RangeBoundaryType.Inclusive,
MessageTemplate = "{1} must be between {3} and {5} characters.")]

If this validator is attached to a property named Description, and the value of this property is invalid, the ValidationResults instance will contain the error message Description must be between 5 and 20 characters.

Other validators use tokens that are appropriate for the type of validation they perform. The documentation installed with Enterprise Library lists the tokens for each of the Validation block validators. You will also see the range of tokens used in the examples that follow.

Other  
  •  Microsoft Enterprise Library : Banishing Validation Complication - What Does the Validation Block Do? (part 2)
  •  Microsoft Enterprise Library : Banishing Validation Complication - What Does the Validation Block Do? (part 1)
  •  Microsoft Enterprise Library : A Cache Advance for Your Applications - How Do I Use the Caching Block (part 4) - Refreshing the Cache, Loading the Cache
  •  Microsoft Enterprise Library : A Cache Advance for Your Applications - How Do I Use the Caching Block (part 3) - Removing Items from and Flushing the Cache
  •  Microsoft Enterprise Library : A Cache Advance for Your Applications - How Do I Use the Caching Block (part 2)
  •  Microsoft Enterprise Library : A Cache Advance for Your Applications - How Do I Use the Caching Block (part 1) - Adding Items to and Retrieving Items from the Cache
  •  Microsoft Enterprise Library : A Cache Advance for Your Applications - How Do I Configure the Caching Block?
  •  Microsoft Visual Studio 2010 : Data Parallelism - Unrolling Sequential Loops into Parallel Tasks (part 4) - Handling Exceptions
  •  Microsoft Visual Studio 2010 : Data Parallelism - Unrolling Sequential Loops into Parallel Tasks (part 3) - Interrupting a Loop
  •  Microsoft Visual Studio 2010 : Data Parallelism - Unrolling Sequential Loops into Parallel Tasks (part 2) - The Parallel For Loop
  •  
    Top 10
    - Microsoft Visio 2013 : Adding Structure to Your Diagrams - Finding containers and lists in Visio (part 2) - Wireframes,Legends
    - Microsoft Visio 2013 : Adding Structure to Your Diagrams - Finding containers and lists in Visio (part 1) - Swimlanes
    - Microsoft Visio 2013 : Adding Structure to Your Diagrams - Formatting and sizing lists
    - Microsoft Visio 2013 : Adding Structure to Your Diagrams - Adding shapes to lists
    - Microsoft Visio 2013 : Adding Structure to Your Diagrams - Sizing containers
    - Microsoft Access 2010 : Control Properties and Why to Use Them (part 3) - The Other Properties of a Control
    - Microsoft Access 2010 : Control Properties and Why to Use Them (part 2) - The Data Properties of a Control
    - Microsoft Access 2010 : Control Properties and Why to Use Them (part 1) - The Format Properties of a Control
    - Microsoft Access 2010 : Form Properties and Why Should You Use Them - Working with the Properties Window
    - Microsoft Visio 2013 : Using the Organization Chart Wizard with new data
    REVIEW
    - First look: Apple Watch

    - 3 Tips for Maintaining Your Cell Phone Battery (part 1)

    - 3 Tips for Maintaining Your Cell Phone Battery (part 2)
    programming4us programming4us
    programming4us
     
     
    programming4us