Using attribute of inherited property from an interface

314 views Asked by At

I've been trying to use an attribute of a property that has been declared in an interface.

Assume:

[AttributeUsage(AttributeTargets.Property, Inherited=true)]
class My1Attribute : Attribute
{
    public int x { get; set; }
}

interface ITest
{
    [My1]
    int y { get; set; }
}

class Child : ITest
{
    public Child() { }

    public int y { get; set; }
}

Now, from what I read, GetCustomAttribute() with inheritance=true should return the inherited attribute, but it looks it doesn't work.

Attribute my = typeof(Child).GetProperty("y").GetCustomAttribute(typeof(My1Attribute), true); // my == null

Why doesn't it work? and how can I get the attribute?

2

There are 2 answers

0
Dan Wilson On BEST ANSWER

Child does not have any custom attributes, ITest has them, so you will have to call GetCustomAttributes on the members of ITest.

There is a difference between inheritance and implementation. Inheritance would be fine if Child was derived from some base class that had a y property decorated with My1Attribute.

In your case, Child implements ITest and ITest is a different type, outside of the inheritance hierarchy.

void Main()
{
    var my1Attribute = typeof(ITest).GetProperty("y").GetCustomAttribute(typeof(My1Attribute)) as My1Attribute;
    Console.WriteLine(my1Attribute.x); // Outputs: 0
}

[AttributeUsage(AttributeTargets.Property, Inherited = true)]
class My1Attribute : Attribute
{
    public int x { get; set; }
}

interface ITest
{
    [My1]
    int y { get; set; }
}

class Child : ITest
{
    public Child() { }

    public int y { get; set; }
}
0
Jeppe Stig Nielsen On

This is just a sketch, not a detailed answer. It should give an idea of how you could find the attribute, starting from Child.

You can use typeof(Child).GetInterfaces() to get an array from which you can see that Child implements ITest. Suppose t is the typeof(ITest) you got out of the array, then:

typeof(Child).GetInterfaceMap(t)

will give you a structure ("map") to see what the property getter (get accessor) get_y from Child (in .TargetMethods) corresponds to in the interface (.InterfaceMethods). The answer is another get_y of course. So what you have is the MethodInfo of the get accessor of the y property in ITest. To find the property itself, see e.g. this answer to Finding the hosting PropertyInfo from the MethodInfo of getter/setter. Once you have the property info, inspect its custom attributes to find the My1Attribute and its value of x.