116 lines
4.2 KiB
C#
116 lines
4.2 KiB
C#
using TheCr3w.Shared.Crypto;
|
|
using TheCr3w.Shared.Models;
|
|
using Xunit;
|
|
|
|
namespace TheCr3w.Tests;
|
|
|
|
public class CryptoTests
|
|
{
|
|
[Fact]
|
|
public void GenerateKeyPair_ShouldGenerateValidHexKeys()
|
|
{
|
|
var (privKey, pubKey) = Ed25519Service.GenerateKeyPair();
|
|
|
|
Assert.NotNull(privKey);
|
|
Assert.NotNull(pubKey);
|
|
Assert.Equal(64, privKey.Length); // 32 bytes seed in hex
|
|
Assert.Equal(64, pubKey.Length); // 32 bytes public key in hex
|
|
}
|
|
|
|
[Fact]
|
|
public void ReleaseMetadata_SignAndVerify_ShouldSucceedForValidData()
|
|
{
|
|
var (privKey, pubKey) = Ed25519Service.GenerateKeyPair();
|
|
|
|
var metadata = new ReleaseMetadata
|
|
{
|
|
ReleaseId = Guid.NewGuid(),
|
|
AppId = "com.thecr3w.app",
|
|
Version = "1.0.0",
|
|
VersionCode = 1,
|
|
Platform = "android",
|
|
Architecture = "arm64-v8a",
|
|
Channel = "stable",
|
|
Mandatory = false,
|
|
MinimumSupportedVersion = "1.0.0",
|
|
FileSize = 10485760,
|
|
Sha256 = "e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855",
|
|
PublishedAt = DateTimeOffset.UtcNow,
|
|
ReleaseNotes = "Wstępne wydanie"
|
|
};
|
|
|
|
var canonicalBytes = Ed25519Service.GetCanonicalBytes(metadata);
|
|
var signature = Ed25519Service.Sign(canonicalBytes, privKey);
|
|
|
|
Assert.NotNull(signature);
|
|
Assert.Equal(128, signature.Length);
|
|
|
|
var isValid = Ed25519Service.Verify(canonicalBytes, signature, pubKey);
|
|
Assert.True(isValid, "Podpis powinien być poprawny dla oryginalnych danych");
|
|
}
|
|
|
|
[Fact]
|
|
public void ReleaseMetadata_TamperingData_ShouldFailVerification()
|
|
{
|
|
var (privKey, pubKey) = Ed25519Service.GenerateKeyPair();
|
|
|
|
var metadata = new ReleaseMetadata
|
|
{
|
|
ReleaseId = Guid.NewGuid(),
|
|
AppId = "com.thecr3w.app",
|
|
Version = "1.0.0",
|
|
VersionCode = 1,
|
|
Platform = "android",
|
|
Architecture = "arm64-v8a",
|
|
Channel = "stable",
|
|
Mandatory = false,
|
|
MinimumSupportedVersion = "1.0.0",
|
|
FileSize = 10485760,
|
|
Sha256 = "e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855",
|
|
PublishedAt = DateTimeOffset.UtcNow,
|
|
ReleaseNotes = "Oryginał"
|
|
};
|
|
|
|
var canonicalBytes = Ed25519Service.GetCanonicalBytes(metadata);
|
|
var signature = Ed25519Service.Sign(canonicalBytes, privKey);
|
|
|
|
// Atak podmiany: Zmiana sumy SHA256 w pobranym pakiecie
|
|
metadata.Sha256 = "ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff";
|
|
var tamperedBytes = Ed25519Service.GetCanonicalBytes(metadata);
|
|
|
|
var isValid = Ed25519Service.Verify(tamperedBytes, signature, pubKey);
|
|
Assert.False(isValid, "Podpis NIE może przejść weryfikacji po zmodyfikowaniu danych");
|
|
}
|
|
|
|
[Fact]
|
|
public void DeploymentManifest_SignAndVerify_ShouldSucceed()
|
|
{
|
|
var (privKey, pubKey) = Ed25519Service.GenerateKeyPair();
|
|
|
|
var manifest = new DeploymentManifest
|
|
{
|
|
ManifestId = Guid.NewGuid(),
|
|
Project = "thecr3w-backend",
|
|
Environment = "production",
|
|
ServiceName = "backend",
|
|
Image = "git.thecr3wnet.com/thecr3w/backend",
|
|
ImmutableDigest = "sha256:7a59d8134bb8df389a9f24255198ec51787c9dc08269d7b420f1885b0d0ce0bf",
|
|
ConfigHash = "b5a2c96250612366ea8c2c10df6be0ab45e561398730707cdaed864537197f4f",
|
|
SecretsReferences = new() { "DB_PASSWORD", "KEYCLOAK_SECRET" },
|
|
RequiredMigrations = new() { "20261031_01_Init" },
|
|
CreatedAt = DateTimeOffset.UtcNow,
|
|
CreatedBy = "ci-bot"
|
|
};
|
|
|
|
var canonicalBytes = ManifestSigner.GetCanonicalBytes(manifest);
|
|
var signature = Ed25519Service.Sign(canonicalBytes, privKey);
|
|
manifest.SignatureEd25519 = signature;
|
|
|
|
var sha256 = ManifestSigner.ComputeManifestSha256(manifest);
|
|
Assert.NotNull(sha256);
|
|
Assert.Equal(64, sha256.Length);
|
|
|
|
var isValid = Ed25519Service.Verify(canonicalBytes, signature, pubKey);
|
|
Assert.True(isValid);
|
|
}
|
|
}
|