Implement ledger metrics for observability and add tests for Ruby packages endpoints
Some checks failed
Docs CI / lint-and-preview (push) Has been cancelled
Some checks failed
Docs CI / lint-and-preview (push) Has been cancelled
- Added `LedgerMetrics` class to record write latency and total events for ledger operations. - Created comprehensive tests for Ruby packages endpoints, covering scenarios for missing inventory, successful retrieval, and identifier handling. - Introduced `TestSurfaceSecretsScope` for managing environment variables during tests. - Developed `ProvenanceMongoExtensions` for attaching DSSE provenance and trust information to event documents. - Implemented `EventProvenanceWriter` and `EventWriter` classes for managing event provenance in MongoDB. - Established MongoDB indexes for efficient querying of events based on provenance and trust. - Added models and JSON parsing logic for DSSE provenance and trust information.
This commit is contained in:
@@ -0,0 +1,142 @@
|
||||
using MongoDB.Bson;
|
||||
|
||||
namespace StellaOps.Provenance.Mongo;
|
||||
|
||||
public static class ProvenanceMongoExtensions
|
||||
{
|
||||
private const string ProvenanceFieldName = "provenance";
|
||||
private const string DsseFieldName = "dsse";
|
||||
private const string TrustFieldName = "trust";
|
||||
private const string ChainFieldName = "chain";
|
||||
private static BsonValue StringOrNull(string? value) =>
|
||||
value is null ? BsonNull.Value : new BsonString(value);
|
||||
|
||||
/// <summary>
|
||||
/// Attach DSSE provenance + trust info to an event document in-place.
|
||||
/// Designed for generic BsonDocument-based event envelopes.
|
||||
/// </summary>
|
||||
public static BsonDocument AttachDsseProvenance(
|
||||
this BsonDocument eventDoc,
|
||||
DsseProvenance dsse,
|
||||
TrustInfo trust)
|
||||
{
|
||||
if (eventDoc is null) throw new ArgumentNullException(nameof(eventDoc));
|
||||
if (dsse is null) throw new ArgumentNullException(nameof(dsse));
|
||||
if (trust is null) throw new ArgumentNullException(nameof(trust));
|
||||
|
||||
var dsseDoc = new BsonDocument
|
||||
{
|
||||
{ "envelopeDigest", dsse.EnvelopeDigest },
|
||||
{ "payloadType", dsse.PayloadType },
|
||||
{ "key", new BsonDocument
|
||||
{
|
||||
{ "keyId", dsse.Key.KeyId },
|
||||
{ "issuer", StringOrNull(dsse.Key.Issuer) },
|
||||
{ "algo", StringOrNull(dsse.Key.Algo) }
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
if (dsse.Rekor is not null)
|
||||
{
|
||||
var rekorDoc = new BsonDocument
|
||||
{
|
||||
{ "logIndex", dsse.Rekor.LogIndex },
|
||||
{ "uuid", dsse.Rekor.Uuid }
|
||||
};
|
||||
|
||||
if (dsse.Rekor.IntegratedTime is not null)
|
||||
rekorDoc.Add("integratedTime", dsse.Rekor.IntegratedTime);
|
||||
|
||||
if (dsse.Rekor.MirrorSeq is not null)
|
||||
rekorDoc.Add("mirrorSeq", dsse.Rekor.MirrorSeq);
|
||||
|
||||
dsseDoc.Add("rekor", rekorDoc);
|
||||
}
|
||||
|
||||
if (dsse.Chain is not null && dsse.Chain.Count > 0)
|
||||
{
|
||||
var chainArray = new BsonArray();
|
||||
foreach (var link in dsse.Chain)
|
||||
{
|
||||
chainArray.Add(new BsonDocument
|
||||
{
|
||||
{ "type", link.Type },
|
||||
{ "id", link.Id },
|
||||
{ "digest", link.Digest }
|
||||
});
|
||||
}
|
||||
|
||||
dsseDoc.Add(ChainFieldName, chainArray);
|
||||
}
|
||||
|
||||
var trustDoc = new BsonDocument
|
||||
{
|
||||
{ "verified", trust.Verified },
|
||||
{ "verifier", StringOrNull(trust.Verifier) }
|
||||
};
|
||||
|
||||
if (trust.Witnesses is not null)
|
||||
trustDoc.Add("witnesses", trust.Witnesses);
|
||||
|
||||
if (trust.PolicyScore is not null)
|
||||
trustDoc.Add("policyScore", trust.PolicyScore);
|
||||
|
||||
var provenanceDoc = new BsonDocument
|
||||
{
|
||||
{ DsseFieldName, dsseDoc }
|
||||
};
|
||||
|
||||
eventDoc[ProvenanceFieldName] = provenanceDoc;
|
||||
eventDoc[TrustFieldName] = trustDoc;
|
||||
|
||||
return eventDoc;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Helper to query for "cryptographically proven" events:
|
||||
/// kind + subject.digest.sha256 + presence of Rekor logIndex + trust.verified = true.
|
||||
/// </summary>
|
||||
public static BsonDocument BuildProvenVexFilter(
|
||||
string kind,
|
||||
string subjectDigestSha256)
|
||||
{
|
||||
return new BsonDocument
|
||||
{
|
||||
{ "kind", kind },
|
||||
{ "subject.digest.sha256", subjectDigestSha256 },
|
||||
{ $"{ProvenanceFieldName}.{DsseFieldName}.rekor.logIndex", new BsonDocument("$exists", true) },
|
||||
{ $"{TrustFieldName}.verified", true }
|
||||
};
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Helper to query for events influencing policy without solid provenance.
|
||||
/// </summary>
|
||||
public static BsonDocument BuildUnprovenEvidenceFilter(
|
||||
IEnumerable<string> kinds)
|
||||
{
|
||||
var kindsArray = new BsonArray(kinds);
|
||||
|
||||
return new BsonDocument
|
||||
{
|
||||
{
|
||||
"kind", new BsonDocument("$in", kindsArray)
|
||||
},
|
||||
{
|
||||
"$or", new BsonArray
|
||||
{
|
||||
new BsonDocument
|
||||
{
|
||||
{ $"{TrustFieldName}.verified", new BsonDocument("$ne", true) }
|
||||
},
|
||||
new BsonDocument
|
||||
{
|
||||
{ $"{ProvenanceFieldName}.{DsseFieldName}.rekor.logIndex",
|
||||
new BsonDocument("$exists", false) }
|
||||
}
|
||||
}
|
||||
}
|
||||
};
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user