using System.Text.Json.Nodes; using Eis.Infrastructure.Administration; namespace Eis.Infrastructure.Tests.Administration; public sealed class AdminPublicationProjectorTests { [Fact] public void VirtualRoundUsesSettingAsPatchTargetAndSuppressesFinalDuplicate() { var setting = Record( "setting-1", "setting", "completed", new JsonObject { ["autoPublish"] = true, ["publicVisible"] = false, ["completedAt"] = "2026-06-02T00:00:00.000Z", ["roundPublishedAt"] = "2026-06-01T00:00:00.000Z" }); var placement = Record( "placement-1", "placement", "final", new JsonObject { ["finalizedRound"] = 2 }); var snapshot = Snapshot([setting, placement]); var publication = Assert.Single(AdminPublicationProjector.Build(snapshot)); Assert.Equal("setting-1", publication["id"]?.GetValue()); Assert.Equal("admission", publication["sourceType"]?.GetValue()); Assert.Equal("示例考试第 2 轮录取名单公示", publication["title"]?.GetValue()); Assert.False(publication["visible"]?.GetValue()); Assert.Equal("hidden", publication["status"]?.GetValue()); Assert.Same(setting, AdminPublicationProjector.FindSourceRecord(snapshot.Records, "admission", "setting-1")); } [Fact] public void ReportingPublicationMatchesNodeProjection() { var report = new AdminPublicationRecord( "report-1", "notification", "exam-1", null, "school-1", "approved", new JsonObject { ["type"] = "admission_reporting", ["supplementDecision"] = "supplement", ["approvedAt"] = "2026-06-03T00:00:00.000Z", ["statistics"] = new JsonObject { ["totalQuota"] = 20, ["reportedCount"] = 15, ["reportingRate"] = 75 } }, "2026-06-01T00:00:00.000Z", "2026-06-03T00:00:00.000Z"); var publication = Assert.Single(AdminPublicationProjector.Build(Snapshot([report]))); Assert.Equal("reporting", publication["sourceType"]?.GetValue()); Assert.Equal("示例考试 · 示例学校考生报到情况及补录说明", publication["title"]?.GetValue()); Assert.Equal("计划 20 人,已报到 15 人,完成率 75%。", publication["summary"]?.GetValue()); Assert.True(publication["visible"]?.GetValue()); } private static AdminPublicationRecord Record(string id, string kind, string status, JsonObject payload) => new( id, kind, "exam-1", null, null, status, payload, "2026-06-01T00:00:00.000Z", "2026-06-02T00:00:00.000Z"); private static AdminNoticeManagementSnapshot Snapshot(IReadOnlyList records) => new( [], records, new Dictionary { ["exam-1"] = "示例考试" }, new Dictionary { ["school-1"] = "示例学校" }); }