I want to check custom attributes on my class members (fields only) by using an extension method.
public class DatabaseIdAttribute : Attribute
{
public int ID { get; set; }
public DatabaseIdAttribute(int id)
{
this.ID = id;
}
}
public class MyClass
{
[DatabaseId(1)]
double Height {get;set;}
[DatabaseId(2)]
double Width {get;set;}
double Area { get { return this.Height * this.Width; }
}
I want to use LINQ expression in the extension method to access the class field instead of passing magic strings.
var myClass = new MyClass();
var attribute = myClass.GetAttribute<DatabaseIdAttribute>(c => c.Height);
Is it possible to achieve?
[EDIT]
For the time being, I have achieved the following with the help of @leppie
public static MemberInfo GetMember<T, R>(this T instance, Expression<Func<T, R>> selector)
{
var member = selector.Body as MemberExpression;
if (member != null)
{
return member.Member;
}
return null;
}
public static T GetAttribute<T>(this MemberInfo member) where T : Attribute
{
return member.GetCustomAttributes(false).OfType<T>().SingleOrDefault();
}
which enables to get the attribute in the following way
var c = new MyClass();
var attribute = c.GetMember(m => m.Height).GetAttribute<DatabaseIdAttribute>();
but I want to be able to access it in the following way
var c = new MyClass();
var attribute = c.GetAttribute<DatabaseIdAttribute>(m => m.Height);
You are almost there! This should work (untested).
public static class ObjectExtensions
{
public static MemberInfo GetMember<T,R>(this T instance,
Expression<Func<T, R>> selector)
{
var member = selector.Body as MemberExpression;
if (member != null)
{
return member.Member;
}
return null;
}
// unnecessary in .NET 4.5 and up, see note!
public static T GetAttribute<T>(this MemberInfo meminfo) where T : Attribute
{
return meminfo.GetCustomAttributes(typeof(T)).FirstOrDefault() as T;
}
}
Usage:
var attr = someobject.GetMember(x => x.Height).
GetAttribute<DatabaseIdAttribute>();
Note: As of .NET 4.5 and up (including .NET Core), the BCL provides a GetCustomAttribute<T>(MemberInfo)
extension method that functions identically to the GetAttribute
method defined above, and should be used instead if available.