C# 验证方法参数上的DataAnnotation

C# 验证方法参数上的DataAnnotation,c#,data-annotations,C#,Data Annotations,数据注释属性如何与方法参数一起使用?我希望这样做,但是没有抛出异常 private string TestValidate([StringLength(5)] string name = "Default: throw exception") { ValidationContext context = new ValidationContext(name); Validator.ValidateObject(name, context); return name; }

数据注释属性如何与方法参数一起使用?我希望这样做,但是没有抛出异常

private string TestValidate([StringLength(5)] string name = "Default: throw exception")
{
    ValidationContext context = new ValidationContext(name);
    Validator.ValidateObject(name, context);
    return name;
}
或者,我知道这会奏效。但是,这并没有使用属性约定的便利性

private string TestValidate(string name = "Default: throw exception")
{
    ValidationContext context = new ValidationContext(name);
    Validator.ValidateValue(name, context, new[] { new StringLengthAttribute(5) });
        return name;
}

如果您想为代码添加工具,那么您应该使用一些反射(请参阅)

您可以在类初始化时对反射进行一次评估,但反射代码的工作方式如下:

// NOTE: nameof() is a .NET 4.6 feature.  If you are using an older
// version of .NET, you'll have to write the string yourself.
MethodInfo method = GetType().GetMethod(nameof(TestValidate), typeof(string));
// NOTE: it's on you to validate this and use the version with binding flags for
// special cases like non-public and static methods

ParameterInfo parameter = method.GetParameters().First();
// This is shorthand: GetCustomAttributes returns object[], you'll have
// convert that properly and reference your customAttributes later
ValidationAttribute[] customAttributes = parameter.GetCustomAttributes(
        typeof(ValidationAttribute), true); // second parameter ignored

// At this point you can handle the rest of your validation
ValidationContext context = new ValidationContext(name);
Validator.ValidateValue(name, context, customAttributes);
    return name;
许多验证框架只是封装了获取验证属性所需的所有反射。注意:在本例中,我使用了
ValidationAttribute
的子类,而不是更具体的
StringLengthAttribute
。调用
GetCustomAttributes()
将返回扩展我们请求的基类的任何属性。这允许您完全更改方法上的属性并添加更多约束,而无需更改代码。如果计算多个参数或删除一个参数,则必须进行一些更改

您可以让它更通用一些,因为从您拥有特定的
MethodInfo
对象开始,代码通常是相同的。在这种情况下,我可能会做一些改变:

public static void Validate(MethodInfo method, params object[] values)
{
    ValidationContext context = new ValidationContext(method.Name);
    ParameterInfo[] parameters = method.GetParameters();

    for(int i = 0; i < Math.Min(parameters.Length, values.Length); i++)
    {
        // This is shorthand: GetCustomAttributes returns object[], you'll have
        // convert that properly and reference your customAttributes later
        ValidationAttribute[] customAttributes = parameter[i].GetCustomAttributes(
                typeof(ValidationAttribute), true); // second parameter ignored

        Validator.ValidateValue(values[i], context, customAttributes);
    }
}
publicstaticvoidvalidate(MethodInfo方法,params对象[]值)
{
ValidationContext=新的ValidationContext(method.Name);
ParameterInfo[]parameters=method.GetParameters();
对于(int i=0;i
Wow。真的那么难吗?如果Microsoft自己不提供验证,为什么要在
StringLengthAttribute
attributesage
定义中包含
AttributeTargets.Parameter