Add unit tests for RabbitMq and Udp transport servers and clients
Some checks failed
Docs CI / lint-and-preview (push) Has been cancelled

- Implemented comprehensive unit tests for RabbitMqTransportServer, covering constructor, disposal, connection management, event handlers, and exception handling.
- Added configuration tests for RabbitMqTransportServer to validate SSL, durable queues, auto-recovery, and custom virtual host options.
- Created unit tests for UdpFrameProtocol, including frame parsing and serialization, header size validation, and round-trip data preservation.
- Developed tests for UdpTransportClient, focusing on connection handling, event subscriptions, and exception scenarios.
- Established tests for UdpTransportServer, ensuring proper start/stop behavior, connection state management, and event handling.
- Included tests for UdpTransportOptions to verify default values and modification capabilities.
- Enhanced service registration tests for Udp transport services in the dependency injection container.
This commit is contained in:
master
2025-12-05 19:01:12 +02:00
parent 53508ceccb
commit cc69d332e3
245 changed files with 22440 additions and 27719 deletions

View File

@@ -0,0 +1,252 @@
namespace StellaOps.Cryptography;
/// <summary>
/// Built-in compliance profiles for different jurisdictional crypto requirements.
/// </summary>
public static class ComplianceProfiles
{
/// <summary>
/// Default/World profile using BLAKE3 for graph hashing, SHA-256 for everything else.
/// Suitable for international deployments without specific compliance requirements.
/// </summary>
public static readonly ComplianceProfile World = new()
{
ProfileId = "world",
StandardName = "ISO/Default",
Description = "Default profile using BLAKE3 for graph content-addressing, SHA-256 for symbol/content hashing.",
PurposeAlgorithms = new Dictionary<string, string>
{
[HashPurpose.Graph] = HashAlgorithms.Blake3_256,
[HashPurpose.Symbol] = HashAlgorithms.Sha256,
[HashPurpose.Content] = HashAlgorithms.Sha256,
[HashPurpose.Merkle] = HashAlgorithms.Sha256,
[HashPurpose.Attestation] = HashAlgorithms.Sha256,
[HashPurpose.Interop] = HashAlgorithms.Sha256,
[HashPurpose.Secret] = PasswordHashAlgorithms.Argon2id,
},
HashPrefixes = new Dictionary<string, string>
{
[HashPurpose.Graph] = "blake3:",
[HashPurpose.Symbol] = "sha256:",
[HashPurpose.Content] = "sha256:",
[HashPurpose.Merkle] = "sha256:",
[HashPurpose.Attestation] = "sha256:",
[HashPurpose.Interop] = "sha256:",
[HashPurpose.Secret] = "argon2id:",
},
AllowInteropOverride = true,
};
/// <summary>
/// FIPS 140-3 (US Federal) compliance profile.
/// Uses only FIPS-approved algorithms: SHA-256, SHA-384, SHA-512, PBKDF2.
/// Note: BLAKE3 is not FIPS-approved, so SHA-256 is used for graph hashing.
/// </summary>
public static readonly ComplianceProfile Fips = new()
{
ProfileId = "fips",
StandardName = "FIPS 140-3",
Description = "US Federal Information Processing Standard 140-3. Uses only FIPS-approved algorithms.",
PurposeAlgorithms = new Dictionary<string, string>
{
[HashPurpose.Graph] = HashAlgorithms.Sha256, // BLAKE3 not FIPS-approved
[HashPurpose.Symbol] = HashAlgorithms.Sha256,
[HashPurpose.Content] = HashAlgorithms.Sha256,
[HashPurpose.Merkle] = HashAlgorithms.Sha256,
[HashPurpose.Attestation] = HashAlgorithms.Sha256,
[HashPurpose.Interop] = HashAlgorithms.Sha256,
[HashPurpose.Secret] = PasswordHashAlgorithms.Pbkdf2Sha256,
},
HashPrefixes = new Dictionary<string, string>
{
[HashPurpose.Graph] = "sha256:",
[HashPurpose.Symbol] = "sha256:",
[HashPurpose.Content] = "sha256:",
[HashPurpose.Merkle] = "sha256:",
[HashPurpose.Attestation] = "sha256:",
[HashPurpose.Interop] = "sha256:",
[HashPurpose.Secret] = "pbkdf2:",
},
AllowInteropOverride = true,
};
/// <summary>
/// GOST R 34.11-2012 (Russian) compliance profile.
/// Uses GOST Stribog hash for all purposes except Interop (which remains SHA-256 for external compatibility).
/// </summary>
public static readonly ComplianceProfile Gost = new()
{
ProfileId = "gost",
StandardName = "GOST R 34.11-2012",
Description = "Russian GOST R 34.11-2012 (Stribog) hash standard. Interop uses SHA-256 for external tool compatibility.",
PurposeAlgorithms = new Dictionary<string, string>
{
[HashPurpose.Graph] = HashAlgorithms.Gost3411_2012_256,
[HashPurpose.Symbol] = HashAlgorithms.Gost3411_2012_256,
[HashPurpose.Content] = HashAlgorithms.Gost3411_2012_256,
[HashPurpose.Merkle] = HashAlgorithms.Gost3411_2012_256,
[HashPurpose.Attestation] = HashAlgorithms.Gost3411_2012_256,
[HashPurpose.Interop] = HashAlgorithms.Sha256, // Override for external compatibility
[HashPurpose.Secret] = PasswordHashAlgorithms.Argon2id,
},
HashPrefixes = new Dictionary<string, string>
{
[HashPurpose.Graph] = "gost3411:",
[HashPurpose.Symbol] = "gost3411:",
[HashPurpose.Content] = "gost3411:",
[HashPurpose.Merkle] = "gost3411:",
[HashPurpose.Attestation] = "gost3411:",
[HashPurpose.Interop] = "sha256:",
[HashPurpose.Secret] = "argon2id:",
},
AllowInteropOverride = true,
};
/// <summary>
/// GB/T SM3 (Chinese) compliance profile.
/// Uses SM3 hash for all purposes except Interop (which remains SHA-256 for external compatibility).
/// </summary>
public static readonly ComplianceProfile Sm = new()
{
ProfileId = "sm",
StandardName = "GB/T (SM3)",
Description = "Chinese GB/T 32905-2016 SM3 cryptographic hash standard. Interop uses SHA-256 for external tool compatibility.",
PurposeAlgorithms = new Dictionary<string, string>
{
[HashPurpose.Graph] = HashAlgorithms.Sm3,
[HashPurpose.Symbol] = HashAlgorithms.Sm3,
[HashPurpose.Content] = HashAlgorithms.Sm3,
[HashPurpose.Merkle] = HashAlgorithms.Sm3,
[HashPurpose.Attestation] = HashAlgorithms.Sm3,
[HashPurpose.Interop] = HashAlgorithms.Sha256, // Override for external compatibility
[HashPurpose.Secret] = PasswordHashAlgorithms.Argon2id,
},
HashPrefixes = new Dictionary<string, string>
{
[HashPurpose.Graph] = "sm3:",
[HashPurpose.Symbol] = "sm3:",
[HashPurpose.Content] = "sm3:",
[HashPurpose.Merkle] = "sm3:",
[HashPurpose.Attestation] = "sm3:",
[HashPurpose.Interop] = "sha256:",
[HashPurpose.Secret] = "argon2id:",
},
AllowInteropOverride = true,
};
/// <summary>
/// KCMVP (Korea Cryptographic Module Validation Program) compliance profile.
/// Uses SHA-256 for hashing. Note: ARIA/SEED/LEA are for encryption, KCDSA for signatures.
/// </summary>
public static readonly ComplianceProfile Kcmvp = new()
{
ProfileId = "kcmvp",
StandardName = "KCMVP (Korea)",
Description = "Korea Cryptographic Module Validation Program. Uses SHA-256 for hashing.",
PurposeAlgorithms = new Dictionary<string, string>
{
[HashPurpose.Graph] = HashAlgorithms.Sha256,
[HashPurpose.Symbol] = HashAlgorithms.Sha256,
[HashPurpose.Content] = HashAlgorithms.Sha256,
[HashPurpose.Merkle] = HashAlgorithms.Sha256,
[HashPurpose.Attestation] = HashAlgorithms.Sha256,
[HashPurpose.Interop] = HashAlgorithms.Sha256,
[HashPurpose.Secret] = PasswordHashAlgorithms.Argon2id,
},
HashPrefixes = new Dictionary<string, string>
{
[HashPurpose.Graph] = "sha256:",
[HashPurpose.Symbol] = "sha256:",
[HashPurpose.Content] = "sha256:",
[HashPurpose.Merkle] = "sha256:",
[HashPurpose.Attestation] = "sha256:",
[HashPurpose.Interop] = "sha256:",
[HashPurpose.Secret] = "argon2id:",
},
AllowInteropOverride = true,
};
/// <summary>
/// eIDAS/ETSI TS 119 312 (European) compliance profile.
/// Uses SHA-256 for hashing per ETSI cryptographic suites specification.
/// </summary>
public static readonly ComplianceProfile Eidas = new()
{
ProfileId = "eidas",
StandardName = "eIDAS/ETSI TS 119 312",
Description = "European eIDAS regulation with ETSI TS 119 312 cryptographic suites. Uses SHA-256/384 for hashing.",
PurposeAlgorithms = new Dictionary<string, string>
{
[HashPurpose.Graph] = HashAlgorithms.Sha256,
[HashPurpose.Symbol] = HashAlgorithms.Sha256,
[HashPurpose.Content] = HashAlgorithms.Sha256,
[HashPurpose.Merkle] = HashAlgorithms.Sha256,
[HashPurpose.Attestation] = HashAlgorithms.Sha256,
[HashPurpose.Interop] = HashAlgorithms.Sha256,
[HashPurpose.Secret] = PasswordHashAlgorithms.Argon2id,
},
HashPrefixes = new Dictionary<string, string>
{
[HashPurpose.Graph] = "sha256:",
[HashPurpose.Symbol] = "sha256:",
[HashPurpose.Content] = "sha256:",
[HashPurpose.Merkle] = "sha256:",
[HashPurpose.Attestation] = "sha256:",
[HashPurpose.Interop] = "sha256:",
[HashPurpose.Secret] = "argon2id:",
},
AllowInteropOverride = true,
};
/// <summary>
/// All built-in profiles indexed by profile ID.
/// </summary>
public static readonly IReadOnlyDictionary<string, ComplianceProfile> All =
new Dictionary<string, ComplianceProfile>(StringComparer.OrdinalIgnoreCase)
{
[World.ProfileId] = World,
[Fips.ProfileId] = Fips,
[Gost.ProfileId] = Gost,
[Sm.ProfileId] = Sm,
[Kcmvp.ProfileId] = Kcmvp,
[Eidas.ProfileId] = Eidas,
};
/// <summary>
/// Gets a profile by ID, returning the World profile if not found.
/// </summary>
/// <param name="profileId">The profile ID to look up.</param>
/// <returns>The matching profile, or World if not found.</returns>
public static ComplianceProfile GetProfile(string? profileId)
{
if (string.IsNullOrWhiteSpace(profileId))
{
return World;
}
return All.TryGetValue(profileId, out var profile) ? profile : World;
}
/// <summary>
/// Gets a profile by ID, throwing if not found.
/// </summary>
/// <param name="profileId">The profile ID to look up.</param>
/// <returns>The matching profile.</returns>
/// <exception cref="ArgumentException">Thrown when the profile ID is not found.</exception>
public static ComplianceProfile GetProfileOrThrow(string profileId)
{
if (string.IsNullOrWhiteSpace(profileId))
{
throw new ArgumentException("Profile ID cannot be null or empty.", nameof(profileId));
}
if (!All.TryGetValue(profileId, out var profile))
{
throw new ArgumentException(
$"Unknown compliance profile '{profileId}'. Valid profiles: {string.Join(", ", All.Keys)}",
nameof(profileId));
}
return profile;
}
}