views:

37

answers:

2

I have a app that requires a dll to be loaded at runtime and I want to create some Custom Attributes in the dynamically loaded DLL so when it is loaded I can check to make sure that certain attributes have certain values before trying to use it.

I create an attribute like this

using System;
[AttributeUsage(AttributeTargets.Class)]
public class ValidReleaseToApp : Attribute
{
    private string ReleaseToApplication;

    public ValidReleaseToApp(string ReleaseToApp)
    {
        this.ReleaseToApplication = ReleaseToApp;
    }
} 

In the dynamically loaded DLL I set the attribute like this

[ValidReleaseToApp("TheAppName")]
public class ClassName : IInterfaceName
etc... etc....

But when I try and read the Attribute Value I only get the Attribute Name "ValidReleaseToApp" How do I retrieve the Value "TheAppName"?

Assembly a = Assembly.LoadFrom(PathToDLL);
Type type = a.GetType("Namespace.ClassName", true);
System.Reflection.MemberInfo info = type;
var attributes = info.GetCustomAttributes(true);
MessageBox.Show(attributes[0].ToString());

Update:

Since I am Dynamically loading the dll at runtime the definition of the Attribute is not avail. to the Main App. So when I try to do the following as suggested

string value = ((ValidReleaseToApp)attributes[0]).ReleaseToApplication;
MessageBox.Show(value);

I get this error

The type or namespace name 'ValidReleaseToApp' could not be found

Update2:

OK so the problem was that I defined the Attribute within the project of the dynamically loaded DLL. Once I moved the Attribute definitions to it's own project and Added a reference to that project to both the Main Project and that of the Dynamically loaded dll The suggested code worked.

+2  A: 

This should work, I don't have an example in front of me right now, but it looks right. You're basically skipping the steps of exposing the property you want access to, and casting to the attribute type to retrieve that property.

using System;
[AttributeUsage(AttributeTargets.Class)]
public class ValidReleaseToApp : Attribute
{
    private string _releaseToApplication;
    public string ReleaseToApplication { get { return _releaseToApplication; } }

    public ValidReleaseToApp(string ReleaseToApp)
    {
        this._releaseToApplication = ReleaseToApp;
    }
} 


Assembly a = Assembly.LoadFrom(PathToDLL);
Type type = a.GetType("Namespace.ClassName", true);
System.Reflection.MemberInfo info = type;
var attributes = info.GetCustomAttributes(true);
if(attributes[0] is ValidReleaseToApp){
   string value = ((ValidReleaseToApp)attributes[0]).ReleaseToApplication ;
   MessageBox.Show(value);
}
Jim Schubert
The DLL has the definition of the Attribute but not the app that I a calling it from so when I tried the Code above I rec'd compile error "The Type or Namespace ValidReleaseToApp Could not be found" If I copy the Attrib def into the calling app I get run time error Unable to cast object of type 'ValidReleaseToApp' to type 'ValidReleaseToApp'." any ideas?
TooFat
In that case, you'll have to get the type of the attribute the same way you're getting the type of the class (where you have `type`). Then instead of `is ValidReleaseToApp`, I think you can just do `is typeof(attributeTypeFromAssembly)`
Jim Schubert
Thanks for the help but if I retrieve the type like this "Type attrType = a.GetType("ValidReleaseToApp", true);"How can I use that to cast the object to a ValidReleaseToApp?
TooFat
Sorry, I was out of town for a memorial service. Did you figure out the task?
Jim Schubert
A: 

Once you have the custom attributes, you can cast them to instances of the attribute class and access their proerties:

object[] attributes = info.GetCustomAttributes(typeof(ValidReleaseToAppAttribute), true);
ValidReleaseToAppAttrigute attrib = attributes[0] as ValidReleaseToAppAttribute;
MessageBox.Show(attrib.ReleaseToApp);
Dr Herbie