这个问题与使用 MSTest 在 Visual Studio 中进行单元测试有关(这很重要,因为 MSTest 的执行顺序)。标记为 [TestInitialize] 的方法和测试类构造函数都将在每个测试方法之前运行。
所以,问题是,你倾向于在这些领域做什么?您是否避免在其中任何一个中进行某些活动?你的理由是什么:风格、技术、迷信?
这个问题与使用 MSTest 在 Visual Studio 中进行单元测试有关(这很重要,因为 MSTest 的执行顺序)。标记为 [TestInitialize] 的方法和测试类构造函数都将在每个测试方法之前运行。
所以,问题是,你倾向于在这些领域做什么?您是否避免在其中任何一个中进行某些活动?你的理由是什么:风格、技术、迷信?
构造函数只是语言提供的一种结构。每个测试框架似乎都有自己的受控生命周期“初始化”。您可能只会在使用构造函数来改变您的本地人时遇到麻烦。
MSTest:您会为每个TestMethod
. 这可能是唯一可以在构造函数、初始化程序或测试方法中改变本地变量而不影响其他测试方法的情况。
public class TestsForWhatever
{
public TestsForWhatever()
{
// You get one of these per test method, yay!
}
[TestInitialize]
public void Initialize()
{
// and one of these too!
}
[TestMethod]
public void AssertItDoesSomething() { }
[TestMethod]
public void AssertItDoesSomethingElse() { }
}
MSpec:你只会得到一个你所有Establish
的Because
断言(It
)。所以,不要在你的断言中改变你的本地人。并且不要依赖于基础上下文中本地人的突变(如果你使用它们)。
[Subject(typeof(Whatever))]
public class When_doing_whatever
{
Establish context = () =>
{
// one of these for all your Its
};
Because of = () => _subject.DoWhatever();
It should_do_something;
It should_do_something_else;
}
以下是我在 TestInitialize 中发现的一些优点。
使用 TestInitialize() 或 ClassInitialize() 而不是测试类实例或静态构造函数的主要优点是其显式性质。它清楚地表明您正在测试之前进行一些设置。从长远来看,始终如一地这样做应该会提高可维护性。
我更喜欢使用该[TestInitialize]
方法来执行被测试对象及其参数的实例化。如果需要实例化测试基类(通常是我创建或刷新存储库等的地方),我只在构造函数中执行工作。这有助于我将测试框架代码和测试代码在逻辑上和物理上分开。
这个问题也被问到(稍后)在 VS 测试框架中使用构造函数与 TestInitialize() 属性有什么区别?
FWIW 我假设“类构造函数”是指实例构造函数(而不是静态构造函数)。
我相信关于静态构造函数与ClassInitialize的问题同样可以问到您提出的相同问题...
我说除非你需要,否则使用构造函数TestContext
。
readonly
在测试初始化中使用 which 是一件大事,您想为测试准备不应该更改的东西(理想情况下,您准备的东西也是不可变的)。您测试的对象不需要在 [TestInitialize] 方法中实例化。您可以在测试方法 [Test] 中测试对象的构造函数。
[TestInitialize] 中的对象可以是设置您的持久性存储或准备测试对象将在测试中使用的值。
还有async
另一个原因(在提出这个问题时不存在)[TestInitialize]
。它允许您进行async
设置操作(例如加载文件),这在构造函数中是不可能的:
private string approver;
[TestInitialize]
public async Task Initialize()
{
approver = await File.ReadAllTextAsync("approver.json");
}
这取决于场景。如果您有一个测试类,并且出于某种奇怪的原因需要在另一个测试类上创建它的实例,则需要使用构造函数。
否则测试初始化更适合这个概念。首先,与上面写的原因相同,第二个 MS 可以在该属性上引入更多功能,您将受益于它们,使用构造函数您将坚持下去。
我希望有人仍然需要它。这是我的解决方案,如何对类构造函数进行单元测试。如果debuggingService 为空,我正在对类服务进行单元测试并抛出异常。
DebuggingStepTests 类构造函数
private readonly IDebuggingService debuggingService;
public string StepName { get; set; }
public DebuggingStep(IDebuggingService _debuggingService)
{
_log.Starting();
StepName = "DebuggingStep";
debuggingService = _debuggingService
?? throw new ArgumentException("DebuggingStep init failure due to => IDebuggingService null");
}
单元测试看起来像这样
[Fact]
public void TestDebuggingStepConstructorWhen_InitServiceIsNull_ResultArgumentException()
{
//Arrange
var arrange = new Action(() =>
{
new DebuggingStep(null);
});
//Act
//Arrange
Assert.Throws<ArgumentException>(arrange);
}
希望这对某人有帮助