Reflect
Helper methods for inspecting a type by reflection.
Many of these methods take ICustomAttributeProvider as an
argument to avoid duplication, even though certain attributes can
only appear on specific types of members, like MethodInfo or Type.
In the case where a type is being examined for the presence of
an attribute, interface or named member, the Reflect methods
operate with the full name of the member being sought. This
removes the necessity of the caller having a reference to the
assembly that defines the item being sought and allows the
NUnit core to inspect assemblies that reference an older
version of the NUnit framework.
using System;
using System.Collections.Generic;
using System.Reflection;
using System.Threading;
namespace NUnit.Framework.Internal
{
public static class Reflect
{
private class BaseTypesFirstComparer : IComparer<MethodInfo>
{
public int Compare(MethodInfo m1, MethodInfo m2)
{
if (m1 == (MethodInfo)null || m2 == (MethodInfo)null)
return 0;
Type declaringType = m1.DeclaringType;
Type declaringType2 = m2.DeclaringType;
if (declaringType == declaringType2)
return 0;
if (declaringType.IsAssignableFrom(declaringType2))
return -1;
return 1;
}
}
private static readonly BindingFlags AllMembers = BindingFlags.Instance | BindingFlags.Static | BindingFlags.Public | BindingFlags.NonPublic;
private static readonly Type[] EmptyTypes = new Type[0];
public static MethodInfo[] GetMethodsWithAttribute(Type fixtureType, Type attributeType, bool inherit)
{
List<MethodInfo> list = new List<MethodInfo>();
BindingFlags bindingAttr = (BindingFlags)((int)AllMembers | (inherit ? 64 : 2));
MethodInfo[] methods = fixtureType.GetMethods(bindingAttr);
foreach (MethodInfo methodInfo in methods) {
if (methodInfo.IsDefined(attributeType, inherit))
list.Add(methodInfo);
}
list.Sort(new BaseTypesFirstComparer());
return list.ToArray();
}
public static bool HasMethodWithAttribute(Type fixtureType, Type attributeType)
{
MethodInfo[] methods = fixtureType.GetMethods(AllMembers | BindingFlags.FlattenHierarchy);
foreach (MethodInfo methodInfo in methods) {
if (methodInfo.IsDefined(attributeType, false))
return true;
}
return false;
}
public static object Construct(Type type)
{
ConstructorInfo constructor = type.GetConstructor(EmptyTypes);
if (constructor == (ConstructorInfo)null)
throw new InvalidTestFixtureException(type.FullName + " does not have a default constructor");
return constructor.Invoke(null);
}
public static object Construct(Type type, object[] arguments)
{
if (arguments == null)
return Construct(type);
Type[] typeArray = GetTypeArray(arguments);
ConstructorInfo constructor = type.GetConstructor(typeArray);
if (constructor == (ConstructorInfo)null)
throw new InvalidTestFixtureException(type.FullName + " does not have a suitable constructor");
return constructor.Invoke(arguments);
}
private static Type[] GetTypeArray(object[] objects)
{
Type[] array = new Type[objects.Length];
int num = 0;
foreach (object obj in objects) {
array[num++] = obj.GetType();
}
return array;
}
public static object InvokeMethod(MethodInfo method, object fixture)
{
return InvokeMethod(method, fixture, null);
}
public static object InvokeMethod(MethodInfo method, object fixture, params object[] args)
{
if (method != (MethodInfo)null)
try {
return method.Invoke(fixture, args);
} catch (ThreadAbortException) {
return null;
} catch (TargetInvocationException ex2) {
throw new NUnitException("Rethrown", ex2.InnerException);
} catch (Exception inner) {
throw new NUnitException("Rethrown", inner);
}
return null;
}
}
}