feat: verify Tornado PGM cut sequence
This commit is contained in:
@@ -8,7 +8,8 @@ internal enum SmokeCommandKind
|
||||
TestPlan,
|
||||
TestConnect,
|
||||
TestSequence,
|
||||
PgmConnectDiagnostic
|
||||
PgmConnectDiagnostic,
|
||||
PgmCutsSequence
|
||||
}
|
||||
|
||||
internal sealed record SmokeCommandInvocation(
|
||||
@@ -19,7 +20,8 @@ internal sealed record SmokeCommandInvocation(
|
||||
int? ObservationMilliseconds = null,
|
||||
string? Host = null,
|
||||
int? Port = null,
|
||||
string? ExpectedPgmWindowTitle = null);
|
||||
string? ExpectedPgmWindowTitle = null,
|
||||
string? SceneRoot = null);
|
||||
|
||||
internal sealed record SmokeCommandParseResult(
|
||||
bool IsValid,
|
||||
@@ -32,6 +34,8 @@ internal static class SmokeCommandLine
|
||||
"--acknowledge-isolated-non-program-test-output";
|
||||
internal const string PgmConnectAcknowledgementFlag =
|
||||
"--i-understand-this-will-contact-current-pgm-tornado-via-ktap-connect-and-disconnect-only";
|
||||
internal const string PgmCutsSequenceAcknowledgementFlag =
|
||||
"--i-understand-this-will-render-current-pgm-tornado-cuts-5001-then-5006-and-take-them-out";
|
||||
|
||||
public static SmokeCommandParseResult Parse(IReadOnlyList<string> arguments)
|
||||
{
|
||||
@@ -57,6 +61,7 @@ internal static class SmokeCommandLine
|
||||
"--test-connect" => SmokeCommandKind.TestConnect,
|
||||
"--test-sequence" => SmokeCommandKind.TestSequence,
|
||||
"--pgm-connect-diagnostic" => SmokeCommandKind.PgmConnectDiagnostic,
|
||||
"--pgm-cuts-sequence" => SmokeCommandKind.PgmCutsSequence,
|
||||
_ => SmokeCommandKind.Invalid
|
||||
};
|
||||
if (kind == SmokeCommandKind.Invalid)
|
||||
@@ -71,6 +76,7 @@ internal static class SmokeCommandLine
|
||||
string? host = null;
|
||||
int? port = null;
|
||||
string? expectedPgmWindowTitle = null;
|
||||
string? sceneRoot = null;
|
||||
var acknowledged = false;
|
||||
|
||||
for (var index = 1; index < arguments.Count; index++)
|
||||
@@ -78,8 +84,10 @@ internal static class SmokeCommandLine
|
||||
var argument = arguments[index];
|
||||
switch (argument)
|
||||
{
|
||||
case AcknowledgementFlag when kind != SmokeCommandKind.PgmConnectDiagnostic:
|
||||
case AcknowledgementFlag when kind is not (
|
||||
SmokeCommandKind.PgmConnectDiagnostic or SmokeCommandKind.PgmCutsSequence):
|
||||
case PgmConnectAcknowledgementFlag when kind == SmokeCommandKind.PgmConnectDiagnostic:
|
||||
case PgmCutsSequenceAcknowledgementFlag when kind == SmokeCommandKind.PgmCutsSequence:
|
||||
if (acknowledged)
|
||||
{
|
||||
return Invalid("duplicate-option");
|
||||
@@ -88,7 +96,8 @@ internal static class SmokeCommandLine
|
||||
acknowledged = true;
|
||||
break;
|
||||
|
||||
case "--host" when kind == SmokeCommandKind.PgmConnectDiagnostic:
|
||||
case "--host" when kind is
|
||||
SmokeCommandKind.PgmConnectDiagnostic or SmokeCommandKind.PgmCutsSequence:
|
||||
if (host is not null)
|
||||
{
|
||||
return Invalid("duplicate-option");
|
||||
@@ -101,7 +110,8 @@ internal static class SmokeCommandLine
|
||||
|
||||
break;
|
||||
|
||||
case "--port" when kind == SmokeCommandKind.PgmConnectDiagnostic:
|
||||
case "--port" when kind is
|
||||
SmokeCommandKind.PgmConnectDiagnostic or SmokeCommandKind.PgmCutsSequence:
|
||||
if (port is not null)
|
||||
{
|
||||
return Invalid("duplicate-option");
|
||||
@@ -122,7 +132,8 @@ internal static class SmokeCommandLine
|
||||
break;
|
||||
|
||||
case "--expected-pgm-window-title"
|
||||
when kind == SmokeCommandKind.PgmConnectDiagnostic:
|
||||
when kind is
|
||||
SmokeCommandKind.PgmConnectDiagnostic or SmokeCommandKind.PgmCutsSequence:
|
||||
if (expectedPgmWindowTitle is not null)
|
||||
{
|
||||
return Invalid("duplicate-option");
|
||||
@@ -135,7 +146,21 @@ internal static class SmokeCommandLine
|
||||
|
||||
break;
|
||||
|
||||
case "--config" when kind != SmokeCommandKind.PgmConnectDiagnostic:
|
||||
case "--scene-root" when kind == SmokeCommandKind.PgmCutsSequence:
|
||||
if (sceneRoot is not null)
|
||||
{
|
||||
return Invalid("duplicate-option");
|
||||
}
|
||||
|
||||
if (!TryReadValue(arguments, ref index, out sceneRoot))
|
||||
{
|
||||
return Invalid("missing-option-value");
|
||||
}
|
||||
|
||||
break;
|
||||
|
||||
case "--config" when kind is not (
|
||||
SmokeCommandKind.PgmConnectDiagnostic or SmokeCommandKind.PgmCutsSequence):
|
||||
if (configPath is not null)
|
||||
{
|
||||
return Invalid("duplicate-option");
|
||||
@@ -194,6 +219,26 @@ internal static class SmokeCommandLine
|
||||
observationMilliseconds = observationValue;
|
||||
break;
|
||||
|
||||
case "--observe-ms" when kind == SmokeCommandKind.PgmCutsSequence:
|
||||
if (observationMilliseconds is not null)
|
||||
{
|
||||
return Invalid("duplicate-option");
|
||||
}
|
||||
|
||||
if (!TryReadValue(arguments, ref index, out var pgmObservationText) ||
|
||||
!int.TryParse(
|
||||
pgmObservationText,
|
||||
System.Globalization.NumberStyles.None,
|
||||
System.Globalization.CultureInfo.InvariantCulture,
|
||||
out var pgmObservationValue) ||
|
||||
pgmObservationValue != 5_000)
|
||||
{
|
||||
return Invalid("invalid-observation-duration");
|
||||
}
|
||||
|
||||
observationMilliseconds = pgmObservationValue;
|
||||
break;
|
||||
|
||||
default:
|
||||
return Invalid("unknown-option");
|
||||
}
|
||||
@@ -220,6 +265,28 @@ internal static class SmokeCommandLine
|
||||
ExpectedPgmWindowTitle: expectedPgmWindowTitle));
|
||||
}
|
||||
|
||||
if (kind == SmokeCommandKind.PgmCutsSequence)
|
||||
{
|
||||
if (string.IsNullOrWhiteSpace(host) ||
|
||||
!System.Net.IPAddress.TryParse(host, out var literalHost) ||
|
||||
!System.Net.IPAddress.IsLoopback(literalHost) ||
|
||||
port is null ||
|
||||
string.IsNullOrWhiteSpace(expectedPgmWindowTitle) ||
|
||||
string.IsNullOrWhiteSpace(sceneRoot) ||
|
||||
!Path.IsPathFullyQualified(sceneRoot))
|
||||
{
|
||||
return Invalid("missing-or-invalid-required-option");
|
||||
}
|
||||
|
||||
return Valid(new SmokeCommandInvocation(
|
||||
kind,
|
||||
ObservationMilliseconds: observationMilliseconds ?? 5_000,
|
||||
Host: host,
|
||||
Port: port,
|
||||
ExpectedPgmWindowTitle: expectedPgmWindowTitle,
|
||||
SceneRoot: sceneRoot));
|
||||
}
|
||||
|
||||
if (string.IsNullOrWhiteSpace(configPath))
|
||||
{
|
||||
return Invalid("missing-required-option");
|
||||
@@ -254,7 +321,8 @@ internal static class SmokeCommandLine
|
||||
observationMilliseconds,
|
||||
host,
|
||||
port,
|
||||
expectedPgmWindowTitle));
|
||||
expectedPgmWindowTitle,
|
||||
sceneRoot));
|
||||
}
|
||||
|
||||
internal static bool IsSafeSceneCode(string value)
|
||||
|
||||
Reference in New Issue
Block a user