Move admin UI to separate internal port (5275) for security

- Admin API and static files only accessible on port 5275
- Main proxy port (8080) no longer serves admin endpoints
- AdminPortFilter rejects admin requests on wrong port
- AdminStaticFilesMiddleware only serves static files on admin port
- Port 5275 NOT exposed in Dockerfile or docker-compose by default
- Access admin UI via SSH tunnel or by uncommenting port mapping
This commit is contained in:
2026-02-03 14:39:07 -05:00
parent 6abf0e0717
commit a8d04b225b
6 changed files with 99 additions and 7 deletions

View File

@@ -0,0 +1,51 @@
namespace allstarr.Middleware;
/// <summary>
/// Middleware that only serves static files on the admin port (5275).
/// This keeps the admin UI isolated from the main proxy port.
/// </summary>
public class AdminStaticFilesMiddleware
{
private readonly RequestDelegate _next;
private readonly StaticFileMiddleware _staticFileMiddleware;
private readonly DefaultFilesMiddleware _defaultFilesMiddleware;
private const int AdminPort = 5275;
public AdminStaticFilesMiddleware(
RequestDelegate next,
IWebHostEnvironment env,
ILoggerFactory loggerFactory)
{
_next = next;
var staticFileOptions = new StaticFileOptions();
var defaultFilesOptions = new DefaultFilesOptions();
_staticFileMiddleware = new StaticFileMiddleware(
_next,
env,
Microsoft.Extensions.Options.Options.Create(staticFileOptions),
loggerFactory);
_defaultFilesMiddleware = new DefaultFilesMiddleware(
(ctx) => _staticFileMiddleware.Invoke(ctx),
env,
Microsoft.Extensions.Options.Options.Create(defaultFilesOptions));
}
public async Task InvokeAsync(HttpContext context)
{
var port = context.Connection.LocalPort;
if (port == AdminPort)
{
// Serve static files on admin port
await _defaultFilesMiddleware.Invoke(context);
}
else
{
// Skip static files on main port
await _next(context);
}
}
}