From cea47108b03cd89acc3bb356d8006cb9c4eb0536 Mon Sep 17 00:00:00 2001 From: Kevin Schneider Date: Mon, 26 Feb 2024 07:35:53 +0100 Subject: [PATCH] Refactor package rendering to be reusable across request handlers --- .../Pages/Components/Package.cs | 58 +++++++++++ .../{Index.cs => Handlers/IndexHandlers.cs} | 4 +- .../Pages/Handlers/PackageHandlers.cs | 99 +++++++++++++++++++ .../PackagesHandlers.cs} | 5 +- src/PackageRegistryService/Pages/Package.cs | 81 --------------- .../Pages/PageEndpoints.cs | 12 ++- 6 files changed, 168 insertions(+), 91 deletions(-) create mode 100644 src/PackageRegistryService/Pages/Components/Package.cs rename src/PackageRegistryService/Pages/{Index.cs => Handlers/IndexHandlers.cs} (90%) create mode 100644 src/PackageRegistryService/Pages/Handlers/PackageHandlers.cs rename src/PackageRegistryService/Pages/{Packages.cs => Handlers/PackagesHandlers.cs} (95%) delete mode 100644 src/PackageRegistryService/Pages/Package.cs diff --git a/src/PackageRegistryService/Pages/Components/Package.cs b/src/PackageRegistryService/Pages/Components/Package.cs new file mode 100644 index 0000000..cd0b32c --- /dev/null +++ b/src/PackageRegistryService/Pages/Components/Package.cs @@ -0,0 +1,58 @@ +using PackageRegistryService.Models; +using System.Text; + +namespace PackageRegistryService.Pages.Components +{ + public class Package + { + public static string Render( + string packageName, + string packageVersion, + string packageDescription, + string packageReleaseNotes, + string packageContent, + DateOnly packageReleaseDate, + string[] packageTags, + Author[] packageAuthors, + string versionTable + ) + { + return $@"
+
+

Validation Package {packageName}

+

{PackageTag.RenderAllInline(packageTags)}

+

v{packageVersion} released on {packageReleaseDate}

+
+
+
+
+

Install with arc-validate

+
 arc-validate package install {packageName} --package-version {packageVersion}
+
+
+
+

Description

+ {PackageDescription.Render(packageDescription)} +
+
+
+
+ Release notes + {PackageReleaseNotes.Render(packageReleaseNotes)} +
+
+
+ Browse code (v{packageVersion}) +
{packageContent}
+
+
+
+ Available versions + {versionTable} +
+
+
+"; + } + } +} diff --git a/src/PackageRegistryService/Pages/Index.cs b/src/PackageRegistryService/Pages/Handlers/IndexHandlers.cs similarity index 90% rename from src/PackageRegistryService/Pages/Index.cs rename to src/PackageRegistryService/Pages/Handlers/IndexHandlers.cs index cf8d2e4..d743016 100644 --- a/src/PackageRegistryService/Pages/Index.cs +++ b/src/PackageRegistryService/Pages/Handlers/IndexHandlers.cs @@ -2,9 +2,9 @@ using PackageRegistryService.Models; using PackageRegistryService.Pages.Components; -namespace PackageRegistryService.Pages +namespace PackageRegistryService.Pages.Handlers { - public static class Index + public static class IndexHandlers { public static async Task Render() { diff --git a/src/PackageRegistryService/Pages/Handlers/PackageHandlers.cs b/src/PackageRegistryService/Pages/Handlers/PackageHandlers.cs new file mode 100644 index 0000000..baae68b --- /dev/null +++ b/src/PackageRegistryService/Pages/Handlers/PackageHandlers.cs @@ -0,0 +1,99 @@ +using Microsoft.AspNetCore.Http.HttpResults; +using Microsoft.EntityFrameworkCore; +using PackageRegistryService.Models; +using PackageRegistryService.Pages.Components; +using System.Text; +using System.Xml.Linq; + +namespace PackageRegistryService.Pages.Handlers +{ + public static class PackageHandlers + { + public static async Task>> Render(string packageName, string version, ValidationPackageDb database) + { + var splt = version.Split('.'); + if (splt.Length != 3) + { + return TypedResults.BadRequest("version was not a of valid format MAJOR.MINOR.REVISION"); + } + + int major; int minor; int revision; + + if ( + !int.TryParse(splt[0], out major) + || !int.TryParse(splt[1], out minor) + || !int.TryParse(splt[2], out revision) + ) + { + return TypedResults.BadRequest("version was not a of valid format MAJOR.MINOR.REVISION"); + } + + var package = await database.ValidationPackages.FindAsync(packageName, major, minor, revision); + + if (package == null) + { + return TypedResults.NotFound(); + } + + var packages = await + database.ValidationPackages + .Where(p => p.Name == packageName) + .ToArrayAsync(); + + var page = Layout.Render( + activeNavbarItem: "", + title: $"Package {packageName} - ARC validation package registry API", + content: Components.Package.Render( + packageName: packageName, + packageVersion: package.GetSemanticVersionString(), + packageContent: Encoding.UTF8.GetString(package.PackageContent), + packageReleaseDate: package.ReleaseDate, + packageTags: package.Tags ?? [], + packageDescription: package.Description, + packageReleaseNotes: package.ReleaseNotes ?? "", + packageAuthors: (package.Authors ?? []).ToArray(), + versionTable: Components.PackageAvailableVersion.RenderVersionTable(packages) + ) + ); + + return TypedResults.Text(content: page, contentType: "text/html"); + } + public static async Task> RenderLatest(string packageName, ValidationPackageDb database) + { + var packages = await + database.ValidationPackages + .Where(p => p.Name == packageName) + .ToArrayAsync(); + + var latestPackage = + packages + .OrderByDescending(p => p.MajorVersion) + .ThenByDescending(p => p.MinorVersion) + .ThenByDescending(p => p.PatchVersion) + .FirstOrDefault(); + + if (latestPackage == null) + { + return TypedResults.NotFound(); + } + + var page = Layout.Render( + activeNavbarItem: "", + title: $"Package {packageName} - ARC validation package registry API", + content: Components.Package.Render( + packageName: packageName, + packageVersion: latestPackage.GetSemanticVersionString(), + packageContent: Encoding.UTF8.GetString(latestPackage.PackageContent), + packageReleaseDate: latestPackage.ReleaseDate, + packageTags: latestPackage.Tags ?? [], + packageDescription: latestPackage.Description, + packageReleaseNotes: latestPackage.ReleaseNotes ?? "", + packageAuthors: (latestPackage.Authors ?? []).ToArray(), + versionTable: Components.PackageAvailableVersion.RenderVersionTable(packages) + ) + ); + + return TypedResults.Text(content: page, contentType: "text/html"); + } + } +} diff --git a/src/PackageRegistryService/Pages/Packages.cs b/src/PackageRegistryService/Pages/Handlers/PackagesHandlers.cs similarity index 95% rename from src/PackageRegistryService/Pages/Packages.cs rename to src/PackageRegistryService/Pages/Handlers/PackagesHandlers.cs index 989a51b..53a4a45 100644 --- a/src/PackageRegistryService/Pages/Packages.cs +++ b/src/PackageRegistryService/Pages/Handlers/PackagesHandlers.cs @@ -7,11 +7,10 @@ using System.Linq; using static System.Net.Mime.MediaTypeNames; -namespace PackageRegistryService.Pages +namespace PackageRegistryService.Pages.Handlers { - public static class Packages + public static class PackagesHandlers { - public static async Task Render(ValidationPackageDb database) { var packages = await database.ValidationPackages.ToArrayAsync(); diff --git a/src/PackageRegistryService/Pages/Package.cs b/src/PackageRegistryService/Pages/Package.cs deleted file mode 100644 index c517eae..0000000 --- a/src/PackageRegistryService/Pages/Package.cs +++ /dev/null @@ -1,81 +0,0 @@ -using Microsoft.AspNetCore.Http.HttpResults; -using Microsoft.EntityFrameworkCore; -using PackageRegistryService.Models; -using PackageRegistryService.Pages.Components; -using System.Text; - -namespace PackageRegistryService.Pages -{ - public static class Package - { - public static async Task> Render(string packageName, string version, ValidationPackageDb database) - { - var content = $"{packageName}, {version}"; - return TypedResults.Text(content: content, contentType: "text/html"); - } - public static async Task> RenderLatest(string packageName, ValidationPackageDb database) - { - var packages = await - database.ValidationPackages - .Where(p => p.Name == packageName) - .ToArrayAsync(); - - var latestPackage = - packages - .OrderByDescending(p => p.MajorVersion) - .ThenByDescending(p => p.MinorVersion) - .ThenByDescending(p => p.PatchVersion) - .FirstOrDefault(); - - if (latestPackage == null) - { - return TypedResults.NotFound(); - } - - var content = $@"
-
-

Validation Package {packageName}

-

{PackageTag.RenderAllInline(latestPackage.Tags)}

-

v{latestPackage.GetSemanticVersionString()}

-
-
-
-
-

Install with arc-validate

-
 arc-validate package install {packageName} --package-version {latestPackage.GetSemanticVersionString()}
-
-
-
-

Description

- {PackageDescription.Render(latestPackage.Description)} -
-
-
-
- Release notes - {PackageReleaseNotes.Render(latestPackage.ReleaseNotes)} -
-
-
- Browse code (v{latestPackage.GetSemanticVersionString()}) -
{Encoding.UTF8.GetString(latestPackage.PackageContent)}
-
-
-
- Available versions - {PackageAvailableVersion.RenderVersionTable(packages)} -
-
-
-"; - - var page = Layout.Render( - activeNavbarItem: "", - title: $"Package {packageName} - ARC validation package registry API", - content: content - ); - - return TypedResults.Text(content: page, contentType: "text/html"); - } - } -} diff --git a/src/PackageRegistryService/Pages/PageEndpoints.cs b/src/PackageRegistryService/Pages/PageEndpoints.cs index 8a8624c..fc5ab8f 100644 --- a/src/PackageRegistryService/Pages/PageEndpoints.cs +++ b/src/PackageRegistryService/Pages/PageEndpoints.cs @@ -1,16 +1,18 @@ -namespace PackageRegistryService.Pages +using PackageRegistryService.Pages.Handlers; + +namespace PackageRegistryService.Pages { public static class PageEndpoints { public static RouteGroupBuilder MapPageEndpoints(this RouteGroupBuilder group) { - group.MapGet("", Index.Render); + group.MapGet("", IndexHandlers.Render); - group.MapGet("packages", Packages.Render); + group.MapGet("packages", PackagesHandlers.Render); - group.MapGet("package/{packageName}", Package.RenderLatest); + group.MapGet("package/{packageName}", PackageHandlers.RenderLatest); - group.MapGet("package/{packageName}/{version}", Package.Render); + group.MapGet("package/{packageName}/{version}", PackageHandlers.Render); return group; }