Refactor code structure for improved readability and maintainability
Some checks failed
AOC Guard CI / aoc-guard (push) Has been cancelled
AOC Guard CI / aoc-verify (push) Has been cancelled
Docs CI / lint-and-preview (push) Has been cancelled
Policy Lint & Smoke / policy-lint (push) Has been cancelled

This commit is contained in:
StellaOps Bot
2025-12-06 21:48:12 +02:00
parent f6c22854a4
commit dd0067ea0b
105 changed files with 12662 additions and 427 deletions

View File

@@ -0,0 +1,21 @@
using System.Text.Json.Serialization;
using StellaOps.Scanner.Core.Contracts;
namespace StellaOps.Scanner.WebService.Contracts;
public sealed record BunPackagesResponse
{
[JsonPropertyName("scanId")]
public string ScanId { get; init; } = string.Empty;
[JsonPropertyName("imageDigest")]
public string ImageDigest { get; init; } = string.Empty;
[JsonPropertyName("generatedAt")]
public DateTimeOffset GeneratedAt { get; init; }
= DateTimeOffset.UtcNow;
[JsonPropertyName("packages")]
public IReadOnlyList<BunPackageArtifact> Packages { get; init; }
= Array.Empty<BunPackageArtifact>();
}

View File

@@ -71,6 +71,12 @@ internal static class ScanEndpoints
.Produces<RubyPackagesResponse>(StatusCodes.Status200OK)
.Produces(StatusCodes.Status404NotFound)
.RequireAuthorization(ScannerPolicies.ScansRead);
scans.MapGet("/{scanId}/bun-packages", HandleBunPackagesAsync)
.WithName("scanner.scans.bun-packages")
.Produces<BunPackagesResponse>(StatusCodes.Status200OK)
.Produces(StatusCodes.Status404NotFound)
.RequireAuthorization(ScannerPolicies.ScansRead);
}
private static async Task<IResult> HandleSubmitAsync(
@@ -497,6 +503,63 @@ internal static class ScanEndpoints
return Json(response, StatusCodes.Status200OK);
}
private static async Task<IResult> HandleBunPackagesAsync(
string scanId,
IScanCoordinator coordinator,
IBunPackageInventoryStore inventoryStore,
HttpContext context,
CancellationToken cancellationToken)
{
ArgumentNullException.ThrowIfNull(coordinator);
ArgumentNullException.ThrowIfNull(inventoryStore);
if (!ScanId.TryParse(scanId, out var parsed))
{
return ProblemResultFactory.Create(
context,
ProblemTypes.Validation,
"Invalid scan identifier",
StatusCodes.Status400BadRequest,
detail: "Scan identifier is required.");
}
var inventory = await inventoryStore.GetAsync(parsed.Value, cancellationToken).ConfigureAwait(false);
if (inventory is null)
{
BunPackageInventory? fallback = null;
if (!LooksLikeScanId(scanId))
{
var snapshot = await TryResolveSnapshotAsync(scanId, coordinator, cancellationToken).ConfigureAwait(false);
if (snapshot is not null)
{
fallback = await inventoryStore.GetAsync(snapshot.ScanId.Value, cancellationToken).ConfigureAwait(false);
}
}
if (fallback is null)
{
return ProblemResultFactory.Create(
context,
ProblemTypes.NotFound,
"Bun packages not found",
StatusCodes.Status404NotFound,
detail: "Bun package inventory is not available for the requested scan.");
}
inventory = fallback;
}
var response = new BunPackagesResponse
{
ScanId = inventory.ScanId,
ImageDigest = inventory.ImageDigest,
GeneratedAt = inventory.GeneratedAtUtc,
Packages = inventory.Packages
};
return Json(response, StatusCodes.Status200OK);
}
private static IReadOnlyDictionary<string, string> NormalizeMetadata(IDictionary<string, string> metadata)
{
if (metadata is null || metadata.Count == 0)