Search code examples
c#asp.netsystem.reflection

Use reflection to get instances of static instances of derived class


Apologies if this has been answered elsewhere, but I'm not overly familiar with Reflection so I'm not sure of the exact terms I should be searching for.

Basically I'm trying to find a list of defined public static fields for classes based on a type.

So given the class LocalisationToken I have a number of classes based on this, eg, AboutToken, AdminToken, etc.

Each of these classes has public static readonly instances of these derived classes, eg,:

public static readonly LocalisationToken TermsAndConditions = new AboutToken("Terms And Conditions", Guid.Parse("595FB313-4940-489b-9CC8-4B9BF0B62E8B"));
public static readonly LocalisationToken OkGotIt = new AboutToken("OK, got it", Guid.Parse("5F5F22A4-C45C-43f0-A2A4-304740E0EE12"));

What I would like to do is find all instances in a compiled library at run time. The underlying code when instantiating an AboutToken, say, is to create a new LocalisationToken using the constructor properties. My requirement is to get the Guid and default text back, eg, "Terms and Conditions" and 595FB313-4940-489b-9CC8-4B9BF0B62E8B

If I use GetTypes() on the assembly containing LocalisationToken, I just get the various derived classes of AboutToken, AdminToken, etc. I need the actual instances instead.

As it happens, I don't need the derived classes at all. But would I need to iterate through those, even if all instances are marked as "LocalisationTokens"?


Solution

  • It's important to understand that it's the field which is static - not the instance.

    You can easily find readonly static fields though, and fetch their values. For example:

    var someAssembly = typeof(Foo).Assembly; // Or whatever
    var values = from type in someAssembly.GetTypes()
                 from field in type.GetFields(BindingFlags.Static |
                                              BindingFlags.Public |
                                              BindingFlags.NonPublic)
                 where field.IsInitOnly &&
                       field.FieldType == typeof(LocalisationToken)
                 select (LocalisationToken) field.GetValue(null);