Implement test-runner PoC (#8)

This commit is contained in:
minsung
2026-04-07 15:21:03 +09:00
parent 836afea5ee
commit 96df2ef65d
12 changed files with 665 additions and 0 deletions

View File

@@ -0,0 +1,161 @@
using System.Text.Json;
using Recordingtest.Runner;
using Xunit;
namespace Recordingtest.Runner.Tests;
public class TestRunnerTests : IDisposable
{
private readonly string _root;
public TestRunnerTests()
{
_root = Path.Combine(Path.GetTempPath(), "rt-runner-" + Guid.NewGuid().ToString("N"));
Directory.CreateDirectory(_root);
}
public void Dispose()
{
try { Directory.Delete(_root, true); } catch { }
}
private (string scenariosDir, string baselinesDir, string outDir) MakeDirs()
{
var s = Path.Combine(_root, "scenarios");
var b = Path.Combine(_root, "baselines");
var o = Path.Combine(_root, "out");
Directory.CreateDirectory(s);
Directory.CreateDirectory(b);
Directory.CreateDirectory(o);
return (s, b, o);
}
private static string ScenarioYaml(string name) => $@"name: {name}
description: test
sut:
exe: dummy.exe
steps:
- kind: save
value: ctrl+s
";
private static void WriteScenario(string dir, string name)
=> File.WriteAllText(Path.Combine(dir, name + ".yaml"), ScenarioYaml(name));
[Fact]
public void TwoScenarios_BothIdentical_ExitZero_AllPass()
{
var (sDir, bDir, oDir) = MakeDirs();
WriteScenario(sDir, "alpha");
WriteScenario(sDir, "beta");
var content = "{\"x\":1}";
File.WriteAllText(Path.Combine(bDir, "alpha.json"), content);
File.WriteAllText(Path.Combine(bDir, "beta.json"), content);
var opts = new RunnerOptions { ScenariosDir = sDir, BaselinesDir = bDir, OutDir = oDir };
var report = new TestRunner().RunAll(opts, new FakeHostFactory(content), new SpyNormalizer(), new StubDiffer(identical: true));
Assert.Equal(2, report.Total);
Assert.Equal(2, report.Passed);
Assert.Equal(0, report.Failed);
Assert.Equal(0, TestRunner.ToExitCode(report));
}
[Fact]
public void OneScenarioDiffers_ExitOne_HunkCount()
{
var (sDir, bDir, oDir) = MakeDirs();
WriteScenario(sDir, "alpha");
var content = "{\"x\":1}";
File.WriteAllText(Path.Combine(bDir, "alpha.json"), content);
var opts = new RunnerOptions { ScenariosDir = sDir, BaselinesDir = bDir, OutDir = oDir };
var report = new TestRunner().RunAll(opts, new FakeHostFactory(content), new SpyNormalizer(), new StubDiffer(identical: false, hunkCount: 1));
Assert.Equal(1, TestRunner.ToExitCode(report));
Assert.Equal("fail", report.Scenarios[0].Status);
Assert.Equal(1, report.Scenarios[0].Hunks);
}
[Fact]
public void PlayerThrows_ExitTwo_ErrorStatus()
{
var (sDir, bDir, oDir) = MakeDirs();
// scenario with a click step so the throw triggers
var name = "boom";
var yaml = @"name: boom
sut:
exe: dummy.exe
steps:
- kind: click
target:
uia_path: /Window
offset: [0.5, 0.5]
";
File.WriteAllText(Path.Combine(sDir, name + ".yaml"), yaml);
var opts = new RunnerOptions { ScenariosDir = sDir, BaselinesDir = bDir, OutDir = oDir };
var report = new TestRunner().RunAll(opts, new FakeHostFactory("{}", throwOnClick: true), new SpyNormalizer(), new StubDiffer(identical: true));
Assert.True(report.Errored >= 1);
Assert.Equal(2, TestRunner.ToExitCode(report));
}
[Fact]
public void EmptyScenariosDir_ExitZero_TotalZero()
{
var (sDir, bDir, oDir) = MakeDirs();
var opts = new RunnerOptions { ScenariosDir = sDir, BaselinesDir = bDir, OutDir = oDir };
var report = new TestRunner().RunAll(opts, new FakeHostFactory("{}"), new SpyNormalizer(), new StubDiffer(identical: true));
Assert.Equal(0, report.Total);
Assert.Equal(0, TestRunner.ToExitCode(report));
}
[Fact]
public void ProfileOverride_IsPassedToNormalizer()
{
var (sDir, bDir, oDir) = MakeDirs();
WriteScenario(sDir, "alpha");
var content = "{\"x\":1}";
File.WriteAllText(Path.Combine(bDir, "alpha.json"), content);
var spy = new SpyNormalizer();
var opts = new RunnerOptions { ScenariosDir = sDir, BaselinesDir = bDir, OutDir = oDir, Profile = "strict" };
new TestRunner().RunAll(opts, new FakeHostFactory(content), spy, new StubDiffer(identical: true));
Assert.Contains("strict", spy.Profiles);
Assert.DoesNotContain("default", spy.Profiles);
}
[Fact]
public void ReportJson_HasExpectedSchema_And_ReportMd_Exists()
{
var (sDir, bDir, oDir) = MakeDirs();
WriteScenario(sDir, "alpha");
var content = "{\"x\":1}";
File.WriteAllText(Path.Combine(bDir, "alpha.json"), content);
var opts = new RunnerOptions { ScenariosDir = sDir, BaselinesDir = bDir, OutDir = oDir };
new TestRunner().RunAll(opts, new FakeHostFactory(content), new SpyNormalizer(), new StubDiffer(identical: true));
var jsonPath = Path.Combine(oDir, "report.json");
var mdPath = Path.Combine(oDir, "report.md");
Assert.True(File.Exists(jsonPath));
Assert.True(File.Exists(mdPath));
using var doc = JsonDocument.Parse(File.ReadAllText(jsonPath));
var root = doc.RootElement;
Assert.True(root.TryGetProperty("runAt", out _));
Assert.True(root.TryGetProperty("total", out _));
Assert.True(root.TryGetProperty("passed", out _));
Assert.True(root.TryGetProperty("failed", out _));
Assert.True(root.TryGetProperty("errored", out _));
Assert.True(root.TryGetProperty("scenarios", out var scenarios));
var first = scenarios[0];
Assert.True(first.TryGetProperty("name", out _));
Assert.True(first.TryGetProperty("status", out _));
Assert.True(first.TryGetProperty("hunks", out _));
Assert.True(first.TryGetProperty("checkpointCount", out _));
Assert.True(first.TryGetProperty("artifactDir", out _));
}
}