From 1730aa0166bddd3eb967fcd943d0d4595d2ec979 Mon Sep 17 00:00:00 2001 From: daniel-c-harvey Date: Tue, 16 Jun 2026 20:07:43 -0400 Subject: [PATCH] docs(public): document StatusCodePages middleware ordering constraint --- DeepDrftPublic/CLAUDE.md | 13 +++++++------ 1 file changed, 7 insertions(+), 6 deletions(-) diff --git a/DeepDrftPublic/CLAUDE.md b/DeepDrftPublic/CLAUDE.md index ed7dea6..85e8a60 100644 --- a/DeepDrftPublic/CLAUDE.md +++ b/DeepDrftPublic/CLAUDE.md @@ -76,12 +76,13 @@ The middleware pipeline in `Program.cs` is ordered as follows: 1. `UseForwardedHeaders()` — reads `X-Forwarded-*` headers from nginx. HTTPS redirect is conditionally disabled via `ForwardedHeaders:DisableHttpsRedirection` so the app can sit behind a reverse proxy without forcing HTTPS at the host level. 2. Exception handler and HTTPS redirect (production only). -3. `UseAntiforgery()` — required by Blazor form handling. -4. **`UseStaticFiles()`** — serves compiled static assets from `wwwroot/` (including `/js/audio/*.js` compiled from TypeScript) with correct MIME types (`application/javascript` for `.js`). This must run *before* `MapStaticAssets()` to ensure production audio interop loads correctly. -5. Cache-control middleware (dev only) — disables caching for `/_framework` and `/_content` assets. -6. `MapStaticAssets()` — endpoint mapper for Blazor framework assets and remaining static content. -7. Development-only `UseStaticFiles()` — serves raw TypeScript from `/Interop/` for source-map debugging. -8. `MapControllers()` and `MapRazorComponents()` — route controller and component requests. +3. `UseStatusCodePagesWithReExecute("/404", createScopeForStatusCodePages: true)` — must sit *before* `UseAntiforgery()` so that re-executed requests (e.g. the `/404` route) pass through antiforgery middleware before reaching the endpoint. Placing it after `UseAntiforgery()` causes an `InvalidOperationException` on re-execution. +4. `UseAntiforgery()` — required by Blazor form handling. +5. **`UseStaticFiles()`** — serves compiled static assets from `wwwroot/` (including `/js/audio/*.js` compiled from TypeScript) with correct MIME types (`application/javascript` for `.js`). This must run *before* `MapStaticAssets()` to ensure production audio interop loads correctly. +6. Cache-control middleware (dev only) — disables caching for `/_framework` and `/_content` assets. +7. `MapStaticAssets()` — endpoint mapper for Blazor framework assets and remaining static content. +8. Development-only `UseStaticFiles()` — serves raw TypeScript from `/Interop/` for source-map debugging. +9. `MapControllers()` and `MapRazorComponents()` — route controller and component requests. ## The proxy controller