ASP.NET MVC以ModelValidator为核心的Model验证体系:ModelValidatorProviders2012-09-21 cnblogs Artech前面篇文章我们分别介绍用真正用于实施Model验证的ModelValidator(《ASP.NET MVC以ModelValidator为核心的Model验证体系: ModelValidator》),以及用于提供ModelValidator的ModelValidatorProvider(《ASP.NET MVC以ModelValidator为核心的Model验证体系: ModelValidatorProvider》),那么对于ASP.NET MVC的Model验证体系来说,最终是通过怎样的方式对ModelValidatorProvider进行注册,又是如何利用它们来创建相应的ModelValidator来实施Model验证的呢?这就是本篇文章论述的重点。一、ModelValidatorProviders我们通过静态类型ModelValidatorProviders对ModelValidatorProvider进行注册。如下面的代码片断所示,ModelValidatorProviders具有一个静态只读属性Providers,其类型为ModelValidatorProviderCollection,表示注册的基于整个Web应用范围的ModelValidatorProvider列表。
 1: public static class ModelValidatorProviders
 2: {
 3: public static ModelValidatorProviderCollection Providers { get; }
 4: }
 5:
 6: public class ModelValidatorProviderCollection : Collection<ModelValidatorProvider>
 7: {
 8: public ModelValidatorProviderCollection();
 9: public ModelValidatorProviderCollection(IList<ModelValidatorProvider> list);
10: public IEnumerable<ModelValidator> GetValidators(ModelMetadata metadata, ControllerContext context);
11: }
值得一提的是,ModelValidatorProviderCollection定义了一个GetValidators方法用于返回一个通过集合中每个ModelValidatorProvider创建的ModelValidator集合。在这个方法中,指定的Model元数据和Controller上下文会被传入每个ModelValidatorProvider对象的GetValidators方法,得到的每个ModelValidator对象将会作为最终返回的ModelValidator集合的元素。在默认的情况下,通过ModelValidatorProviders的Providers表示注册的ModelValidatorProvider列表会包含三个对象,对应着我们前面介绍的三种ModelValidatorProvider类型,即DataAnnotationsModelValidatorProvider、ClientDataTypeModelValidatorProvider和DataErrorInfoPropertyModelValidator。如果我们需要添加一个自定义ModelValidatorProvider,可以直接将相应的对象添加到ModelValidatorProviders的Providers列表中。如果需要采用自定义ModelValidatorProvider来替换掉现有的ModelValidatorProvider,比如我们创建了一个扩展的DataAnnotationsModelValidatorProvider,还需要将现有的ModelValidatorProvider从该列表中移除。实现在ModelValidatorProvider中的ModelValidator提供机制是基于Model元数据和Controller上下文的,实际上用于描述Model元数据的ModelMetadata类型同样定义了一个GetValidators方法用于根据指定的Controller上下文的所有ModelValidator对象。如下面的代码片断所示,该方法直接调用了通过ModelValidatorProviders的Providers属性表述的ModelValidatorProviderCollection对象的同名方法。
 1: public abstract class ModelValidator
 2: {
 3: //其他成员
 4: public virtual IEnumerable<ModelValidator> GetValidators(ControllerContext context)
 5: {
 6: return ModelValidatorProviders.Providers.GetValidators(this, context);
 7: }
 8: }
二、ModelValidator、ModelValidatorProvider和ModelValidatorProviders上面我们介绍用于进行Model验证的ModelValidator,用于提供ModelValidator的ModelValidatorProvider,以及用于注册ModelValidatorProvider的ModelValidatorProviders,整个ModelValidator的提供机制以此三类组件为核心,下图所示的UML体现了它们之间的关系。
