// ----------------------------------------------------------------------------- // BaselineEndpointsTests.cs // Sprint: SPRINT_4200_0002_0006_delta_compare_api // Description: Integration tests for baseline selection endpoints. // ----------------------------------------------------------------------------- using System.Net; using System.Net.Http.Json; using System.Text.Json; using StellaOps.Scanner.WebService.Contracts; namespace StellaOps.Scanner.WebService.Tests; /// /// Integration tests for baseline selection endpoints. /// public sealed class BaselineEndpointsTests { private static readonly JsonSerializerOptions SerializerOptions = new(JsonSerializerDefaults.Web); [Fact] public async Task GetRecommendations_ValidDigest_ReturnsRecommendations() { using var factory = new ScannerApplicationFactory(); using var client = factory.CreateClient(); var response = await client.GetAsync("/api/v1/baselines/recommendations/sha256:artifact123"); Assert.Equal(HttpStatusCode.OK, response.StatusCode); var result = await response.Content.ReadFromJsonAsync(SerializerOptions); Assert.NotNull(result); Assert.Equal("sha256:artifact123", result!.ArtifactDigest); Assert.NotEmpty(result.Recommendations); Assert.Contains(result.Recommendations, r => r.IsDefault); } [Fact] public async Task GetRecommendations_WithEnvironment_FiltersCorrectly() { using var factory = new ScannerApplicationFactory(); using var client = factory.CreateClient(); var response = await client.GetAsync("/api/v1/baselines/recommendations/sha256:artifact123?environment=production"); Assert.Equal(HttpStatusCode.OK, response.StatusCode); var result = await response.Content.ReadFromJsonAsync(SerializerOptions); Assert.NotNull(result); Assert.NotEmpty(result!.Recommendations); } [Fact] public async Task GetRecommendations_IncludesRationale() { using var factory = new ScannerApplicationFactory(); using var client = factory.CreateClient(); var response = await client.GetAsync("/api/v1/baselines/recommendations/sha256:artifact123"); var result = await response.Content.ReadFromJsonAsync(SerializerOptions); Assert.NotNull(result); foreach (var rec in result!.Recommendations) { Assert.NotEmpty(rec.Rationale); Assert.NotEmpty(rec.Type); Assert.NotEmpty(rec.Label); } } [Fact] public async Task GetRationale_ValidDigests_ReturnsDetailedRationale() { using var factory = new ScannerApplicationFactory(); using var client = factory.CreateClient(); var response = await client.GetAsync("/api/v1/baselines/rationale/sha256:base123/sha256:head456"); Assert.Equal(HttpStatusCode.OK, response.StatusCode); var result = await response.Content.ReadFromJsonAsync(SerializerOptions); Assert.NotNull(result); Assert.Equal("sha256:base123", result!.BaseDigest); Assert.Equal("sha256:head456", result.HeadDigest); Assert.NotEmpty(result.SelectionType); Assert.NotEmpty(result.Rationale); Assert.NotEmpty(result.DetailedExplanation); } [Fact] public async Task GetRationale_IncludesSelectionCriteria() { using var factory = new ScannerApplicationFactory(); using var client = factory.CreateClient(); var response = await client.GetAsync("/api/v1/baselines/rationale/sha256:baseline-base123/sha256:head456"); var result = await response.Content.ReadFromJsonAsync(SerializerOptions); Assert.NotNull(result); Assert.NotNull(result!.SelectionCriteria); Assert.NotEmpty(result.SelectionCriteria); } [Fact] public async Task GetRecommendations_DefaultIsFirst() { using var factory = new ScannerApplicationFactory(); using var client = factory.CreateClient(); var response = await client.GetAsync("/api/v1/baselines/recommendations/sha256:artifact123"); var result = await response.Content.ReadFromJsonAsync(SerializerOptions); Assert.NotNull(result); Assert.NotEmpty(result!.Recommendations); Assert.True(result.Recommendations[0].IsDefault); } }