- Added IIssuerDirectory interface for managing VEX document issuers, including methods for registration, revocation, and trust validation. - Created InMemoryIssuerDirectory class as an in-memory implementation of IIssuerDirectory for testing and single-instance deployments. - Introduced ISignatureVerifier interface for verifying signatures on VEX documents, with support for multiple signature formats. - Developed SignatureVerifier class as the default implementation of ISignatureVerifier, allowing extensibility for different signature formats. - Implemented handlers for DSSE and JWS signature formats, including methods for verification and signature extraction. - Defined various records and enums for issuer and signature metadata, enhancing the structure and clarity of the verification process.
87 lines
2.8 KiB
C#
87 lines
2.8 KiB
C#
using System.Collections.Concurrent;
|
|
|
|
namespace StellaOps.Policy.Engine.Attestation;
|
|
|
|
/// <summary>
|
|
/// In-memory implementation of verification policy store per CONTRACT-VERIFICATION-POLICY-006.
|
|
/// </summary>
|
|
internal sealed class InMemoryVerificationPolicyStore : IVerificationPolicyStore
|
|
{
|
|
private readonly ConcurrentDictionary<string, VerificationPolicy> _policies = new(StringComparer.OrdinalIgnoreCase);
|
|
|
|
public Task<VerificationPolicy?> GetAsync(string policyId, CancellationToken cancellationToken = default)
|
|
{
|
|
ArgumentException.ThrowIfNullOrWhiteSpace(policyId);
|
|
|
|
_policies.TryGetValue(policyId, out var policy);
|
|
return Task.FromResult(policy);
|
|
}
|
|
|
|
public Task<IReadOnlyList<VerificationPolicy>> ListAsync(
|
|
string? tenantScope = null,
|
|
CancellationToken cancellationToken = default)
|
|
{
|
|
IEnumerable<VerificationPolicy> policies = _policies.Values;
|
|
|
|
if (!string.IsNullOrWhiteSpace(tenantScope))
|
|
{
|
|
policies = policies.Where(p =>
|
|
p.TenantScope == "*" ||
|
|
p.TenantScope.Equals(tenantScope, StringComparison.OrdinalIgnoreCase));
|
|
}
|
|
|
|
var result = policies
|
|
.OrderBy(p => p.PolicyId)
|
|
.ToList() as IReadOnlyList<VerificationPolicy>;
|
|
|
|
return Task.FromResult(result);
|
|
}
|
|
|
|
public Task<VerificationPolicy> CreateAsync(
|
|
VerificationPolicy policy,
|
|
CancellationToken cancellationToken = default)
|
|
{
|
|
ArgumentNullException.ThrowIfNull(policy);
|
|
|
|
if (!_policies.TryAdd(policy.PolicyId, policy))
|
|
{
|
|
throw new InvalidOperationException($"Policy '{policy.PolicyId}' already exists.");
|
|
}
|
|
|
|
return Task.FromResult(policy);
|
|
}
|
|
|
|
public Task<VerificationPolicy?> UpdateAsync(
|
|
string policyId,
|
|
Func<VerificationPolicy, VerificationPolicy> update,
|
|
CancellationToken cancellationToken = default)
|
|
{
|
|
ArgumentException.ThrowIfNullOrWhiteSpace(policyId);
|
|
ArgumentNullException.ThrowIfNull(update);
|
|
|
|
if (!_policies.TryGetValue(policyId, out var existing))
|
|
{
|
|
return Task.FromResult<VerificationPolicy?>(null);
|
|
}
|
|
|
|
var updated = update(existing);
|
|
_policies[policyId] = updated;
|
|
|
|
return Task.FromResult<VerificationPolicy?>(updated);
|
|
}
|
|
|
|
public Task<bool> DeleteAsync(string policyId, CancellationToken cancellationToken = default)
|
|
{
|
|
ArgumentException.ThrowIfNullOrWhiteSpace(policyId);
|
|
|
|
return Task.FromResult(_policies.TryRemove(policyId, out _));
|
|
}
|
|
|
|
public Task<bool> ExistsAsync(string policyId, CancellationToken cancellationToken = default)
|
|
{
|
|
ArgumentException.ThrowIfNullOrWhiteSpace(policyId);
|
|
|
|
return Task.FromResult(_policies.ContainsKey(policyId));
|
|
}
|
|
}
|