pentaho/pentaho-kettle · error · KettleDatabaseException

MySQLDatabaseMeta.Exception.LegacyColumnNameNoDBMetaDataException

MySQLDatabaseMeta.Exception.LegacyColumnNameNoDBMetaDataException

Error message

MySQLDatabaseMeta.Exception.LegacyColumnNameNoDBMetaDataException (localized via BaseMessages)

What it means

Thrown by MariaDBDatabaseMeta.getLegacyColumnName when the JDBC DatabaseMetaData argument is null. The method resolves a legacy column name/label from result set metadata, which requires the database metadata (e.g. driver version checks) to be present, so a null argument is treated as a programming/configuration error and wrapped in a KettleDatabaseException with a localized message.

Solutions

  1. Ensure the java.sql.Connection is open and call connection.getMetaData() before invoking getLegacyColumnName, aborting early if it returns null
  2. Check the caller that produced the DatabaseMetaData — fix it to propagate a real connection instead of null
  3. If metadata is genuinely unavailable, fall back to ResultSetMetaData-only logic or skip legacy name resolution rather than calling this method

Example fix

// before
String label = meta.getLegacyColumnName(null, rsMetaData, index);
// after
DatabaseMetaData dbMetaData = connection.getMetaData();
if (dbMetaData != null) {
  String label = meta.getLegacyColumnName(dbMetaData, rsMetaData, index);
}
Defensive patterns

Strategy: type-guard

Validate before calling

DatabaseMetaData dbMeta = connection != null ? connection.getMetaData() : null;
if (dbMeta == null) throw new IllegalStateException("No DatabaseMetaData: connection closed or invalid");

Type guard

function hasDbMetaData(Connection c) { try { return c != null && c.getMetaData() != null; } catch (SQLException e) { return false; } }

Try / catch

try {
  String label = meta.getLegacyColumnName(dbMetaData, rsMetaData, index);
} catch (KettleDatabaseException e) {
  log.error("No DB metadata available for legacy column lookup", e);
}

Prevention

When it happens

Trigger: Calling getLegacyColumnName(dbMetaData=null, rsMetaData, index) — typically when a caller obtained no DatabaseMetaData from a Connection (e.g. connection closed or getMetaData() returned null) and passes it straight through.

Common situations: Custom database plugin or fork code invoking the legacy column-name API without first acquiring DatabaseMetaData; a broken/closed JDBC connection returning null metadata; mocking frameworks injecting null metadata in tests.

Related errors


AI-assisted analysis of pentaho/pentaho-kettle@f3058517a1 (2026-09-13). Data as JSON: /api/errors/0da621d76b4a726c. Report an issue: GitHub.

Appendix: source

Thrown at core/src/main/java/org/pentaho/di/core/database/MariaDBDatabaseMeta.java:64

  }

  @Override public boolean fullExceptionLog( Exception e ) {
    Throwable cause = ( e == null ? null : e.getCause() );
    return !( cause != null && SHORT_MESSAGE_EXCEPTIONS.contains( cause.getClass().getName() ) );
  }

  /**
   * Returns the column name for a MariaDB field.
   *
   * @param dbMetaData
   * @param rsMetaData
   * @param index
   * @return The column label.
   * @throws KettleDatabaseException
   */
  @Override public String getLegacyColumnName( DatabaseMetaData dbMetaData, ResultSetMetaData rsMetaData, int index ) throws KettleDatabaseException {
    if ( dbMetaData == null ) {
      throw new KettleDatabaseException( BaseMessages.getString( PKG, "MySQLDatabaseMeta.Exception.LegacyColumnNameNoDBMetaDataException" ) );
    }

    if ( rsMetaData == null ) {
      throw new KettleDatabaseException( BaseMessages.getString( PKG, "MySQLDatabaseMeta.Exception.LegacyColumnNameNoRSMetaDataException" ) );
    }

    try {
      return rsMetaData.getColumnLabel( index );
    } catch ( Exception e ) {
      throw new KettleDatabaseException( String.format( "%s: %s", BaseMessages.getString( PKG, "MySQLDatabaseMeta.Exception.LegacyColumnNameException" ), e.getMessage() ), e );
    }
  }
}

View on GitHub (pinned to f3058517a1)