Skip to content

[v1 API] 12 — Parameterized aggregations: quantile_cont, quantile_disc, iqr #415

Description

@tomanizer

Part of #403. Depends on #413.

What

Add quantile and IQR aggregations. These are essential for financial analytics (Value at Risk, distribution shape) and require a params extension to the measure spec.

Model change

Add params to MeasureSpec:

class MeasureSpec(BaseModel):
    field: str
    aggregation: AggregationFunction = "sum"
    alias: str | None = None
    sort_by: str | None = None
    params: dict[str, Any] | None = None

New aggregation functions

quantile_cont

Continuous (interpolated) quantile. params.q is required.

{ "field": "daily_return", "aggregation": "quantile_cont", "params": { "q": 0.05 }, "alias": "var_95" }

SQL: QUANTILE_CONT("daily_return", 0.05)

When q is an array, returns an object keyed by p{nn}:

{ "field": "price", "aggregation": "quantile_cont", "params": { "q": [0.05, 0.25, 0.5, 0.75, 0.95] }, "alias": "dist" }

Response cell value: { "p05": 142.1, "p25": 155.3, "p50": 161.8, "p75": 168.4, "p95": 179.2 }

Key naming: p + zero-padded two-decimal integer representation of q * 100 (e.g. 0.05p05, 0.975p97).

SQL: QUANTILE_CONT("price", [0.05, 0.25, 0.5, 0.75, 0.95]) — DuckDB returns an array; Python post-processes into the named object.

quantile_disc

Discrete (actual data value) quantile. Same interface as quantile_cont.

SQL: QUANTILE_DISC("field", q)

iqr

Interquartile range (Q75 − Q25). No params needed.

{ "field": "price", "aggregation": "iqr", "alias": "price_iqr" }

SQL: QUANTILE_CONT("price", 0.75) - QUANTILE_CONT("price", 0.25)

Validation

  • quantile_cont/quantile_disc without params.q422 VALIDATION_ERROR
  • params.q scalar: must be in [0.0, 1.0]
  • params.q array: each element must be in [0.0, 1.0], max 20 quantiles per request
  • iqr with params → ignored (or rejected — decide in implementation)
  • All three functions applicable to numeric fields only

Acceptance criteria

  • quantile_cont with scalar q returns a single numeric value
  • quantile_cont with array q returns a named object (p05, p50, etc.)
  • quantile_disc works identically with discrete semantics
  • iqr returns Q75 − Q25 without params
  • Missing params.q returns 422
  • q out of [0, 1] returns 422
  • Array q with more than 20 elements returns 422
  • Tests cover scalar quantile, multi-quantile object, IQR, and all validation failures

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions