为WPF项目创建单元测试
原文作者: 周银辉 来源: 博客园 原文地址:http://www.cnblogs.com/zhouyinhui/archive/2007/09/30/911522.html
可能你已发现一个问题,我们无法使用VS对WPF项目创建单元测试(VS2005不行,VS2008我没试过,但据说也不行),这让人很郁闷,这里将介绍如何使用NUnit来对WPF项目创建单元测试并解决其中的难题(但利用NUnit来对WPF创建单元测试时并不会像针对.Net2.0一样容易,可能会出现一些小问题).
1,对普通类(非WPF UI组件)进行测试:
这和在.Net2.0中使用NUnit进行测试时一样,不会出现任何问题,参考下面的代码:
[TestFixture]
public class ClassTest
{
[Test]
public void TestRun()
{
ClassLibrary1.Class1 obj = new ClassLibrary1.Class1();
double expected = 9;
double result = obj.GetSomeValue(3);
Assert.AreEqual(expected, result);
}
}
2,对WPF UI组件进行测试
使用NUnit对WPF UI组件(比如MyWindow,MyUserControl)进行测试的时候,NUnit会报如下异常:“The calling thread must be STA, because many UI components require this”。
下面是错误的测试代码:
[TestFixture]
public class ClassTest
{
[Test]
public void TestRun()
{
WindowsApplication1.Window1 obj = new WindowsApplication1.Window1();
double expected = 9;
double result = obj.GetSomeValue(3);
Assert.AreEqual(expected, result);
}
}

为了让调用线程为STA,我们可以编写一个辅助类CrossThreadTestRunner:
using System;
using System.Collections.Generic;
using System.Text;
using System.Threading;
using System.Security.Permissions;
using System.Reflection;
namespace TestUnit
{
public class CrossThreadTestRunner
{
private Exception lastException;
public void RunInMTA(ThreadStart userDelegate)
{
Run(userDelegate, ApartmentState.MTA);
}
public void RunInSTA(ThreadStart userDelegate)
{
Run(userDelegate, ApartmentState.STA);
}
private void Run(ThreadStart userDelegate, ApartmentState apartmentState)
{
lastException = null;
Thread thread = new Thread(
delegate()
{
try
{
userDelegate.Invoke();
}
catch (Exception e)
{
lastException = e;
}
});
thread.SetApartmentState(apartmentState);
thread.Start();
thread.Join();
if (ExceptionWasThrown())
ThrowExceptionPreservingStack(lastException);
}
private bool ExceptionWasThrown()
{
return lastException != null;
}
[ReflectionPermission(SecurityAction.Demand)]
private static void ThrowExceptionPreservingStack(Exception exception)
{
FieldInfo remoteStackTraceString = typeof(Exception).GetField(
"_remoteStackTraceString",
BindingFlags.Instance | BindingFlags.NonPublic);
remoteStackTraceString.SetValue(exception, exception.StackTrace + Environment.NewLine);
throw exception;
}
}
}
并编写正确的测试代码:
[TestFixture]
public class ClassTest
{
[Test]
public void TestRun()
{
CrossThreadTestRunner runner = new CrossThreadTestRunner();
runner.RunInSTA(
delegate
{
Console.WriteLine(Thread.CurrentThread.GetApartmentState());
WindowsApplication1.Window1 obj = new WindowsApplication1.Window1();
double expected = 9;
double result = obj.GetSomeValue(3);
Assert.AreEqual(expected, result);
}); 
}
}



