Skip to content

Commit

Permalink
Add Swagger UI
Browse files Browse the repository at this point in the history
  • Loading branch information
Kaliumhexacyanoferrat committed Dec 15, 2024
1 parent 79b78aa commit 4a6b53b
Show file tree
Hide file tree
Showing 10 changed files with 225 additions and 1 deletion.
7 changes: 7 additions & 0 deletions GenHTTP.sln
Original file line number Diff line number Diff line change
Expand Up @@ -107,6 +107,8 @@ Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "GenHTTP.Adapters.AspNetCore
EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "GenHTTP.Modules.I18n", "Modules\GenHTTP.Modules.I18n\GenHTTP.Modules.I18n.csproj", "{E17F6CF0-295D-408C-9664-FE18C6E83433}"
EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "GenHTTP.Modules.Swagger", "Modules\Swagger\GenHTTP.Modules.Swagger.csproj", "{8B6D634E-D804-41C8-BEB3-9958E57164F6}"
EndProject
Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|Any CPU = Debug|Any CPU
Expand Down Expand Up @@ -261,6 +263,10 @@ Global
{E17F6CF0-295D-408C-9664-FE18C6E83433}.Debug|Any CPU.Build.0 = Debug|Any CPU
{E17F6CF0-295D-408C-9664-FE18C6E83433}.Release|Any CPU.ActiveCfg = Release|Any CPU
{E17F6CF0-295D-408C-9664-FE18C6E83433}.Release|Any CPU.Build.0 = Release|Any CPU
{8B6D634E-D804-41C8-BEB3-9958E57164F6}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{8B6D634E-D804-41C8-BEB3-9958E57164F6}.Debug|Any CPU.Build.0 = Debug|Any CPU
{8B6D634E-D804-41C8-BEB3-9958E57164F6}.Release|Any CPU.ActiveCfg = Release|Any CPU
{8B6D634E-D804-41C8-BEB3-9958E57164F6}.Release|Any CPU.Build.0 = Release|Any CPU
EndGlobalSection
GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE
Expand Down Expand Up @@ -305,6 +311,7 @@ Global
{7CEE048E-FA6A-4D8C-B6A6-EEEA0B048C54} = {AFBFE61E-0C33-42F6-9370-9F5088EB8633}
{AD7904BC-27BE-4EB5-84BC-62FF32DCBB78} = {C3265C1A-E9A9-45FD-BD24-66DE9C7062F1}
{E17F6CF0-295D-408C-9664-FE18C6E83433} = {23B23225-275E-4F52-8B29-6F44C85B6ACE}
{8B6D634E-D804-41C8-BEB3-9958E57164F6} = {23B23225-275E-4F52-8B29-6F44C85B6ACE}
EndGlobalSection
GlobalSection(ExtensibilityGlobals) = postSolution
SolutionGuid = {9C67B3AF-0BF6-4E21-8C39-3F74CFCF9632}
Expand Down
67 changes: 67 additions & 0 deletions Modules/Swagger/GenHTTP.Modules.Swagger.csproj
Original file line number Diff line number Diff line change
@@ -0,0 +1,67 @@
<Project Sdk="Microsoft.NET.Sdk">

<PropertyGroup>

<TargetFrameworks>net8.0;net9.0</TargetFrameworks>

<LangVersion>13.0</LangVersion>
<Nullable>enable</Nullable>
<TreatWarningsAsErrors>true</TreatWarningsAsErrors>
<ImplicitUsings>enable</ImplicitUsings>

<AssemblyVersion>9.4.0.0</AssemblyVersion>
<FileVersion>9.4.0.0</FileVersion>
<Version>9.4.0</Version>

<Authors>Andreas Nägeli</Authors>
<Company/>

<PackageLicenseFile>LICENSE</PackageLicenseFile>
<PackageProjectUrl>https://genhttp.org/</PackageProjectUrl>

<Description>Serves Swagger UI for debugging purposes.</Description>
<PackageTags>HTTP Webserver C# Module Swagger UI</PackageTags>

<PublishRepositoryUrl>true</PublishRepositoryUrl>
<IncludeSymbols>true</IncludeSymbols>
<SymbolPackageFormat>snupkg</SymbolPackageFormat>

<GenerateDocumentationFile>true</GenerateDocumentationFile>
<NoWarn>CS1591,CS1587,CS1572,CS1573</NoWarn>

<PackageIcon>icon.png</PackageIcon>

</PropertyGroup>

<ItemGroup>

<None Include="..\..\LICENSE" Pack="true" PackagePath="\"/>
<None Include="..\..\Resources\icon.png" Pack="true" PackagePath="\"/>

</ItemGroup>

<ItemGroup>

<ProjectReference Include="..\..\API\GenHTTP.Api.csproj"/>

<ProjectReference Include="..\IO\GenHTTP.Modules.IO.csproj" />

<ProjectReference Include="..\Layouting\GenHTTP.Modules.Layouting.csproj"/>

<ProjectReference Include="..\Pages\GenHTTP.Modules.Pages.csproj" />

<PackageReference Include="Microsoft.SourceLink.GitHub" Version="8.0.0" PrivateAssets="All"/>

</ItemGroup>

<ItemGroup>
<None Remove="Resources\Static\swagger-ui.css" />
<EmbeddedResource Include="Resources\Static\swagger-ui.css" />
<None Remove="Resources\Static\swagger-ui-bundle.js" />
<EmbeddedResource Include="Resources\Static\swagger-ui-bundle.js" />
<None Remove="Resources\Static\swagger-ui-standalone-preset.js" />
<None Remove="Resources\Templates\Index.html" />
<EmbeddedResource Include="Resources\Templates\Index.html" />
</ItemGroup>

