LonG.DevTool is a developer tool UI for ASP.NET Core: an in-browser API Explorer that loads your OpenAPI/Swagger document and lets you try operations (path, query, body, JWT, foreign-key dropdowns) without leaving the app.
- NuGet: LonG.DevTool
- Install:
dotnet add package LonG.DevTool --version 1.0.0
-
API Explorer SPA – Single-page app served at a path (e.g.
/_devtool) that:- Loads your API’s OpenAPI (Swagger) JSON from the same host
- Lists operations by tag/group
- Lets you fill path/query/body, send requests, and view responses
- Supports JWT (set token, “Apply JWT from response” after login)
- Shows foreign-key dropdowns when schema uses “Foreign key to <Entity>”
-
Drop-in for any ASP.NET Core API – Add the package, expose OpenAPI, call
MapDevToolUi("/_devtool"), and open/_devtoolin the browser. No separate Swagger UI host required.
| Layer | Technology |
|---|---|
| Package | LonG.DevTool 1.0.0 (.NET 10) |
| Host | ASP.NET Core (minimal API or controllers) |
| OpenAPI | Microsoft.AspNetCore.OpenApi, MapOpenApi() and/or Swashbuckle.AspNetCore |
| UI | React SPA (pre-built in package) + middleware to serve it and fetch/cache OpenAPI |
The Explorer UI is built with React, Tailwind, and Zustand; the package ships the built assets under wwwroot/dev-tool-ui. The middleware resolves them from the assembly location when you reference the NuGet package.
You can use either controllers or minimal APIs (or both). The steps are the same; only how you define endpoints differs.
- .NET 10 (or the TFM your app targets)
- An ASP.NET Core Web API project
This mirrors the Sample.Api project in this repo (see Sample.Api/).
dotnet add package LonG.DevTool --version 1.0.0
dotnet add package Microsoft.AspNetCore.OpenApi
dotnet add package Swashbuckle.AspNetCoreOr in the project file:
<ItemGroup>
<PackageReference Include="LonG.DevTool" Version="1.0.0" />
<PackageReference Include="Microsoft.AspNetCore.OpenApi" Version="10.0.0" />
<PackageReference Include="Swashbuckle.AspNetCore" Version="10.1.2" />
</ItemGroup>In Program.cs:
builder.Services.AddOpenApi();
builder.Services.AddSwaggerGen();
builder.Services.AddControllers();
builder.Services.AddEndpointsApiExplorer();if (app.Environment.IsDevelopment())
{
app.MapOpenApi(); // exposes /openapi/v1.json
app.UseSwaggerUI(c => c.SwaggerEndpoint("/openapi/v1.json", "My API"));
}app.UseStaticFiles();
app.MapDevToolUi("/_devtool"); // requires: using DevTool.UI.Middleware;
app.MapControllers();
app.Run();[ApiController]
[Route("api/[controller]")]
public class ProductController : ControllerBase
{
[HttpGet]
public ActionResult<IEnumerable<Product>> GetAll() => Ok(products);
[HttpGet("{id:int}")]
public ActionResult<Product> GetById(int id) => ...
}- Run the app (
dotnet runor F5). - Open
https://localhost:<port>/_devtool. - The Explorer loads
/openapi/v1.jsonand lists your controller actions; you can try them from the UI.
Same package and OpenAPI setup; endpoints are defined with MapGet, MapPost, MapGroup, etc. (see Sample.Api Endpoints/CategoryEndpoints.cs).
Same as Option A:
dotnet add package LonG.DevTool --version 1.0.0
dotnet add package Microsoft.AspNetCore.OpenApi
dotnet add package Swashbuckle.AspNetCoreIn Program.cs:
builder.Services.AddOpenApi();
builder.Services.AddSwaggerGen();
builder.Services.AddEndpointsApiExplorer();if (app.Environment.IsDevelopment())
{
app.MapOpenApi();
app.UseSwaggerUI(c => c.SwaggerEndpoint("/openapi/v1.json", "My API"));
}app.UseStaticFiles();
app.MapDevToolUi("/_devtool"); // using DevTool.UI.Middleware;
app.MapGet("/api/hello", () => Results.Ok(new { message = "Hello" }));
// Or use extension method for a group:
app.MapCategoryEndpoints();
app.Run();// Endpoints/CategoryEndpoints.cs
public static void MapCategoryEndpoints(this WebApplication app)
{
var group = app.MapGroup("/api/category").WithTags("Category");
group.MapGet("", () => Results.Ok(categories));
group.MapGet("{id:int}", (int id) => ...);
}- Run the app and open
https://localhost:<port>/_devtool. - The Explorer uses
/openapi/v1.jsonand lists your minimal API endpoints.
If your OpenAPI document is at a different path (e.g. Swashbuckle-only at /swagger/v1/swagger.json):
app.MapDevToolUi("/_devtool", "index.html", opts =>
{
opts.OpenApiPath = "/swagger/v1/swagger.json";
opts.SwaggerJsonFileName = "swagger.json";
});For body or path parameters that are foreign keys (e.g. categoryId), the Explorer can show a dropdown filled from a list endpoint:
- In your OpenAPI schema, set the property description to
Foreign key to <EntityName>(e.g.Foreign key to Category). - Expose a GET list endpoint for that entity (e.g.
GET /api/categories) returning an array withidand a label field (name,title, orcode).
See DevTool.WebApi and its DTOs for [SwaggerSchema(Description = "Foreign key to Category")] examples.
You can let the Explorer auto-generate request bodies via a /prompt endpoint that calls an LLM hosted on Hugging Face.
-
Configure Hugging Face in your API (
appsettings.jsonor user secrets):"HuggingFace": { "Url": "https://router.huggingface.co", "ApiKey": "<your api key here>", "Model": "meta-llama/Llama-3.1-8B-Instruct" }
-
Register the HttpClient and options in
Program.cs(host API):using DevTool.UI.Extensions; // AddDevToolHttpClients, MapPromptEndpoint var builder = WebApplication.CreateBuilder(args); // ... builder.Services.AddDevToolHttpClients(builder.Configuration); // ... var app = builder.Build();
-
Map the
/promptendpoint:// after building 'app' app.MapPromptEndpoint(); // POST /prompt
With this in place, the Quick fill button in the Request Body section:
- Builds a JSON template from the operation’s OpenAPI schema
- Sends it to
/prompt, which calls your configured Hugging Face model - Parses the JSON response and uses it as the request payload
If your API protects endpoints with JWT Bearer authentication, add the authentication package and configure it so the Explorer can send the token from the Authorize panel (and use “Apply JWT from response” after a login call).
dotnet add package Microsoft.AspNetCore.Authentication.JwtBearerusing System.Text;
using Microsoft.AspNetCore.Authentication.JwtBearer;
using Microsoft.IdentityModel.Tokens;
builder.Services.AddAuthentication(JwtBearerDefaults.AuthenticationScheme)
.AddJwtBearer(options =>
{
options.TokenValidationParameters = new TokenValidationParameters
{
ValidateIssuer = true,
ValidateAudience = true,
ValidateLifetime = true,
ValidateIssuerSigningKey = true,
ValidIssuer = "long.dev",
ValidAudience = "long.dev",
IssuerSigningKey = new SymmetricSecurityKey(
Encoding.UTF8.GetBytes("super-secret-key-123"))
};
});
builder.Services.AddAuthorization();Use appsettings.json or User Secrets for issuer, audience, and signing key in real apps—do not hardcode secrets.
Call these before MapControllers() or your endpoint mappings:
app.UseAuthentication();
app.UseAuthorization();
app.MapDevToolUi("/_devtool");
app.MapControllers();Then protect endpoints with [Authorize] (controllers) or .RequireAuthorization() (minimal API). In the Explorer, set the JWT in Authorize; it will be sent on subsequent requests.
| Project | Description |
|---|---|
| DevTool.WebApi | Full sample with OpenAPI, JWT, EF Core, and dev tool integration (project reference). |
| DevTool.UI | Source for the NuGet package: builds the React SPA and produces the LonG.DevTool package. |
| dev-tool-ui | React (Bun + Tailwind) app: API Explorer UI source. |
- To use the dev tool in your app: install LonG.DevTool and follow the steps above.
- To build or publish the package: see DevTool.UI/README.md.
MIT. See repository license.