Skip to content

Commit 2dbe85c

Browse files
committed
Assemble package publication evidence
1 parent 04182ee commit 2dbe85c

5 files changed

Lines changed: 153 additions & 4 deletions

File tree

README.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -77,7 +77,7 @@ The first production milestone is M3UA over a transport abstraction. SCCP, TCAP,
7777
| Commercial evidence file verification | Phase 39 foundation-complete: retained file evidence item verification, retained file manifest coverage, file verification blocker reporting, retention ledger modeling, integrity sealing, publication attachment planning, verified promotion gating, command planning, status reporting, final validation, and documentation alignment are available, checking file existence, non-empty size, SHA-256 validity, digest match, UTC observation time, unique retained paths, promotion-required handoff coverage, explicit verification blockers, reviewer identity, immutable retention, UTC retention windows, minimum duration, deterministic aggregate ledger digests, sealed ledger attachment coverage, trace-bearing redaction approval, commercial readiness report presence, explicit promotion approval, workflow-ready verification command order, and readiness status separation; real retained file evidence remains required before commercial publication |
7878
| Commercial evidence filesystem execution | Phase 40 foundation-complete: filesystem observation, manifest execution, verification report execution, artifact writing, ledger execution, seal execution, publication attachment execution, promotion execution, command materialization, status reporting, documentation, and final validation are complete, reading retained files from disk, computing real SHA-256 digests, reporting file existence and size, supporting retained-path-to-local-path overrides, building retained file manifests from real observations, exposing blocker-aware retained file reports from filesystem evidence, writing retained Markdown/TSV verification artifacts, creating retention ledgers from filesystem-backed reports, sealing those ledgers with deterministic aggregate SHA-256 digests, creating release dossier attachments with redaction approval gates, evaluating reviewer-approved promotion gates, and writing ordered execution scripts; commercial publication still requires a real approved commercial run |
7979
| Approved commercial run publication handoff | Phase 41 foundation-complete: approved run target identity, approval checklist, reviewer approval manifest, approval report writing, promotion package, publication handoff, handoff gate, approval audit trail, command materialization, status reporting, documentation, and final validation are complete, binding package version, source commit, operator identity, UTC run timing, retained artifact root, filesystem-backed promotion execution, verified report, ready ledger/seal/attachments, redaction approval, promotion approval, release/security/operations reviewer approvals, UTC approval timestamps, checklist digest coverage, retained Markdown report output, report SHA-256 digest coverage, approved package references, requested publication channel, requester identity, UTC handoff time, explicit publish intent, channel version policy, handoff blocker reporting, digest-covered audit lifecycle events, and ordered approval workflow scripts; package publication still requires a real approved commercial run |
80-
| Commercial package publication gate integration | Phase 42 in progress: handoff-derived package publication request, digest-covered package artifact binding, and secret-name based credential readiness are available, binding package version, channel, requester identity, run id, promotion package id, UTC request time, nupkg/snupkg paths, retained sizes, SHA-256 digests, version-matched paths, package integrity manifest projection, NuGet API key presence, signing secret presence, missing-secret reporting, and UTC credential evaluation; package publication remains blocked until evidence assembly, release guard, channel policy, gate execution, dry-run rehearsal, guarded commands, and status reporting are complete |
80+
| Commercial package publication gate integration | Phase 42 in progress: handoff-derived package publication request, digest-covered package artifact binding, secret-name based credential readiness, and publication evidence assembly are available, binding package version, channel, requester identity, run id, promotion package id, UTC request time, nupkg/snupkg paths, retained sizes, SHA-256 digests, version-matched paths, package integrity manifest projection, NuGet API key presence, signing secret presence, missing-secret reporting, UTC credential evaluation, supply-chain readiness, commercial evidence readiness, and final publication evidence manifest output; package publication remains blocked until release guard, channel policy, gate execution, dry-run rehearsal, guarded commands, and status reporting are complete |
8181

8282
## Requirements
8383

docs/PHASE42_COMMERCIAL_PACKAGE_PUBLICATION_GATE_INTEGRATION.md

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,7 @@ Phase 42 connects an approved commercial evidence publication handoff to the pac
99
| 1 | Package publication request derived from approved handoff gate | Complete |
1010
| 2 | Package artifact binding with package and symbols digests | Complete |
1111
| 3 | Credential readiness bridge for required publication secrets | Complete |
12-
| 4 | Publication evidence assembly from approved run and artifacts | Pending |
12+
| 4 | Publication evidence assembly from approved run and artifacts | Complete |
1313
| 5 | Release publish guard bridge | Pending |
1414
| 6 | Publication channel policy evaluation bridge | Pending |
1515
| 7 | Commercial package publication gate execution | Pending |
@@ -27,6 +27,8 @@ The request can only move to package artifact binding when the upstream handoff
2727

