Kasum
Kasum

Reputation: 41

Attribute values do not reflect changes made at runtime

I have a problem and can't wrap my mind around it: I made a mathode which should set propertie values of an specific attribute "MappingAttribute" and return the new object.

The problem: The attribute values are always set to the default value "false". Where am I wrong?

    static public T MapToClass<T>(SqlDataReader reader) where T : class
    {
        T returnedObject = Activator.CreateInstance<T>();
        PropertyInfo[] modelProperties = returnedObject.GetType().GetProperties();
        for (int i = 0; i < modelProperties.Length; i++)
        {
            MappingAttribute[] attributes = modelProperties[i].GetCustomAttributes<MappingAttribute>(true).ToArray();


            if (attributes.Length > 0) {
                attributes[0].AutoIncrement = true;
                attributes[0].Primekey = true;
            }
        }
        return returnedObject;
    }

Upvotes: 2

Views: 178

Answers (1)

Marc Gravell
Marc Gravell

Reputation: 1062650

Attributes are not stored anywhere except in the assembly metadata. They are only materialized into attribute instances when asked to do so by reflection - in your case via GetCustomAttributes<MappingAttribute>. But: you then discard these. The next time GetCustomAttributes<MappingAttribute> is called, fresh new instances will be handed out, with the values from the assembly metadata.

Basically: updating properties of attribute instances does not mean that other code will see those changes when that code asks about attribute metadata.

To illustrate this:

using System;
class FooAttribute : Attribute { public string Value { get; set; } }

[Foo(Value = "abc")]
class Bar
{
    static void Main()
    {
        var attrib = (FooAttribute)typeof(Bar)
            .GetCustomAttributes(typeof(FooAttribute), false)[0];
        Console.WriteLine(attrib.Value); // "abc"
        attrib.Value = "def";
        Console.WriteLine(attrib.Value); // "def"

        // now re-fetch
        attrib = (FooAttribute)typeof(Bar)
            .GetCustomAttributes(typeof(FooAttribute), false)[0];
        Console.WriteLine(attrib.Value); // "abc"
    }
}

Upvotes: 2

Related Questions