2011-08-12 62 views
3

有沒有辦法在服務器端代碼中獲取註釋的值?例如,我有:獲取mvc3服務器端代碼的顯示註釋值

public class Dummy 
{ 
    [Display(Name = "Foo")] 
    public string foo { get; set; } 

    [Display(Name = "Bar")] 
    public string bar { get; set; } 
} 

我希望能夠得到與出張貼回到頁面服務器端的價值「富」,但像類的屬性,或某事這種排序。像一個@ Html.LabelFor(model => model.Foo)但在c#服務器代碼。

這可能嗎?

謝謝。

+1

你用C#服務器代碼是什麼意思? – sll

+0

@ Html.LabelFor(model => model.Foo)< - 不會輸出「Foo」?也許你需要改用DisplayNameAttribute。 –

+0

@sllev對不起,我的意思是後面的代碼。在控制器中的操作。 – AJC

回答

5

像這樣的事情?

string displayName = GetDisplayName((Dummy x) => x.foo); 

// ... 

public static string GetDisplayName<T, U>(Expression<Func<T, U>> exp) 
{ 
    var me = exp.Body as MemberExpression; 
    if (me == null) 
     throw new ArgumentException("Must be a MemberExpression.", "exp"); 

    var attr = me.Member 
       .GetCustomAttributes(typeof(DisplayAttribute), false) 
       .Cast<DisplayAttribute>() 
       .SingleOrDefault(); 

    return (attr != null) ? attr.Name : me.Member.Name; 
} 

或者,如果你希望能夠調用該方法針對一個實例,並採取類型推斷的優勢:

var dummy = new Dummy(); 
string displayName = dummy.GetDisplayName(x => x.foo); 

// ... 

public static string GetDisplayName<T, U>(this T src, Expression<Func<T, U>> exp) 
{ 
    var me = exp.Body as MemberExpression; 
    if (me == null) 
     throw new ArgumentException("Must be a MemberExpression.", "exp"); 

    var attr = me.Member 
       .GetCustomAttributes(typeof(DisplayAttribute), false) 
       .Cast<DisplayAttribute>() 
       .SingleOrDefault(); 

    return (attr != null) ? attr.Name : me.Member.Name; 
} 
+0

+1,非常簡潔。如何在不將其轉換爲'Displayattribute'的情況下訪問'attr.Name'? 'GetCustomAttributes(type,inherit)'返回'Object []'。 – Chev

+0

第一個很好用,但後一個選項'GetDisplayName'不會作爲'dummy'實例的擴展名出現。 – Chev

+0

@Alex:我在投射它:'var attr =(DisplayAttribute)me.Member ...'。 (或者說,我是在投射它;我剛剛編輯了使用Cast ()'方法的答案,而不是顯式投射) – LukeH

3

您將需要使用反射。這是一個示例控制檯程序,可以實現您想要的功能。

class Program 
{ 
    static void Main(string[] args) 
    { 
     Dummy dummy = new Dummy(); 
     PropertyInfo[] properties = dummy.GetType().GetProperties(); 
     foreach (PropertyInfo property in properties) 
     { 
      IEnumerable<DisplayAttribute> displayAttributes = property.GetCustomAttributes(typeof(DisplayAttribute), false).Cast<DisplayAttribute>(); 
      foreach (DisplayAttribute displayAttribute in displayAttributes) 
      { 
       Console.WriteLine("Property {0} has display name {1}", property.Name, displayAttribute.Name); 
      } 
     } 
     Console.ReadLine(); 
    } 
} 

public class Dummy 
{ 
    [Display(Name = "Foo")] 
    public string foo { get; set; } 

    [Display(Name = "Bar")] 
    public string bar { get; set; } 
} 

這將產生以下結果:

http://www.codetunnel.com/content/images/reflectresult.jpg

+0

我更新了答案,以便在成員擁有多個顯示屬性的情況下遍歷所有DisplayAttribute。 – Chev

+0

成員不應該有多個成員,因爲'DisplayAttribute'註釋了'AllowMultiple = false'。 – LukeH

+0

@LukeH這很好,但我不喜歡用我的代碼進行假設;) – Chev