risingwavelabs/risingwave · critical

multiple clean watermark columns are not supported yet

Error message

multiple clean watermark columns are not supported yet

What it means

When constructing a `StateTable` from a `TableCatalog`, RisingWave supports at most one column designated as a clean watermark column. If the catalog declares more than one (`get_clean_watermark_column_indices().len() > 1`), `unimplemented!` panics because the state table's watermark-rewrite machinery only handles a single clean watermark index. This is a feature-completeness guard, not a data corruption error.

Source

Thrown at src/stream/src/common/table/state_table.rs:829

            table_catalog
                .get_dist_key_in_pk()
                .iter()
                .map(|idx| *idx as usize)
                .collect()
        };

        let vnode_col_idx_in_pk = table_catalog.vnode_col_index.as_ref().and_then(|idx| {
            let vnode_col_idx = *idx as usize;
            pk_indices.iter().position(|&i| vnode_col_idx == i)
        });
        let value_indices = table_catalog
            .value_indices
            .iter()
            .map(|val| *val as usize)
            .collect_vec();
        let clean_watermark_indices = table_catalog.get_clean_watermark_column_indices();
        if clean_watermark_indices.len() > 1 {
            unimplemented!("multiple clean watermark columns are not supported yet")
        }
        let clean_watermark_index = clean_watermark_indices.first().map(|&i| i as usize);

        Self {
            table_id,
            table_name_for_debug: table_catalog.name.clone(),
            table_columns,
            order_types,
            pk_indices,
            dist_key_in_pk_indices,
            vnode_col_idx_in_pk,
            expected_vnode_count: table_catalog.vnode_count(),
            value_indices,
            prefix_hint_len: table_catalog.read_prefix_len_hint as usize,
            retention_seconds: table_catalog.retention_seconds,
            versioned: table_catalog.version.is_some(),
            fragment_id: table_catalog.fragment_id,
            clean_watermark_index,

View on GitHub (pinned to 6469eb736d)

Solutions

  1. Redesign the table/MV to define at most one watermark column; pick the single column that should drive watermark cleaning.
  2. If multiple watermark columns are truly needed, check RisingWave release notes/roadmap for multi-clean-watermark support and upgrade.
  3. Inspect the generated catalog (`SHOW CREATE ...` or the meta catalog dump) to find which planner step added the extra clean watermark column, and adjust the query.
  4. This is a panic (unimplemented), so it cannot be caught at runtime — it must be fixed at the catalog/query level.

Example fix

-- before
CREATE MATERIALIZED VIEW mv WITH (watermark = ts_a) AS SELECT ... ; -- plus a second watermark column added internally
-- after
CREATE MATERIALIZED VIEW mv WITH (watermark = ts_a) AS SELECT ts_a, ts_b, ... ; -- only one clean watermark column
Defensive patterns

Strategy: validation

Validate before calling

// Check the catalog before building the state table
let n = table_catalog.get_clean_watermark_column_indices().len();
if n > 1 {
    return Err(format!("table '{}' has {n} clean watermark columns; only 1 is supported", table_catalog.name));
}

Type guard

// Rust
fn has_single_clean_watermark(catalog: &TableCatalog) -> bool {
    catalog.get_clean_watermark_column_indices().len() == 1
}

Try / catch

// This panics via unimplemented! and cannot be caught — validate the catalog beforehand.
// Wrap table construction behind a pre-check:
if !has_single_clean_watermark(&catalog) {
    return Err(StreamExecutorError::from(anyhow!("multi clean watermark table not supported")));
}
let table = StateTable::from_table_catalog(&catalog);

Prevention

When it happens

Trigger: Creating a table, materialized view, or sink whose `TableCatalog` has two or more columns flagged as clean watermark columns — e.g. a MV with multiple watermark definitions used as a state table.

Common situations: SQL like `CREATE MATERIALIZED VIEW ... WITH (watermark = ...)` on multiple columns feeding one state table, or internal catalog construction that sets clean watermark columns on more than one value column; attempting features not yet supported by the current RisingWave version.

Understand the failure class

Background: UnsupportedOperationException and "is not supported" errors: when a library deliberately refuses a call — this error's family across 30 libraries.

Related errors


AI-assisted analysis of risingwavelabs/risingwave@6469eb736d (2026-09-11). Data as JSON: /api/errors/c09739249753524d. Report an issue: GitHub.