risingwavelabs/risingwave · error
relative_error must be in the range (0, 1), got {}
Error message
relative_error must be in the range (0, 1), got {} What it means
`approx_percentile` takes the relative error as a constant DIRECT argument of the aggregate call. The builder requires it to be strictly between 0 and 1 (exclusive) because it is used to compute ratio `base = (1+e)/(1-e)`, which is undefined or degenerate outside that range.
Source
Thrown at src/expr/impl/src/aggregate/approx_percentile.rs:43
use risingwave_expr::aggregate::{AggCall, AggStateDyn, AggregateFunction, AggregateState};
use risingwave_expr::{Result, build_aggregate};
/// TODO(kwannoel): for single phase agg, we can actually support `UDDSketch`.
/// For two phase agg, we still use `DDSketch`.
/// Then we also need to store the `relative_error` of the sketch, so we can report it
/// in an internal table, if it changes.
#[build_aggregate("approx_percentile(float8) -> float8", state = "bytea")]
fn build(agg: &AggCall) -> Result<Box<dyn AggregateFunction>> {
let quantile = agg.direct_args[0]
.literal()
.map(|x| (*x.as_float64()).into())
.unwrap();
let relative_error: f64 = agg.direct_args[1]
.literal()
.map(|x| (*x.as_float64()).into())
.unwrap();
if relative_error <= 0.0 || relative_error >= 1.0 {
bail!(
"relative_error must be in the range (0, 1), got {}",
relative_error
)
}
let base = (1.0 + relative_error) / (1.0 - relative_error);
Ok(Box::new(ApproxPercentile { quantile, base }))
}
pub struct ApproxPercentile {
quantile: f64,
base: f64,
}
type BucketCount = u64;
type BucketId = i32;
type Count = u64;
#[derive(Debug, Default)]View on GitHub (pinned to 6469eb736d)
Solutions
- Pass a relative error strictly between 0 and 1, e.g. 0.01 for ~1% error.
- Check argument order: quantile first, relative error second, both as literals.
- Remember the error is a fraction, not a percentage: use 0.05 not 5.
Example fix
// before SELECT approx_percentile(latency, 0.95, 1.0) FROM t; // after SELECT approx_percentile(latency, 0.95, 0.01) FROM t;
Defensive patterns
Strategy: validation
Validate before calling
-- verify the error argument before running the query
-- in application code (JS example):
if (!(relErr > 0 && relErr < 1)) throw new Error('relative_error must be in (0,1)'); Try / catch
match approx_percentile_build(...) {
Err(e) if e.to_string().contains("relative_error") => {
// fall back to a default error like 0.01
}
other => other?,
} Prevention
- Always pass relative error as a fraction strictly between 0 and 1.
- Never confuse quantile (0..1) with relative error (0..1).
- Use literals, not expressions, for the DIRECT arguments.
When it happens
Trigger: `approx_percentile(x, q, e)` called with e <= 0.0 or e >= 1.0, e.g. `approx_percentile(latency, 0.95, 1.0)` or `approx_percentile(latency, 0.95, 0)`, at materialized-view/aggregate build time.
Common situations: Confusing relative error with percentile (passing 0.95 as error); passing 0 expecting 'exact'; unit confusion (passing 100 for percent instead of 0.01-0.99).
Understand the failure class
Background: "Must be a positive integer", "Invalid value", "Unsupported": the invalid-argument-value error family, when a library rejects the value you pass — this error's family across 35 libraries.
Related errors
- missing FORMAT ... ENCODE ...
- missing FORMAT ... ENCODE ...
- Must specify 'connector' in WITH clause
- connector '{}' is not supported
- Expect Array Type
AI-assisted analysis of risingwavelabs/risingwave@6469eb736d (2026-09-11).
Data as JSON: /api/errors/59025ae58d5ad9c8.
Report an issue: GitHub.