2828
`SigtranPackagePublicationCredentialReadiness` evaluates required publication credentials by secret name only. It uses the default NuGet publication credential policy, reports missing secret names, tracks NuGet API key and signing secret availability, and requires a UTC evaluation time before moving into evidence assembly.
2929

30+
`SigtranPackagePublicationEvidenceAssembly` creates the publication gate evidence manifest from credential readiness, package integrity, supply-chain promotion readiness, and approved commercial evidence readiness. It reuses the existing `SigtranPublicationEvidenceManifest` contract so the final package publication gate receives the same evidence shape as earlier release foundations.
31+
3032
## Commercial Gate Position
3133

32-
Phase 42 is still in progress. Units 1 through 3 establish the handoff-to-publication request boundary, digest-covered package artifact binding, and secret-name based credential readiness. Real package publication remains blocked until retained evidence, release guard, channel policy, and the final publication gate all pass.
34+
Phase 42 is still in progress. Units 1 through 4 establish the handoff-to-publication request boundary, digest-covered package artifact binding, secret-name based credential readiness, and publication evidence assembly. Real package publication remains blocked until release guard, channel policy, and the final publication gate all pass.

docs/PHASE42_SUMMARY.md

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,8 @@ Phase 42 is in progress. It connects approved commercial evidence handoff record
77
- Package publication request that derives package version, channel, requester identity, run id, promotion package id, UTC request time, and artifact-binding readiness from an approved handoff gate.
88
- Package publication artifact set that binds the request to nupkg/snupkg paths, retained sizes, SHA-256 digests, requested package version matching, and the existing package integrity manifest.
99
- Package publication credential readiness that evaluates NuGet and signing secret availability by secret name without storing secret values.
10+
- Package publication evidence assembly that creates the final publication evidence manifest from package integrity, supply-chain readiness, and approved commercial evidence readiness.
1011

1112
## Readiness Position
1213

13-
Units 1 through 3 are complete. The SDK can now represent the publication request boundary after commercial approval handoff, bind digest-covered package artifacts to that request, and gate the next step on required publication secret names. Package publication still requires evidence assembly, release guard evaluation, channel policy evaluation, final gate execution, dry-run rehearsal, guarded command materialization, status reporting, and retained real release evidence.
14+
Units 1 through 4 are complete. The SDK can now represent the publication request boundary after commercial approval handoff, bind digest-covered package artifacts to that request, gate the next step on required publication secret names, and assemble the publication evidence manifest. Package publication still requires release guard evaluation, channel policy evaluation, final gate execution, dry-run rehearsal, guarded command materialization, status reporting, and retained real release evidence.

src/Sigtran.NET.Tests/Program.cs

Lines changed: 50 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -325,6 +325,7 @@
325325
Run("SIGTRAN package publication request derives from approved handoff", SigtranPackagePublicationRequestDerivesFromApprovedHandoff);
326326
Run("SIGTRAN package publication artifacts bind package and symbols digests", SigtranPackagePublicationArtifactsBindPackageAndSymbolsDigests);
327327
Run("SIGTRAN package publication credential readiness gates required secrets", SigtranPackagePublicationCredentialReadinessGatesRequiredSecrets);
328+
Run("SIGTRAN package publication evidence assembly creates gate manifest", SigtranPackagePublicationEvidenceAssemblyCreatesGateManifest);
328329
Run("SIGTRAN commercial evidence approval audit trail covers lifecycle", SigtranCommercialEvidenceApprovalAuditTrailCoversLifecycle);
329330
Run("SIGTRAN commercial evidence approval command materializer writes script", SigtranCommercialEvidenceApprovalCommandMaterializerWritesScript);
330331
Run("SIGTRAN commercial evidence approval handoff status summarizes final validation", SigtranCommercialEvidenceApprovalHandoffStatusSummarizesFinalValidation);
@@ -5821,6 +5822,42 @@ static void SigtranPackagePublicationCredentialReadinessGatesRequiredSecrets()
58215822
}
58225823
}
58235824

