using System.Linq; using StellaOps.Feedser.Models; namespace StellaOps.Feedser.Models.Tests; public sealed class AdvisoryTests { [Fact] public void CanonicalizesAliasesAndReferences() { var advisory = new Advisory( advisoryKey: "TEST-123", title: "Sample Advisory", summary: " summary with spaces ", language: "EN", published: DateTimeOffset.Parse("2024-01-01T00:00:00Z"), modified: DateTimeOffset.Parse("2024-01-02T00:00:00Z"), severity: "CRITICAL", exploitKnown: true, aliases: new[] { " CVE-2024-0001", "GHSA-aaaa", "cve-2024-0001" }, references: new[] { new AdvisoryReference("https://example.com/b", "patch", null, null, AdvisoryProvenance.Empty), new AdvisoryReference("https://example.com/a", null, null, null, AdvisoryProvenance.Empty), }, affectedPackages: new[] { new AffectedPackage( type: AffectedPackageTypes.SemVer, identifier: "pkg:npm/sample", platform: "node", versionRanges: new[] { new AffectedVersionRange("semver", "1.0.0", "1.0.1", null, null, AdvisoryProvenance.Empty), new AffectedVersionRange("semver", "1.0.0", "1.0.1", null, null, AdvisoryProvenance.Empty), new AffectedVersionRange("semver", "0.9.0", null, "0.9.9", null, AdvisoryProvenance.Empty), }, statuses: Array.Empty(), provenance: new[] { new AdvisoryProvenance("nvd", "map", "", DateTimeOffset.Parse("2024-01-01T00:00:00Z")), new AdvisoryProvenance("vendor", "map", "", DateTimeOffset.Parse("2024-01-02T00:00:00Z")), }) }, cvssMetrics: Array.Empty(), provenance: new[] { new AdvisoryProvenance("nvd", "map", "", DateTimeOffset.Parse("2024-01-01T00:00:00Z")), new AdvisoryProvenance("vendor", "map", "", DateTimeOffset.Parse("2024-01-02T00:00:00Z")), }); Assert.Equal(new[] { "CVE-2024-0001", "GHSA-aaaa" }, advisory.Aliases); Assert.Equal(new[] { "https://example.com/a", "https://example.com/b" }, advisory.References.Select(r => r.Url)); Assert.Equal( new[] { "semver|0.9.0||0.9.9|", "semver|1.0.0|1.0.1||", }, advisory.AffectedPackages.Single().VersionRanges.Select(r => r.CreateDeterministicKey())); } }