apache/iceberg · error · UncheckedSQLException

Failed to execute exists query: %s

Error message

Failed to execute exists query: %s

What it means

JdbcUtil.exists runs a user-supplied existence query (tableExists, viewExists, namespaceExists) inside interruptible SQL execution. Any SQLException is wrapped in UncheckedSQLException as 'Failed to execute exists query: <sql>' so callers see the exact SQL that failed alongside the driver's cause. It indicates the catalog metadata database could not answer the existence probe.

Source

Thrown at core/src/main/java/org/apache/iceberg/jdbc/JdbcUtil.java:829

    try {
      return connections.run(
          conn -> {
            try (PreparedStatement preparedStatement = conn.prepareStatement(sql)) {
              for (int pos = 0; pos < args.length; pos += 1) {
                preparedStatement.setString(pos + 1, args[pos]);
              }

              try (ResultSet rs = preparedStatement.executeQuery()) {
                if (rs.next()) {
                  return true;
                }
              }
            }

            return false;
          });
    } catch (SQLException e) {
      throw new UncheckedSQLException(e, "Failed to execute exists query: %s", sql);
    } catch (InterruptedException e) {
      Thread.currentThread().interrupt();
      throw new UncheckedInterruptedException(e, "Interrupted in SQL query");
    }
  }
}

View on GitHub (pinned to 86d9c8fc54)

Solutions

  1. Inspect the chained SQLException cause for the vendor error code (connection refused, unknown table, access denied)
  2. Initialize the JDBC catalog schema (run the DDL that creates jdbc_tables/jdbc_namespaces) on the target DB
  3. Check DB connectivity and credentials in the jdbc catalog properties (uri, user, password)
  4. Grant SELECT on the catalog tables to the configured DB user; verify the schema-version property matches the DB layout

Example fix

// before
JdbcCatalog catalog = new JdbcCatalog(); // configured against empty DB
catalog.tableExists(ident); // UncheckedSQLException: Failed to execute exists query
// after
// pre-create catalog schema, e.g. for Postgres:
// CREATE TABLE IF NOT EXISTS jdbc_tables (...); CREATE TABLE IF NOT EXISTS jdbc_namespaces (...);
JdbcCatalog catalog = catalogWithInitializedDb();
Defensive patterns

Strategy: try-catch

Validate before calling

// before catalog ops, verify DB reachable:
try (Connection c = DriverManager.getConnection(jdbcUri, user, pass)) { /* simple SELECT 1 */ }

Try / catch

try { catalog.tableExists(identifier); } catch (UncheckedSQLException e) { SQLException cause = (SQLException) e.getCause(); LOG.error("exists query failed: state={} code={}", cause.getSQLState(), cause.getErrorCode(), cause); }

Prevention

When it happens

Trigger: Catalog DB unreachable or credentials expired when checking tableExists/viewExists/namespaceExists; the underlying catalog table (jdbc_tables/jdbc_namespaces) missing from a not-yet-initialized DB; SQL syntax/dialect error in the versioned query (schema V0 vs V1 mismatch); permissions lacking SELECT.

Common situations: Fresh JDBC catalog pointing at an empty database; Postgres/MySQL user without grants; network blip between compute engine and metadata DB; driver upgrade changing error semantics.

Understand the failure class

Background: "query failed", "%w: SQL error" — wrapped database query errors in Go libraries explained — this error's family across 3 libraries.

Related errors


AI-assisted analysis of apache/iceberg@86d9c8fc54 (2026-09-12). Data as JSON: /api/errors/896dd991bcac190e. Report an issue: GitHub.