5825+
static void SigtranPackagePublicationEvidenceAssemblyCreatesGateManifest()
5826+
{
5827+
string tempRoot = Path.Combine(Path.GetTempPath(), "sigtran-commercial-evidence-" + Guid.NewGuid().ToString("N"));
5828+
Directory.CreateDirectory(tempRoot);
5829+
5830+
try
5831+
{
5832+
SigtranPackagePublicationCredentialReadiness credentials = CreateReadyPackagePublicationCredentialReadiness(tempRoot);
5833+
5834+
SigtranPackagePublicationEvidenceAssembly ready = SigtranPackagePublicationEvidenceAssemblies.Assemble(
5835+
credentials,
5836+
supplyChainPromotionReady: true,
5837+
commercialEvidenceReady: true,
5838+
DateTimeOffset.UtcNow);
5839+
SigtranPackagePublicationEvidenceAssembly blocked = SigtranPackagePublicationEvidenceAssemblies.Assemble(
5840+
credentials,
5841+
supplyChainPromotionReady: false,
5842+
commercialEvidenceReady: true,
5843+
DateTimeOffset.UtcNow);
5844+
5845+
Assert(ready.IsReadyForPublishGuard, ready.Describe());
5846+
Assert(ready.PackageIntegrityReady, "publication evidence assembly should include package integrity");
5847+
Assert(ready.SupplyChainPromotionReady, "publication evidence assembly should include supply-chain promotion evidence");
5848+
Assert(ready.CommercialEvidenceReady, "publication evidence assembly should include approved commercial evidence");
5849+
Assert(ready.EvidenceManifest.IsComplete, "publication evidence manifest should be complete");
5850+
AssertEqual("1.0.0-rc.1", ready.EvidenceManifest.Version, "publication evidence package version");
5851+
AssertEqual(SigtranPublishChannelKind.Beta, ready.EvidenceManifest.Channel, "publication evidence channel");
5852+
Assert(!blocked.IsReadyForPublishGuard, "missing supply-chain evidence should block publish guard readiness");
5853+
Assert(!blocked.EvidenceManifest.IsComplete, "blocked publication evidence manifest should be incomplete");
5854+
}
5855+
finally
5856+
{
5857+
DeleteTempEvidenceRoot(tempRoot);
5858+
}
5859+
}
5860+
58245861
static void SigtranCommercialEvidenceApprovalAuditTrailCoversLifecycle()
58255862
{
58265863
string tempRoot = Path.Combine(Path.GetTempPath(), "sigtran-commercial-evidence-" + Guid.NewGuid().ToString("N"));
@@ -5923,6 +5960,19 @@ static SigtranPackagePublicationArtifactSet CreateReadyPackagePublicationArtifac
59235960
]);
59245961
}
59255962

