PERF-ONT-003 — Bound semantic-query results
| Field | Value |
|---|---|
| Status | Open finding; source-verified; payload limit pending |
| Severity | High |
| Components | sparqd/oqullus, sparqd/bff-api, sparqd/ontology, Cube, Trino |
| Associated issues | Not opened pending finding review |
Concrete observed case
The builder defaults to no row limit and offers No Limit alongside finite presets. Cube returns a full result; Ontology and BFF buffer the JSON; Oqullus materializes table and chart pivots, then sorts, totals, paginates, and exports the complete array in the browser.
Expected condition
Interactive execution has a server-owned default and hard row/byte boundary, with explicit truncation and continuation. Large exports run asynchronously to bounded object-storage artifacts. Limits are enforced before each buffer.
Why it matters
One high-cardinality query can exhaust Trino, Cube, proxy, or browser memory. Client pagination changes presentation, not transferred or materialized size.
Existing controls and workarounds
Users can choose a finite limit. Voluntary selection is not a capacity control and does not bound wide rows or response bytes.
Alternatives considered
- Recommended: bounded interactive continuation plus asynchronous export.
- Hard row limit only — useful interim control but wide rows remain unbounded.
- Browser pagination — current behavior; it does not protect services.
Component involvement
- Oqullus makes limits/truncation explicit and avoids full client transforms.
- BFF/Ontology enforce payload budgets and continuation/export status.
- Cube/Trino apply source limits, admission, cancellation, and time boundaries.
Reproduction and verification
Follow ONT-S017.
Resolution conditions
Close when supported row/byte/time limits are tested at every hop, partial output is explicit, and complete large export is asynchronous.
Validation and blockers
The No Limit and buffering path is source-confirmed. Safe deployed payload thresholds have not been measured.