</Project>
73 changes: 73 additions & 0 deletions Modules/Swagger/Handler/SwaggerUIHandler.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,73 @@
using Cottle;
using GenHTTP.Api.Content;
using GenHTTP.Api.Protocol;
using GenHTTP.Modules.Basics;
using GenHTTP.Modules.IO;
using GenHTTP.Modules.Pages;
using GenHTTP.Modules.Pages.Rendering;

namespace GenHTTP.Modules.Swagger.Handler;

public sealed class SwaggerUIHandler : IHandler
{

#region Get-/Setters

public IHandler StaticResources { get; }

public TemplateRenderer Template { get; }

public string Url { get; }

#endregion

#region Initialization

public SwaggerUIHandler(string? url)
{
StaticResources = Resources.From(ResourceTree.FromAssembly("Resources.Static"))
.Build();

Template = Renderer.From(Resource.FromAssembly("Index.html").Build());

Url = url ?? "../openapi.json";
}

#endregion

#region Functionality

public ValueTask PrepareAsync() => ValueTask.CompletedTask;

public async ValueTask<IResponse?> HandleAsync(IRequest request)
{
if (!request.HasType(RequestMethod.Get, RequestMethod.Head))
{
throw new ProviderException(ResponseStatus.MethodNotAllowed, "Only GET requests are allowed by this handler", (b) => b.Header("Allow", "GET"));
}

if (request.Target.Ended)
{
var config = new Dictionary<Value, Value>
{
["url"] = Url
};

var content = await Template.RenderAsync(config);

return request.GetPage(content)
.Build();
}

if (request.Target.Current?.Value == "static")
{
request.Target.Advance();
return await StaticResources.HandleAsync(request);
}

return null;
}

#endregion

}
28 changes: 28 additions & 0 deletions Modules/Swagger/Handler/SwaggerUIHandlerBuilder.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
using GenHTTP.Api.Content;

namespace GenHTTP.Modules.Swagger.Handler;

public sealed class SwaggerUIHandlerBuilder : IHandlerBuilder<SwaggerUIHandlerBuilder>
{
private readonly List<IConcernBuilder> _Concerns = [];

private string? _Url;

public SwaggerUIHandlerBuilder Url(string url)
{
_Url = url;
return this;
}

public SwaggerUIHandlerBuilder Add(IConcernBuilder concern)
{
_Concerns.Add(concern);
return this;
}

public IHandler Build()
{
return Concerns.Chain(_Concerns, new SwaggerUIHandler(_Url));
}

}
2 changes: 2 additions & 0 deletions Modules/Swagger/Resources/Static/swagger-ui-bundle.js

Large diffs are not rendered by default.

3 changes: 3 additions & 0 deletions Modules/Swagger/Resources/Static/swagger-ui.css

Large diffs are not rendered by default.

22 changes: 22 additions & 0 deletions Modules/Swagger/Resources/Templates/Index.html
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8" />
<meta name="viewport" content="width=device-width, initial-scale=1" />
<meta name="description" content="SwaggerUI" />
<title>SwaggerUI</title>
<link rel="stylesheet" href="./static/swagger-ui.css" />
</head>
<body>
<div id="swagger-ui"></div>
<script src="./static/swagger-ui-bundle.js"></script>
<script>
window.onload = () => \{
window.ui = SwaggerUIBundle(\{
url: '{url}',
dom_id: '#swagger-ui'
\});
\};
</script>
</body>
</html>
14 changes: 14 additions & 0 deletions Modules/Swagger/SwaggerUI.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
using GenHTTP.Modules.Layouting.Provider;
using GenHTTP.Modules.Swagger.Handler;

namespace GenHTTP.Modules.Swagger;

public static class SwaggerUI
{

public static SwaggerUIHandlerBuilder Create() => new();

public static LayoutBuilder AddSwaggerUI(this LayoutBuilder layout, string segment = "swagger", string? url = null)
=> layout.Add(segment, (url != null) ? Create().Url(url) : Create());

}
1 change: 1 addition & 0 deletions Playground/GenHTTP.Playground.csproj
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,7 @@
<ProjectReference Include="..\Modules\ServerSentEvents\GenHTTP.Modules.ServerSentEvents.csproj" />
<ProjectReference Include="..\Modules\SinglePageApplications\GenHTTP.Modules.SinglePageApplications.csproj"/>
<ProjectReference Include="..\Modules\StaticWebsites\GenHTTP.Modules.StaticWebsites.csproj"/>
<ProjectReference Include="..\Modules\Swagger\GenHTTP.Modules.Swagger.csproj" />
<ProjectReference Include="..\Modules\VirtualHosting\GenHTTP.Modules.VirtualHosting.csproj"/>
<ProjectReference Include="..\Modules\Webservices\GenHTTP.Modules.Webservices.csproj"/>
<ProjectReference Include="..\Modules\Websockets\GenHTTP.Modules.Websockets.csproj"/>
Expand Down
9 changes: 8 additions & 1 deletion Playground/Program.cs
Original file line number Diff line number Diff line change
@@ -1,9 +1,16 @@
using GenHTTP.Engine.Kestrel;
using GenHTTP.Modules.DirectoryBrowsing;
using GenHTTP.Modules.Functional;
using GenHTTP.Modules.IO;
using GenHTTP.Modules.Layouting;
using GenHTTP.Modules.OpenApi;
using GenHTTP.Modules.Practices;
using GenHTTP.Modules.Swagger;

var app = Listing.From(ResourceTree.FromDirectory("."));
var app = Layout.Create()
.Add(Inline.Create().Get(() => "Hello World"))
.AddOpenApi()
.AddSwaggerUI();

await Host.Create()
.Handler(app)
Expand Down

0 comments on commit 4a6b53b

Please sign in to comment.