Skip to content

Commit

Permalink
Makes working with test result artefacts easier
Browse files Browse the repository at this point in the history
If you use SaveTestOutput (a method on OutputDirectoryTest) a saved file will be saved to it's individual directory (as before), registered with mstest, and now (NEW) will also be saved in a daily test output folder in tests/Results/.

This flattened-folder output makes it much easier to compare output between tests when we're debugging.

We have to adhere to the mstest results directory layout for CI tests so SaveTestOutput makes a copy of the file to daily output.

Daily output is disabled for the CI server
  • Loading branch information
atruskie committed May 13, 2020
1 parent f1f705d commit 796057e
Show file tree
Hide file tree
Showing 5 changed files with 84 additions and 12 deletions.
14 changes: 8 additions & 6 deletions tests/Acoustics.Test/.runsettings
Original file line number Diff line number Diff line change
@@ -1,7 +1,8 @@
<?xml version="1.0" encoding="utf-8" ?>
<RunSettings>
<RunConfiguration>
<ResultsDirectory>../../tests/Results</ResultsDirectory>
<ResultsDirectory>../../tests/Results</ResultsDirectory>
<MaxCpuCount>0</MaxCpuCount>
</RunConfiguration>
<LoggerRunSettings>
<Loggers>
Expand All @@ -24,10 +25,11 @@
</DataCollectionRunSettings>
<!-- MSTest adapter -->
<MSTest>
<CaptureTraceOutput>true</CaptureTraceOutput>
<Parallelize>
<Workers>0</Workers>
<Scope>ClassLevel</Scope>
</Parallelize>
<CaptureTraceOutput>true</CaptureTraceOutput>
<!--<DeleteDeploymentDirectoryAfterTestRunIsComplete>false</DeleteDeploymentDirectoryAfterTestRunIsComplete>-->
<Parallelize>
<Workers>0</Workers>
<Scope>ClassLevel</Scope>
</Parallelize>
</MSTest>
</RunSettings>
13 changes: 9 additions & 4 deletions tests/Acoustics.Test/TestHelpers/GeneratedImageTest.cs
Original file line number Diff line number Diff line change
Expand Up @@ -104,15 +104,20 @@ protected void SaveExtraImage(string token, Image<T> image)
private void SaveImage(string typeToken, Image<T> image)
{
var extra = this.ExtraName.IsNullOrEmpty() ? string.Empty : "_" + this.ExtraName;
var path = this.ClassOutputDirectory.CombinePath($"{this.TestContext.TestName}{extra}_{typeToken}.png");

var outName = $"{this.TestContext.TestName}{extra}_{typeToken}.png";
if (image == null)
{
this.TestContext.WriteLine($"Skipping writing expected image `{path}` because it is null");
this.TestContext.WriteLine($"Skipping writing expected image `{outName}` because it is null");
return;
}

image.Save(path);
this.TestContext.AddResultFile(path);
this.SaveTestOutput(output =>
{
var path = output.CombinePath(outName);
image.Save(path);
return path;
});
}

private bool ShouldWrite(WriteTestOutput should) =>
Expand Down
42 changes: 40 additions & 2 deletions tests/Acoustics.Test/TestHelpers/OutputDirectoryTest.cs
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@ public class OutputDirectoryTest
{
private DirectoryInfo classOutputDirectory = null;
private DirectoryInfo testOutputDirectory = null;
private DirectoryInfo dailyOutputDirectory = null;

public static DirectoryInfo ResultsDirectory { get; private set; } = PathHelper.ClassOutputDirectory();

Expand All @@ -32,12 +33,49 @@ public class OutputDirectoryTest
protected DirectoryInfo TestOutputDirectory =>
this.testOutputDirectory ??= PathHelper.TestOutputDirectory(this.TestContext);

protected string SaveTestOutput(Func<DirectoryInfo, string> callback)
/// <summary>
/// Gets a directory that has results grouped by day.
/// </summary>
protected DirectoryInfo DailyOutputDirectory =>
this.dailyOutputDirectory ??= PathHelper.DailyOutputDirectory(this.TestContext);

/// <summary>
/// Save a test result.
/// Also saves copies of test results to daily output directories.
/// The callback provides the output directory to save your file to.
/// You need to return the full path of the file saved.
/// </summary>
protected FileInfo SaveTestOutput(Func<DirectoryInfo, FileInfo> callback)
{
var savedFile = callback.Invoke(this.TestOutputDirectory);
this.TestContext.AddResultFile(savedFile);

if (!savedFile.Exists)
{
throw new InvalidOperationException("You must return the full path of the file that was saved.");
}

this.TestContext.AddResultFile(savedFile.FullName);

// if we're on the CI the DO NOT save the file to a daily work folder
if (!TestHelper.OnContinuousIntegrationServer)
{
var newName = PathHelper.DailyOutputFileNamePrefix(this.TestContext) + savedFile.Name;
var newPath = this
.DailyOutputDirectory
.CombinePath(newName);
savedFile.CopyTo(newPath);
}

return savedFile;
}

/// <summary>
/// Save a test result.
/// Also saves copies of test results to daily output directories.
/// </summary>
protected FileInfo SaveTestOutput(Func<DirectoryInfo, string> callback)
{
return this.SaveTestOutput(directory => callback.Invoke(directory)?.ToFileInfo());
}
}
}
23 changes: 23 additions & 0 deletions tests/Acoustics.Test/TestHelpers/PathHelper.cs
Original file line number Diff line number Diff line change
Expand Up @@ -91,6 +91,29 @@ public static DirectoryInfo TestOutputDirectory(TestContext context = null)
return ClassOutputDirectory(context).CreateSubdirectory(context.TestName);
}

/// <summary>
/// DO NOT USE THIS DIRECTLY.
/// <see cref="OutputDirectoryTest.SaveTestOutput(Func{DirectoryInfo, FileInfo})"/>.
/// </summary>
public static DirectoryInfo DailyOutputDirectory(TestContext context = null)
{
context ??= testContext;
var rootResults = Path.Combine(context.TestResultsDirectory, "..", "..");

return rootResults
.ToDirectoryInfo()
.CreateSubdirectory(TestSetup.TestDate.ToString("yyyyMMdd"));
}

public static string DailyOutputFileNamePrefix(TestContext context = null)
{
context ??= testContext;
var lastDot = context.FullyQualifiedTestClassName.LastIndexOf('.') + 1;
var shortClassName = context.FullyQualifiedTestClassName[lastDot..];

return TestSetup.TestDate.ToString("HHmmss") + "_" + shortClassName + "_" + context.TestName + "_";
}

public static void DeleteTempDir(DirectoryInfo dir)
{
try
Expand Down
4 changes: 4 additions & 0 deletions tests/Acoustics.Test/TestHelpers/TestSetup.cs
Original file line number Diff line number Diff line change
Expand Up @@ -4,18 +4,22 @@

namespace Acoustics.Test.TestHelpers
{
using System;
using Acoustics.Shared.Logging;
using log4net.Core;
using Microsoft.VisualStudio.TestTools.UnitTesting;

[TestClass]
public class TestSetup
{
public static DateTime TestDate { get; private set; }

public static Logging TestLogging { get; set; }

[AssemblyInitialize]
public static void AssemblyInitialize(TestContext context)
{
TestDate = DateTime.Now;
PathHelper.Initialize(context);
TestLogging = new Logging(
enableMemoryLogger: true,
Expand Down

0 comments on commit 796057e

Please sign in to comment.