如何在STAThread模式下运行单元测试?

62

我想测试一个使用剪贴板(WindowsForms)的应用程序,我还需要在我的单元测试中使用剪贴板。为了使用它,它应该在STA模式下运行,但由于NUnit TestFixture没有主方法,我不知道在哪里/如何对其进行注释。


好奇一下,将属性[STATThread]添加到您的TextFixture/TestMethod/TestClass顶部是否就足够了? - Will Marcouiller
它只适用于方法,而不适用于fixture设置、测试方法等。当然,我可能会忽略了什么。如果您发现其他解决方案,欢迎回答。 - Peter
4个回答

105

3
在尝试使用Visual Studio 2010 SP1中的ReSharper 5.1测试运行程序时,这是唯一有效的方法。 - Jim Raden
5
你还可以在单独的测试方法上使用 RequiresSTA,而 BCL 中的 STAThread 属性可以作为 RequiresSTA 的同义词。 - Alex Humphrey
1
在app.config中设置和在程序集属性中作为属性的区别是什么?在我的情况下,两者都会使测试报告以STA运行,但仅设置属性似乎可以使需要在同一线程上运行的测试通过。这是否意味着配置确保每个测试夹具按顺序在单独的线程上运行,并且程序集级别的属性使整个测试批处理在一个线程上运行? - Zepee
19
[RequiteSTA]现在已经过时了,应该使用[Apartment(ApartmentState.STA)] - bvj
现在你应该使用[RequiresThread(ApartmentState.STA)] - FredM

90

NUnit 3.0

最近我们迁移到了NUnit 3.0版本。我们之前使用的旧特性已经不再起作用。我们的测试中混合使用了[STAThread][RequiresSTA],就像mas_oz2k1的回答中所述。由于它们已经过时,因此STAThread产生了编译错误,而RequiresSTA则产生了警告。

新版本似乎使用以下内容:

程序集级别

[assembly: Apartment(ApartmentState.STA)]

课程难度

[TestFixture]
[Apartment(ApartmentState.STA)]

方法级别

[Test]
[Apartment(ApartmentState.STA)]

我试图寻找这些信息,这让我走上了一条黑暗之路,在那里人们使用名为CrossThreadTestRunner的类修改他们的测试代码。我猜这是在属性类被创建之前的2004年的解决方案。


5
这是针对 NUnit 3.0+ 的答案。别忘了包含 System.Threading - AutomatedChaos
在2023年,这仍然是使用NUnit 3.13.3的正确解决方案 - Dmitry Avtonomov

35

针对 NUnit 2.2、2.4(针对 2.5,请参见下面的简单解决方案):

向包含您的单元测试的项目添加一个 app.config 文件,并包括以下内容:

<?xml version="1.0" encoding="utf-8" ?>
<configuration>
    <configSections>
        <sectionGroup name="NUnit">
        <section name="TestRunner" type="System.Configuration.NameValueSectionHandler"/>
    </sectionGroup>
    </configSections>
    <NUnit>
        <TestRunner>
            <add key="ApartmentState" value="STA"/>
        </TestRunner>
    </NUnit>
</configuration>
你可以使用以下C#代码验证公寓线程是STA:
if (Thread.CurrentThread.GetApartmentState() != ApartmentState.STA)
{
   throw new ThreadStateException("The current threads apartment state is not STA");
}

6
简单而又令人沮丧的问题,立即得到了有效的答案:有些日子我就是喜欢Stack Overflow。 - Peter
如果您再次需要它(并且SO不可用),这是WatiN提供的示例配置文件中的内容。很高兴我能帮到您。 :) - Bernhard Hofmann
1
令人惊讶的是,即使在VS2010中使用Resharper运行测试,它也能正常工作。非常感谢! - Lee Oades
哇,你刚刚解决了我已经苦恼了一段时间的问题。这是我希望能够多次点赞的时刻之一。 - mdm
2
请注意,app.config文件必须以与dll相对应的名称结尾。例如,MyApp.Tests.dll的配置文件应该是MyApp.Tests.dll.config。VS会自动为您完成此操作,但如果您需要手动创建配置文件,请记住这一步骤。 - Jason Crease
1
在Linux/mono上,需要使用type="System.Configuration.NameValueSectionHandler, System"。 - Tom

4
在NUnit 2.6.1+中,你可以使用/apartment=STA命令行标志来实现:
NUnit-Console version 2.6.3.13283
Copyright (C) 2002-2012 Charlie Poole.
Copyright (C) 2002-2004 James W. Newkirk, Michael C. Two, Alexei A. Vorontsov.
Copyright (C) 2000-2002 Philip Craig.
All Rights Reserved.

Runtime Environment -
   OS Version: Microsoft Windows NT 6.1.7601 Service Pack 1
  CLR Version: 4.0.30319.18052 ( Net 4.5 )


NUNIT-CONSOLE [inputfiles] [options]

Runs a set of NUnit tests from the console.

You may specify one or more assemblies or a single
project file of type .nunit.

Options:
...
/apartment=X            Apartment for running tests: MTA (Default), STA
...

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接