如何获取当前执行测试的状态?我想在 Dispose() 方法中知道当前测试是否失败。这应该类似于mstest的 TestContext.CurrentTestOutcome.
我在 xunit 网站上问过同样的问题,我也可以在这里分享答案。 基本上根据 https://github.com/xunit/xunit/issues/398 没有办法知道测试内部的测试状态。另外根据 https://github.com/xunit/xunit/issues/416 xunit 中没有 TestContext 之类的东西。
虽然 xUnit 没有支持显示当前测试是否失败的 API 是正确的,但 Simon Cropp 制作了一个名为 XunitContext 的 Nuget 包,它支持您可以询问测试是否失败:
https://github.com/SimonCropp/XunitContext#test-failure
https://www.nuget.org/packages/XunitContext/
当测试失败时,表示为异常。可以通过启用异常捕获,然后访问 Context.TestException 来查看异常。如果测试通过,则 TestException 将为 null。
我在 MS Playwright 中这样使用它,以确保我只在测试失败时保存跟踪,因为它们会占用大量磁盘空间:
string? tracePath = GetTracePath(testName);
// Stop tracing and save data into a zip archive.
await context.Tracing.StopAsync(new TracingStopOptions
{
Path = tracePath
});
private static string? GetTracePath(string? testName)
{
// Only save trace if the test failed, since it can take up a lot of space in CI.
// TestException will be null if there was a failure in the test, in this case we set the tracePath to null, which Playwright interprets as "do not write the trace file".
// See https://github.com/SimonCropp/XunitContext#test-failure and https://github.com/microsoft/playwright-dotnet/issues/1964
return XunitContext.Context.TestException == null ? null : Path.Combine("Traces", "Trace_" + testName + ".zip");
}
为此,您还需要设置以下内容:
public class GlobalSetup
{
/// <summary>
/// Allows using Context.TestException from XUnitContext. See https://github.com/SimonCropp/XunitContext#test-failure
/// </summary>
[ModuleInitializer]
public static void Setup() => XunitContext.EnableExceptionCapture();
}
让你的测试类继承自 XunitContextBase
public abstract class PlaywrightTestBase : XunitContextBase, IClassFixture<DatabaseFixture>, IAsyncLifetime
并像这样使用 testOutputHelper 和 sourcefile 调用基本构造器:
protected PlaywrightTestBase(PlaywrightFixture playwrightFixture, DatabaseFixture databaseFixture, ITestOutputHelper testOutputHelper, [CallerFilePath] string sourceFile = "")
: base(testOutputHelper, sourceFile)
您也可以在 Dispose 方法中访问所有这些:
public override void Dispose()
{
var theExceptionThrownByTest = Context.TestException;
var testDisplayName = Context.Test.DisplayName;
var testCase = Context.Test.TestCase;
base.Dispose();
}