risingwavelabs/risingwave · error · CatalogError

{object_type} not found: {name}

Error message

{object_type} not found: {name}

What it means

CatalogError::NotFound is the frontend catalog's error for looking up an object (table, schema, database, function, etc.) by name that does not exist. It carries the object type and the missing name and is mapped to a Postgres error code; the TODO notes more concrete codes are planned.

Source

Thrown at src/frontend/src/catalog/mod.rs:111

/// Check if modifications happen to system catalog.
pub fn check_schema_writable(schema: &str) -> Result<()> {
    if is_system_schema(schema) {
        Err(ErrorCode::ProtocolError(format!(
            "permission denied to write on \"{}\", System catalog modifications are currently disallowed.",
            schema
        )).into())
    } else {
        Ok(())
    }
}

pub type CatalogResult<T> = std::result::Result<T, CatalogError>;

// TODO(error-handling): provide more concrete error code for different object types.
#[derive(Error, Debug, thiserror_ext::Box)]
#[thiserror_ext(newtype(name = CatalogError, extra_provide = Self::provide_postgres_error_code))]
pub enum CatalogErrorInner {
    #[error("{object_type} not found: {name}")]
    NotFound {
        object_type: &'static str,
        name: String,
    },

    #[error(
        "{object_type} named {name} already exists{}",
        if *.under_creation { " and is still being created" } else { "" },
    )]
    Duplicated {
        object_type: &'static str,
        name: String,
        under_creation: bool, // only used for StreamingJob type and Subscription for now
    },
}

impl CatalogError {
    /// Provide the Postgres error code for the error.

View on GitHub (pinned to 6469eb736d)

Solutions

  1. Verify the object name and its spelling, including case sensitivity (quote identifiers if needed).
  2. Check you are connected to the right database and that search_path includes the object's schema (`SHOW SCHEMAS`, `SHOW TABLES`).
  3. Confirm the object exists and creation completed before querying it.
  4. If the name is built dynamically, validate existence with catalog views before executing the statement.

Example fix

-- before
SELECT * FROM result;
-- after
SELECT * FROM public.result; -- or fix the typo after SHOW TABLES
Defensive patterns

Strategy: validation

Validate before calling

const exists = await client.query(
  "SELECT 1 FROM rw_tables WHERE name = $1", [tableName]);
if (exists.rows.length === 0) throw new Error(`table ${tableName} missing`);

Type guard

function objectExists(rows) { return Array.isArray(rows) && rows.length > 0; }

Try / catch

try {
  await client.query(`SELECT * FROM ${ident}`);
} catch (e) {
  if (String(e.message).endsWith("not found: " + ident)) {
    // create the object or correct the name
  } else throw e;
}

Prevention

When it happens

Trigger: Querying, altering, or dropping an object whose name is not in the catalog: `SELECT * FROM missing_table`, `DROP TABLE t`, `DESCRIBE unknown_view`, resolving table/function references during binding when the catalog reader cannot find the entry.

Common situations: Typos in table or schema names; querying before a MV/table finished creation; wrong database or search_path; object dropped by another session; case-sensitivity issues with quoted identifiers.

Understand the failure class

Background: 'Could not be found', 'does not exist', 'not found in database': the resource-not-found family when an ID, slug, key, or URI lookup comes back empty — this error's family across 20 libraries.

Related errors


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