另外,使用NUnit时,您需要添加对nunit.framework.dll的引用,并对测试类添加[TestFixture]属性标记以及对测试方法添加[Test]属性标记,然后将生成的程序集用nunit.exe打开就可以了,关于NUnit的具体用法您可以参考其官方文档
为WPF项目创建单元测试的更多相关文章
- 项目中创建单元测试—VS2012
我们在每个项目的开发过程中,开发完一个功能,自己首先需要测试一下,VS提供了很方便的测试功能,可以很容易的创建单元测试,但是在VS2012中类名上点击右键没有『创建单元测试』这个菜单,需要先进行设置一 ...
- WPF入门教程系列(一) 创建你的第一个WPF项目
WPF入门教程系列(一) 创建你的第一个WPF项目 WPF基础知识 快速学习绝不是从零学起的,良好的基础是快速入手的关键,下面先为大家摞列以下自己总结的学习WPF的几点基础知识: 1) C#基础语法知 ...
- 使用 DotNet CLI 创建自定义的 WPF 项目模板
描述 当我们安装完 DotNetCore 3.0 版本的 SDK 后,我们就可以创建基于 DotNetCore 的 WPF 项目模板,通过如下 CLI 可以方便快捷的创建并运行我们的项目: dotne ...
- springmvc 项目完整示例02 项目创建-eclipse创建动态web项目 配置文件 junit单元测试
包结构 所需要的jar包直接拷贝到lib目录下 然后选定 build path 之后开始写项目代码 配置文件 ApplicationContext.xml <?xml version=" ...
- IDEA中SpringBoot项目快速创建单元测试
如何在IDEA中对于SpringBoot项目快速创建单元测试 创建测试用例 右键需要进行测试的方法,选择GO TO然后选择Test 点击Create New Test 勾选需要创建单元测试的方法 然后 ...
- 如何创建一个基于 .NET Core 3 的 WPF 项目
在 Connect(); 2018 大会上,微软发布了 .NET Core 3 Preview,以及基于 .NET Core 3 的 WPF:同时还发布了 Visual Studio 2019 预览版 ...
- VS2012安装完成之后,用自带的Blend无法创建WPF项目,打开WPF项目无法设计
Visual Studio 2012安装完成之后, 打开自带的Blend for Visual Studio 无法创建新的WPF或者Silverlight项.打开WPF项目无法编辑的原因: 1.VS自 ...
- 用Visual C++创建WPF项目的三种主要方法
用Visual C++创建WPF项目的三种主要方法 The problem with using XAML from C++ Because C++ doesn't support partial c ...
- VS Code Java 2 月更新!教育特别版:单元测试、GUI开发支持、Gradle项目创建、以及更多!
新春快乐!欢迎来到 Visual Studio Code Java 的 2 月更新,这个月我们给大家带来了一期教育特别版.每年的年初是许多学校开学的时间,为了给学生和教师提供在 Visual Stud ...
随机推荐
- 学php之翻译wordpress(2)
wp-load.php <?php /** * Bootstrap file for setting the ABSPATH constant * and loading the wp-conf ...
- Android Studio导入GitHub
方法一:引用开源项目的compile添加到gradle中http://www.zhihu.com/question/27027667 方法二:下载安装包引入:http://blog.csdn.net/ ...
- python socket 编程之一:编写socket的基本步骤
一.socket 编写server的步骤: 1.第一步是创建socket对象.调用socket构造函数.如: socket = socket.socket( family, type ) family ...
- bash 变量使用技巧
- MYSQL <=>运算符
<=> 与 =
- 正式学习React(五) Reactjs 的 PropTypes 使用方法
propTypes 使用來規範元件Props的型別與必需狀態 var Test = React.createClass({ propTypes: { // required requiredFunc: ...
- opencv菜鸟学习之旅cvNorm
Norm 计算数组的绝对范数, 绝对差分范数或者相对差分范数 double cvNorm( const CvArr* arr1, const CvArr* arr2=NULL, int norm_ty ...
- OpenSSL win 下报错 OPENSSL_Uplink(58D46000,08): no OPENSSL_Applink
python 中使用 M2Crypto 想读写文件时总是报: OPENSSL_Uplink(58D46000,08): no OPENSSL_Applink windows 平台下使用 openssl ...
- WorkFlow4.0--入门到精通系列-专题索引
原文地址:http://www.cnblogs.com/hegezhou_hot/archive/2011/06/15/2081405.html 开篇 首先.非常感谢大家的支持和厚爱,才有了这个系列, ...
- poj1458 dp入门
Common Subsequence Time Limit: 1000MS Memory Limit: 10000K Total Submissions: 37551 Accepted: 15 ...