2011-10-28 53 views
5

我已经使用需要来自模型属性的属性值的方法扩展了HTML助手。所以我定义了一个自定义属性。无法在MVC3 HTML Helper中获取自定义属性值

public class ChangeLogFieldAttribute : Attribute { 
     public string FieldName { get; set; } 
    } 

它在我的模型中使用就像这样。

[Display(Name = "Style")] 
    [ChangeLogField(FieldName = "styleid")] 
    public string Style { get; set; } 

在帮助我的方法,我有下面的代码让我的属性的字段名的值,如果使用该属性的属性。

 var itemName = ((MemberExpression)ex.Body).Member.Name; 

     var containerType = html.ViewData.ModelMetadata.ContainerType; 
     var attribute = ((ChangeLogFieldAttribute[])containerType.GetProperty(html.ViewData.ModelMetadata.PropertyName).GetCustomAttributes(typeof(ChangeLogFieldAttribute), false)).FirstOrDefault(); 
     if (attribute != null) { 
      itemName = attribute.FieldName; 
     } 

但是,当我到达此代码时,我得到一个异常,因为containerType为null。

我不知道我是否正在做任何这个正确的,但我从大约4个不同的来源拉到这一点。如果你能提出解决我的问题或替代方案,我会很感激。

谢谢。

用解决

我用了Darin季米特洛夫的解决方案,虽然我不得不调整它的一些更新。这是我添加的内容。我必须检查属性metatdata的存在,并且一切都很好。

 var fieldName = ((MemberExpression)ex.Body).Member.Name; 

     var metadata = ModelMetadata.FromLambdaExpression(ex, html.ViewData); 
     if (metadata.AdditionalValues.ContainsKey("fieldName")) { 
      fieldName = (string)metadata.AdditionalValues["fieldName"]; 
     } 
+0

为了得到一个属性名称,你可以用'metadata.PropertyName'代替'((MemberExpression)ex.Body).Member.Name'。但是,这对字段名称不起作用,而且我没有看到任何'.FieldName'或'.MemberName'。 –

回答

11

你可以把属性的元数据感知:

public class ChangeLogFieldAttribute : Attribute, IMetadataAware 
{ 
    public string FieldName { get; set; } 

    public void OnMetadataCreated(ModelMetadata metadata) 
    { 
     metadata.AdditionalValues["fieldName"] = FieldName; 
    } 
} 

,然后助手里面:

var metadata = ModelMetadata.FromLambdaExpression(ex, htmlHelper.ViewData); 
var fieldName = metadata.AdditionalValues["fieldName"];