我的组织正在通过自定义的MSBuild任务将DotCover的控制台运行器(在这里和这里描述)集成到我们基于MSBuild的构建过程中。
正如您所期望的,我们将在单元测试程序集上覆盖NUnit运行。虽然我们对DotCover生成的覆盖结果非常满意,但我们发现我们的测试现在可以失败,而不会导致构建失败。前进一步,后退两步。
DotCover(至少我们运行它的方式)完全隐藏了所覆盖进程的结果,包括控制台输出和退出代码。我希望它在这方面表现得更像NCover——回显所覆盖进程的所有输出和退出代码。
有谁知道如何用DotCover控制台运行程序实现这些?获得被覆盖过程的退出代码是最重要的,因为我们需要在测试失败的情况下构建失败。
我们正在使用MSBuild和MSBuild社区任务来失败构建。
您可以使用MSBuild.CommunityTasks的XmlRead任务分析dotCover生成的输出xml文件。
<Target Name="DetermineCoverage">
<Message Text="==================================================" />
<Message Text="Determine Unit Test Coverage" />
<XmlRead
XPath="/Root/@CoveragePercent"
XmlFileName="dotCoverOutput.xml">
<Output TaskParameter="Value" PropertyName="CoveragePercent"/>
</XmlRead>
<Message Text="==" />
<Message Text="== Coverage Percentage $(CoveragePercent)" />
<Error
Text="Unit Test coverage did not exceed the desired threshold"
Condition="$(CoveragePercent) < 90" />
<Message Text="==================================================" />
</Target>
我也遇到了同样的问题。
另一种解决方法是首先在dotCover之外使用测试运行器运行单元测试。这将暴露正确的返回码。
然后作为第二步,运行dotCover来获得覆盖结果。
因为我需要一个快速的解决方法,所以我添加了一个后处理步骤来抓取在DotCover运行期间生成的NUnit xml文件,以查找测试用例失败,如果发现任何失败,则使构建失败。我通过一个简单的自定义MSBuild任务做到了这一点:
public class CheckNUnitResults : Task
{
[Required]
public string ResultFile { get; set; }
public override bool Execute()
{
Log.LogMessageFromText("Analyzing nunit results : " + ResultFile, MessageImportance.Normal);
var failedCases =
XDocument
.Load(ResultFile)
.Descendants("test-case")
.Where(xe => xe.Attribute("success").Value.Equals("False"));
var fail = failedCases.Any();
if (fail)
{
Log.LogError("Found test case failures : " +
string.Join(", ", failedCases
.Select(xe => xe.Attribute("name").Value)
.ToArray()));
}
return !fail;
}
}
这是由MSBuild调用的:
<CheckNUnitResults ResultFile="YourNUnitResultFile.xml" />
(我在包含结果文件的ItemGroup的循环中调用它)