在RangeAttribute中提供非常量值?

时间:2011-02-03 18:44:45

标签: c# asp.net-mvc data-annotations

当我执行以下操作时:

`[Range(1910, DateTime.Now.Year)]  
public int Year { get; set; }`

我收到以下错误:

An attribute argument must be a constant expression, typeof expression or array creation expression of an attribute parameter type

任何想法为什么?

3 个答案:

答案 0 :(得分:6)

您可以为此构建一个自定义属性,例如RangeYearToCurrent,您可以在其中指定当前年份

public class RangeYearToCurrent : RangeAttribute
{
    public RangYearToCurrent(int from)
        : base(typeof(int), from, DateTime.Today.Year) { }
}

未经测试...

答案 1 :(得分:4)

这是我的版本,基于之前的答案(但同时在客户端/服务器端工作):

 [AttributeUsage(AttributeTargets.Property | AttributeTargets.Field | AttributeTargets.Parameter, AllowMultiple = false)]
public class RangeYearToCurrent : RangeAttribute,IClientValidatable { 
    public RangeYearToCurrent(int from) : base(from, DateTime.Today.Year) { }

    #region IClientValidatable Members

    public IEnumerable<ModelClientValidationRule> GetClientValidationRules(ModelMetadata metadata, ControllerContext context)
    {
        var rules = new ModelClientValidationRangeRule(this.ErrorMessage, this.Minimum, this.Maximum);
        yield return rules;
    }

    #endregion
}

用法例:

[RangeYearToCurrent(1995, ErrorMessage = "Invalid Date")]
public int? Year { get; set; }

答案 2 :(得分:2)

您不能使用属性执行此操作。

属性总是直接编译,并且用作元数据,而不是“可执行代码”。因此,必须始终在编译时完全知道属性中的参数 - 即:常量值。

尝试使用需要运行时表达式的值将在属性中失败。这在所有属性中都是如此,而不仅仅是RangeAttribute。