我正在使用VS2008开发一个我正在Mono下开始测试的项目。 有很多使用VS单元测试框架编写的单元测试,有没有一个工具可以让我在Mono中运行它们?
谢谢,
答案 0 :(得分:2)
根据您使用的功能,它可能很简单或很难。您可以使用命名空间/类型别名来使用另一个类库来执行断言和属性。我编写了手动运行测试的控制台程序 - 当然我可以访问vs命名空间和程序集。
对于mono - 我的建议是完全使用另一个测试系统,因为你自己使用system.reflection命名空间来加载程序集,反映属性并按需要执行,这将是乏味的。
例如:
Pseudo code:
var assembly = loadAsembly(....)
foreach(type in assembly.types) {
if(type is static class and had method with AssemblyInitialiseAttrubute)){
InvokeTheMethod(method);
}
}
foreach(type in assembly.types) {
if(type is not class and had method with TestClass)){
InvokeTheMethod(method);
}
foreach(method in type with ClassinitialiseAttribute)
}
... etc
答案 1 :(得分:0)
我编写了以下代码,它在Mono上运行良好。该代码不依赖于Visual Studio测试专用DLL。令人惊讶的是,它在Mone(在我的PC上的VirtualBox上运行)上运行的速度比在Visual Studio中快一些。
using System;
using System.Collections.Generic;
using System.Linq;
using System.Reflection;
using System.Text;
using System.Threading.Tasks;
using System.IO;
namespace drvrapp {
public class TestRunner {
// assembly file (e.g. MyTestAssembly.dll) which should be in the same directory
public static void TestDll(string assemblyFile) {
string symbolsFile = Path.GetFileNameWithoutExtension(assemblyFile) + ".pdb";
byte[] assemblyBytes = File.ReadAllBytes(assemblyFile);
byte[] symbolsBytes = File.ReadAllBytes(symbolsFile);
Assembly assembly = Assembly.Load(assemblyBytes, symbolsBytes);
foreach (Type type in assembly.GetTypes())
if (HasAttribute(type, "TestClass"))
foreach (MethodInfo method in type.GetMethods())
if (HasAttribute(method, "TestMethod"))
RunTest(method);
}
private static void RunTest(MethodInfo method) {
Console.WriteLine("------------------------------------------------------------------------------------------");
Console.Write("Running {0}.{1}...", method.DeclaringType.Name, method.Name);
if (HasAttribute(method, "Ignore")) {
Console.WriteLine("IGNORED");
return;
}
try {
Type testType = method.DeclaringType;
object typeClassInstance = Activator.CreateInstance(testType);
RunInitializeOrCleanup(typeClassInstance, "TestInitialize");
method.Invoke(typeClassInstance, null);
RunInitializeOrCleanup(typeClassInstance, "TestCleanup");
Console.WriteLine("PASSED");
} catch (Exception e) {
Console.WriteLine();
Console.WriteLine(e);
}
}
private static void RunInitializeOrCleanup(object instance, string attribute) {
MethodInfo method = instance.GetType().GetMethods().SingleOrDefault(x => HasAttribute(x, attribute));
if (method != null)
method.Invoke(instance, null);
}
private static bool HasAttribute(MemberInfo info, string attributeName) {
return info.GetCustomAttributes(false).Any(x => x.GetType().Name == attributeName + "Attribute");
}
}
}
using System;
using System.Collections.Generic;
using System.Linq;
using System.Reflection;
using System.Text;
using System.Threading.Tasks;
using System.IO;
namespace drvrapp {
public class TestRunner {
// assembly file (e.g. MyTestAssembly.dll) which should be in the same directory
public static void TestDll(string assemblyFile) {
string symbolsFile = Path.GetFileNameWithoutExtension(assemblyFile) + ".pdb";
byte[] assemblyBytes = File.ReadAllBytes(assemblyFile);
byte[] symbolsBytes = File.ReadAllBytes(symbolsFile);
Assembly assembly = Assembly.Load(assemblyBytes, symbolsBytes);
foreach (Type type in assembly.GetTypes())
if (HasAttribute(type, "TestClass"))
foreach (MethodInfo method in type.GetMethods())
if (HasAttribute(method, "TestMethod"))
RunTest(method);
}
private static void RunTest(MethodInfo method) {
Console.WriteLine("------------------------------------------------------------------------------------------");
Console.Write("Running {0}.{1}...", method.DeclaringType.Name, method.Name);
if (HasAttribute(method, "Ignore")) {
Console.WriteLine("IGNORED");
return;
}
try {
Type testType = method.DeclaringType;
object typeClassInstance = Activator.CreateInstance(testType);
RunInitializeOrCleanup(typeClassInstance, "TestInitialize");
method.Invoke(typeClassInstance, null);
RunInitializeOrCleanup(typeClassInstance, "TestCleanup");
Console.WriteLine("PASSED");
} catch (Exception e) {
Console.WriteLine();
Console.WriteLine(e);
}
}
private static void RunInitializeOrCleanup(object instance, string attribute) {
MethodInfo method = instance.GetType().GetMethods().SingleOrDefault(x => HasAttribute(x, attribute));
if (method != null)
method.Invoke(instance, null);
}
private static bool HasAttribute(MemberInfo info, string attributeName) {
return info.GetCustomAttributes(false).Any(x => x.GetType().Name == attributeName + "Attribute");
}
}
}