Merge branch 'fix/standby-secret-mirror-status' (M1: standby mirror failures on the health report)

# Conflicts:
#	CLAUDE.md
#	docs/plans/2026-09-28-site-secrets-artifact-deploy-design.md
This commit is contained in:
Joseph Doherty
2026-09-28 21:37:03 -04:00
29 changed files with 1738 additions and 106 deletions
@@ -369,6 +369,7 @@ public class CentralControlDtoMapperTests
Assert.Null(roundTripped.LocalDbReplicationConnected);
Assert.Null(roundTripped.LocalDbOplogBacklog);
Assert.Null(roundTripped.StartupReconcilerActive);
Assert.Null(roundTripped.SecretMirrorStatuses);
}
[Fact]
@@ -384,10 +385,14 @@ public class CentralControlDtoMapperTests
DataConnectionEndpoints = new Dictionary<string, string>(),
DataConnectionTagQuality = new Dictionary<string, TagQualityCounts>(),
ClusterNodes = [],
SecretMirrorStatuses = [],
};
var roundTripped = CentralControlDtoMapper.FromDto(Wire(CentralControlDtoMapper.ToDto(original)));
Assert.NotNull(roundTripped.SecretMirrorStatuses);
Assert.Empty(roundTripped.SecretMirrorStatuses);
Assert.NotNull(roundTripped.DataConnectionEndpoints);
Assert.Empty(roundTripped.DataConnectionEndpoints);
Assert.NotNull(roundTripped.DataConnectionTagQuality);
@@ -559,6 +564,18 @@ public class CentralControlDtoMapperTests
DetachedScriptThreads = 2,
ScriptRunShedCount = 13,
SiteStreamAlarmDropCount = 41L,
// Review finding M1: every node's secret mirror status, standby included.
SecretMirrorStatuses =
[
new SecretMirrorNodeStatus("node-a", SampleInstant, []),
new SecretMirrorNodeStatus(
"node-b",
SampleInstant.AddMinutes(-3),
[
new SecretMirrorFailure("OPC-PWD", "did not decrypt on this node"),
new SecretMirrorFailure("MX-KEY", "could not be confirmed applied"),
]),
],
};
/// <summary>
@@ -611,6 +628,17 @@ public class CentralControlDtoMapperTests
Assert.Equal(expected.DetachedScriptThreads, actual.DetachedScriptThreads);
Assert.Equal(expected.ScriptRunShedCount, actual.ScriptRunShedCount);
Assert.Equal(expected.SiteStreamAlarmDropCount, actual.SiteStreamAlarmDropCount);
Assert.Equal(expected.SecretMirrorStatuses is null, actual.SecretMirrorStatuses is null);
if (expected.SecretMirrorStatuses is not null)
{
Assert.Equal(expected.SecretMirrorStatuses.Count, actual.SecretMirrorStatuses!.Count);
for (var i = 0; i < expected.SecretMirrorStatuses.Count; i++)
{
Assert.Equal(expected.SecretMirrorStatuses[i].NodeName, actual.SecretMirrorStatuses[i].NodeName);
Assert.Equal(expected.SecretMirrorStatuses[i].CheckedAtUtc, actual.SecretMirrorStatuses[i].CheckedAtUtc);
Assert.Equal(expected.SecretMirrorStatuses[i].Failures, actual.SecretMirrorStatuses[i].Failures);
}
}
}
/// <summary>