fix(backend): 400 instead of 500 on an unparseable peildatum (RB-16)

BIO-019: GET /stamdata/{table}?peildatum= called DateOnly.Parse
directly, which throws FormatException on anything unparseable — an
unhandled 500 (leaking exception detail in Development) instead of
the 400-with-problem-details every other bad-input check in this file
returns. §3c named backend/Stamdata's 71.7% branch coverage (BL-005)
as the weak spot this bug lived in.

Switched to DateOnly.TryParse; an unparseable value now returns
Results.Problem(detail: ..., statusCode: 400), matching the shape the
upload/change-request endpoints already use. Endpoint doc gained
.ProducesProblem(400), so the OpenAPI doc + generated client were
regenerated and committed in this same diff (RB-09's note records a
prior incident where a response-shape change shipped without this and
the drift went unnoticed).

No FE change needed: libs/beheer's stamdata adapter already funnels
every call through runSubmit, which folds any thrown ApiException
(now including this 400) into a generic Result error — ADR-0001's
"the FE renders the decision" already covers "the server rejected
this input".

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
This commit is contained in:
eho
2026-08-27 16:53:29 +02:00
co-authored by Claude Opus 5
parent a93218e8ac
commit 2627799284
5 changed files with 121 additions and 1 deletions
+13 -1
View File
@@ -212,12 +212,24 @@ api.MapGet("/stamdata/{table}", (string table, string? peildatum, HttpContext ct
{
var t = StamdataCatalog.Find(table);
if (t is null) return Results.NotFound();
var rows = peildatum is { Length: > 0 } p ? t.RowsOn(DateOnly.Parse(p)) : t.Rows();
DateOnly? peildatumWaarde = null;
// RB-16/BIO-019: DateOnly.Parse threw FormatException on unparseable input, surfacing as
// an unhandled 500 (and, in Development, an exception detail leaked to the caller) — an
// admin-gated but still user-supplied string needs the same 400 path every other bad-input
// check in this file uses, not a crash.
if (peildatum is { Length: > 0 } p)
{
if (!DateOnly.TryParse(p, out var parsed))
return Results.Problem(detail: $"Ongeldige peildatum '{p}'.", statusCode: StatusCodes.Status400BadRequest);
peildatumWaarde = parsed;
}
var rows = peildatumWaarde is { } d ? t.RowsOn(d) : t.Rows();
return Results.Ok(new StamdataTableDto(t.Id, t.Label, t.Columns.Select(ToColumnDto).ToList(), t.Temporal, rows));
}))
.Gate("StamdataAdmin")
.WithName("stamdataTable")
.Produces<StamdataTableDto>()
.ProducesProblem(StatusCodes.Status400BadRequest)
.ProducesProblem(StatusCodes.Status403Forbidden)
.Produces(StatusCodes.Status404NotFound);