Skip to content

ListRunsRequestSchema.limit declares .min(1).max(100) but the boundary enforces only integer-ness — ?limit=0 answers "no runs", ?limit=101 ignores the cap #8054

Description

@baozhoutao

The same declared-vs-enforced family as #7359, on the sibling parameter of the same route, left behind when status was fixed.

Symptom

GET /api/v1/automation/:name/runs against a flow with 10 runs:

queryresult
?limit=0200 with zero rows
?limit=-5200 with zero rows
?limit=101200 with all 10 rows (cap not applied)
?limit=abc400 VALIDATION_FAILED — "Invalid `limit` query parameter — expected a whole number, received "abc""
?limit=1.5the same 400

So the boundary refuses the wrong type but accepts anything outside the declared range. Reproduced 2×, identical both passes.

The ?limit=0 arm is the one that bites: a caller paging with a computed limit that reaches 0 is told the flow has no runs — a confidently wrong answer of exactly the shape #7359 was filed for.

Root cause

packages/runtime/src/query-param.ts:121parseIntegerParam checks Number.isInteger and returns the value; it has no min/max arm — unlike its sibling parseEnumParam, which does read the closed set. packages/runtime/src/domains/automation.ts:737 calls it bare, so ListRunsRequestSchema's declared (1, 100) never reaches the boundary.

Suggested shape

Give parseIntegerParam optional bounds and pass ListRunsRequestSchema's own at the call site, so the declared and enforced ranges cannot drift — the discipline #7359's fix applied to status by reading ExecutionStatus.options rather than re-listing them.

Severity

P3 — no corruption, no leak. A wrong-but-confident answer and an unenforced result-set cap.

Source

Found by the platform checklist retest of automation.flow-runs-page-test-trigger (framework 279ee48a), while verifying #7359's fix. Held no clause of that item.

Metadata

Metadata

Assignees

Type

No type

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions