19 December 2009

AssemblyAttributes

This is a cute little helper class that is useful for almost every .NET or Silverlight application that displays some information about itself (think “About Box”). It retrieves the values of the following assembly attributes in an easy and consistent manner:
  • Title
  • Product
  • Copyright
  • Company
  • Description
  • Trademark
  • Configuration
  • Version
  • FileVersion
  • InformationalVersion

Doing so is a piece of cake for every experienced developer but getting these information for the 100th time manually through reflection is quite cumbersome. And junior developers sometimes don’t know where to start and get lost in learning about reflection and attributes.
With the help of generics and lambdas you can code an elegant class that solves this problem one and for all. Usage is like this:

AssemblyAttributes assembly = new AssemblyAttributes();

string title = assembly.Title;
string version = assembly.Version;

And this is the full source:

/// <summary>
/// Easy access to common Assembly attributes.
/// </summary>
public class AssemblyAttributes
{
    readonly Assembly _assembly;

    public AssemblyAttributes() : this(Assembly.GetCallingAssembly())
    {}

    public AssemblyAttributes(Assembly assembly)
    {
        _assembly = assembly;
    }

    public string Title
    {
        get { return GetValue<AssemblyTitleAttribute>(a => a.Title); }
    }

    public string Product
    {
        get { return GetValue<AssemblyProductAttribute>(a => a.Product); }
    }

    public string Copyright
    {
        get { return GetValue<AssemblyCopyrightAttribute>(a => a.Copyright); }
    }

    public string Company
    {
        get { return GetValue<AssemblyCompanyAttribute>(a => a.Company); }
    }

    public string Description
    {
        get { return GetValue<AssemblyDescriptionAttribute>(a => a.Description); }
    }    
    
    public string Trademark
    {
        get { return GetValue<AssemblyTrademarkAttribute>(a => a.Trademark); }
    }   
    
    public string Configuration
    {
        get { return GetValue<AssemblyConfigurationAttribute>(a => a.Configuration); }
    }

    public string Version
    {
        get
        {
#if !SILVERLIGHT
            return _assembly.GetName().Version.ToString();
#else
            return _assembly.FullName.Split(',')[1].Split('=')[1]; // workaround for silverlight
#endif
        }
    }

    public string FileVersion
    {
        get { return GetValue<AssemblyFileVersionAttribute>(a => a.Version); }
    }

    public string InformationalVersion
    {
        get { return GetValue<AssemblyInformationalVersionAttribute>(a => a.InformationalVersion); }
    }

    /// <summary>
    /// Returns the value of attribute T or String.Empty if no value is available.
    /// </summary>
    string GetValue<T>(Func<T, string> getValue) where T : Attribute
    {
        T a = (T)Attribute.GetCustomAttribute(_assembly, typeof(T));
        return a == null ? "" : getValue(a);
    }

}

The real workhorse of this class is the GetValue<T> method. It gets an arbitrary custom attribute from an assembly. If it exists, it returns the result of applying the getValue delegate on it. If the attributes does not exist, it returns the empty string.


The full article with downloads is posted at CodeProject.

1 comment: