risingwavelabs/risingwave · error · StreamExecutorError
Gap interval must be positive
Error message
Gap interval must be positive
What it means
After the gap interval is resolved (see the null check), the EOWC gap-fill executor validates that the interval is strictly greater than zero using `interval <= Interval::from_month_day_usec(0, 0, 0)`. A zero or negative gap interval would cause the fill loop to make no progress or behave nonsensically, so initialization fails fast with "Gap interval must be positive".
Source
Thrown at src/stream/src/executor/eowc/eowc_gap_fill.rs:370
} = self;
let mut input = input.execute();
let barrier = expect_first_barrier(&mut input).await?;
let first_epoch = barrier.epoch;
yield Message::Barrier(barrier);
this.prev_row_table.init_epoch(first_epoch).await?;
// Calculate and validate gap interval once at initialization
let dummy_row = OwnedRow::new(vec![]);
let interval_datum = this.gap_interval.eval_row_infallible(&dummy_row).await;
let interval = interval_datum
.ok_or_else(|| anyhow::anyhow!("Gap interval expression returned null"))?
.into_interval();
// Validate that gap interval is positive.
if interval <= Interval::from_month_day_usec(0, 0, 0) {
Err(anyhow::anyhow!("Gap interval must be positive"))?;
}
let mut vars = ExecutionVars {
staging_prev_rows: HashMap::new(),
};
#[for_await]
for msg in input {
match msg? {
// Drop the time watermark: a late anchor makes gap fill back-fill below it.
// PARTITION BY column watermarks (if any) pass through unchanged.
Message::Watermark(watermark)
if this.partition_by_indices.contains(&watermark.col_idx) =>
{
yield Message::Watermark(watermark);
}
Message::Watermark(_) => continue,
Message::Chunk(chunk) => {View on GitHub (pinned to 6469eb736d)
Solutions
- Set the gap interval to a strictly positive value, e.g. `INTERVAL '1 minute'`, and recreate the materialized view.
- If the interval comes from application code or a template, validate it is > 0 before generating the SQL.
- If zero gap is intended, remove the gap-fill option entirely instead of passing a zero interval.
- Double-check negative interval strings (`-INTERVAL ...`) and unary minus in generated SQL.
Example fix
// before WITH (gap_interval = INTERVAL '0 seconds') // after WITH (gap_interval = INTERVAL '1 minute')
Defensive patterns
Strategy: validation
Validate before calling
-- Validate the interval is strictly positive before use: SELECT INTERVAL '5 minutes' > INTERVAL '0' AS positive; -- must be true
Prevention
- Validate user-supplied gap intervals are > 0 in application code before generating SQL.
- Use omit-the-option rather than interval 0 to mean 'no gap fill'.
- Check templates for accidental unary minus on intervals.
When it happens
Trigger: Executing a gap-fill query whose constant gap interval evaluates to zero or negative — e.g., `INTERVAL '0 seconds'`, `INTERVAL '-5 minutes'`, or a negative computed literal that survives the constant evaluation.
Common situations: Templated/generated SQL where the interval parameter was substituted as 0 or a negative number; experimenting with gap fill and passing 0 to mean 'no gap' instead of omitting the option; a sign typo in an interval string.
Related errors
- Gap interval expression returned null
- to use iceberg engine table, the variable `iceberg_engine_co
- Scalar subquery might produce more than one row.
- Expected at most 1 clean_watermark_index per table, got {:?}
- Session parameters error: {0}
AI-assisted analysis of risingwavelabs/risingwave@6469eb736d (2026-09-11).
Data as JSON: /api/errors/b470b60a83077798.
Report an issue: GitHub.