MVC 5 - 在运行时解析DataAnnotations

时间:2014-08-05 03:45:08

标签: asp.net-mvc model-view-controller asp.net-mvc-5 data-annotations

我们需要在运行时解决dataAnnotations以了解项目和配置的性质。显然,其中一个选项(最好不使用自定义属性)是子类DataAnnotationsModelValidatorProvider并覆盖其GetValidators方法。稍后在global.axax.cs中,新类添加为ModelValidatorProviders.Providers.Add(new CustomCoolProvider());

问题:这对 MVC 5 仍然有效吗?

此实现背后的想法是替换一些设置为数据注释的格式化值,例如:[Display(Name="COOL.VALUE")]将被理解并替换为其他值:metadata.DisplayName = "Some super cool value"

这里有人为MVC的上一版本写了一个例子。 DataAnnotations dynamically attaching attributes

帮助表示赞赏。

1 个答案:

答案 0 :(得分:0)

这就是我们用来处理数据注释的内容。在您的global.asax.cs文件中。

protected void Application_Start() {
    ...
    ModelMetadataProviders.Current=new MyMetadataProvider();
    ...
}

private class MyMetadataProvider:DataAnnotationsModelMetadataProvider {
    protected override ModelMetadata CreateMetadata(IEnumerable<Attribute> attributes,Type containerType,Func<object> modelAccessor,Type modelType,string propertyName) {
        var metadata = base.CreateMetadata(attributes,containerType,modelAccessor,modelType,propertyName);

        //Automatically replace underscores with spaces and remove the "id" from the end of column names
        if(metadata.DisplayName==null&&propertyName!=null) {
            metadata.DisplayName=propertyName.Replace('_',' ');
            if(metadata.DisplayName.ToLower().EndsWith(" id"))
                metadata.DisplayName=metadata.DisplayName.Remove(metadata.DisplayName.Length-3);
        }

        //Automatically attribute multiline for anything 500 chars and above (or strings with no length defined)
        if(modelType==typeof(string)&&!(attributes.OfType<StringLengthAttribute>()?.FirstOrDefault()?.MaximumLength<500))
            metadata.DataTypeName="MultilineText";

        //Automatically attribute dates (not datetime)
        if(attributes.OfType<ColumnAttribute>()?.FirstOrDefault()?.TypeName?.ToLower()=="date") {
            metadata.DataTypeName="Date";
            metadata.EditFormatString="{0:yyyy-MM-dd}";
        }

        return metadata;
    }
}