5963+
static SigtranPackagePublicationCredentialReadiness CreateReadyPackagePublicationCredentialReadiness(string tempRoot)
5964+
{
5965+
return SigtranPackagePublicationCredentialReadinessEvaluator.EvaluateDefault(
5966+
CreateReadyPackagePublicationArtifactSet(CreateReadyPackagePublicationRequest(tempRoot)),
5967+
new HashSet<string>(StringComparer.Ordinal)
5968+
{
5969+
"NUGET_API_KEY",
5970+
"SIGNING_CERTIFICATE",
5971+
"SIGNING_CERTIFICATE_PASSWORD"
5972+
},
5973+
DateTimeOffset.UtcNow);
5974+
}
5975+
59265976
static SigtranCommercialEvidenceApprovedRunPromotionPackage CreateReadyCommercialEvidenceApprovedRunPromotionPackage(string tempRoot)
59275977
{
59285978
return SigtranCommercialEvidenceApprovedRunPromotionPackages.CreateDefault(
Lines changed: 96 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,96 @@
1+
namespace Sigtran.NET.Core.Utilities;
2+
3+
/// <summary>
4+
/// Describes assembled package publication evidence for gate evaluation.
5+
/// </summary>
6+
public sealed class SigtranPackagePublicationEvidenceAssembly
7+
{
8+
/// <summary>Creates an assembled package publication evidence result.</summary>
9+
/// <param name="credentialReadiness">The package publication credential readiness.</param>
10+
/// <param name="integrityManifest">The package integrity manifest.</param>
11+
/// <param name="evidenceManifest">The publication evidence manifest.</param>
12+
/// <param name="assembledAtUtc">The UTC assembly time.</param>
13+
public SigtranPackagePublicationEvidenceAssembly(
14+
SigtranPackagePublicationCredentialReadiness credentialReadiness,
15+
SigtranPackageIntegrityManifest integrityManifest,
16+
SigtranPublicationEvidenceManifest evidenceManifest,
17+
DateTimeOffset assembledAtUtc)
18+
{
19+
CredentialReadiness = credentialReadiness ?? throw new ArgumentNullException(nameof(credentialReadiness));
20+
IntegrityManifest = integrityManifest ?? throw new ArgumentNullException(nameof(integrityManifest));
21+
EvidenceManifest = evidenceManifest ?? throw new ArgumentNullException(nameof(evidenceManifest));
22+
AssembledAtUtc = assembledAtUtc.Offset == TimeSpan.Zero ? assembledAtUtc : assembledAtUtc.ToUniversalTime();
23+
}
24+
25+
/// <summary>The package publication credential readiness.</summary>
26+
public SigtranPackagePublicationCredentialReadiness CredentialReadiness { get; }
27+
28+
/// <summary>The package integrity manifest.</summary>
29+
public SigtranPackageIntegrityManifest IntegrityManifest { get; }
30+
31+
/// <summary>The publication evidence manifest.</summary>
32+
public SigtranPublicationEvidenceManifest EvidenceManifest { get; }
33+
34+
/// <summary>The UTC assembly time.</summary>
35+
public DateTimeOffset AssembledAtUtc { get; }
36+
37+
/// <summary>Whether the assembly time is normalized to UTC.</summary>
38+
public bool HasUtcAssemblyTime => AssembledAtUtc.Offset == TimeSpan.Zero;
39+
40+
/// <summary>Whether package integrity evidence is complete.</summary>
41+
public bool PackageIntegrityReady => IntegrityManifest.IsComplete
42+
&& EvidenceManifest.PackageIntegrityComplete;
43+
44+
/// <summary>Whether supply-chain promotion evidence is complete.</summary>
45+
public bool SupplyChainPromotionReady => EvidenceManifest.SupplyChainPromotionReady;
46+
47+
/// <summary>Whether commercial evidence is complete.</summary>
48+
public bool CommercialEvidenceReady => EvidenceManifest.CommercialEvidenceReady;
49+
50+
/// <summary>Whether assembled evidence can move into release publish guard evaluation.</summary>
51+
public bool IsReadyForPublishGuard => CredentialReadiness.IsReadyForEvidenceAssembly
52+
&& EvidenceManifest.IsComplete
53+
&& HasUtcAssemblyTime;
54+
55+
/// <summary>Formats a compact package publication evidence assembly summary.</summary>
56+
/// <returns>The package publication evidence assembly summary.</returns>
57+
public string Describe()
58+
{
59+
return $"packagePublicationEvidenceReady={IsReadyForPublishGuard} integrity={PackageIntegrityReady} supplyChain={SupplyChainPromotionReady} commercialEvidence={CommercialEvidenceReady}";
60+
}
61+
}
62+
63+
/// <summary>
64+
/// Provides package publication evidence assembly helpers.
65+
/// </summary>
66+
public static class SigtranPackagePublicationEvidenceAssemblies
67+
{
68+
/// <summary>Assembles package publication evidence from credential readiness and retained evidence gates.</summary>
69+
/// <param name="credentialReadiness">The package publication credential readiness.</param>
70+
/// <param name="supplyChainPromotionReady">Whether supply-chain promotion evidence is ready.</param>
71+
/// <param name="commercialEvidenceReady">Whether commercial evidence is ready.</param>
72+
/// <param name="assembledAtUtc">The UTC assembly time.</param>
73+
/// <returns>The package publication evidence assembly.</returns>
74+
public static SigtranPackagePublicationEvidenceAssembly Assemble(
75+
SigtranPackagePublicationCredentialReadiness credentialReadiness,
76+
bool supplyChainPromotionReady,
77+
bool commercialEvidenceReady,
78+
DateTimeOffset assembledAtUtc)
79+
{
80+
ArgumentNullException.ThrowIfNull(credentialReadiness);
81+
SigtranPackageIntegrityManifest integrityManifest = credentialReadiness.ArtifactSet.ToIntegrityManifest();
82+
bool packageIntegrityComplete = credentialReadiness.ArtifactSet.IsReadyForCredentialEvaluation
83+
&& integrityManifest.IsComplete;
84+
bool approvedCommercialEvidenceReady = credentialReadiness.ArtifactSet.Request.HandoffGateAllowsPackageEvaluation
85+
&& commercialEvidenceReady;
86+
87+
SigtranPublicationEvidenceManifest evidenceManifest = new(
88+
credentialReadiness.ArtifactSet.Request.PackageVersion,
89+
credentialReadiness.ArtifactSet.Request.Channel.Kind,
90+
packageIntegrityComplete,
91+
supplyChainPromotionReady,
92+
approvedCommercialEvidenceReady);
93+
94+
return new(credentialReadiness, integrityManifest, evidenceManifest, assembledAtUtc);
95+
}
96+
}

0 commit comments

Comments
 (0)