pentaho/pentaho-kettle · error · KettleException

DynamicSQLRow.Exception.FieldNotFound

Error message

DynamicSQLRow.Exception.FieldNotFound

What it means

On the first row, DynamicSQLRow.processRow resolves the configured SQL field name to an index in the input row metadata; if the field is absent from the incoming row it throws this KettleException saying the field is unreachable. The step cannot extract the SQL statement from the row without it.

Solutions

  1. Set the 'SQL fieldname' in the step dialog to a field that actually exists upstream
  2. Add/repair the upstream step (e.g. 'Add constants', JavaScript) to produce the SQL text field
  3. Check with a 'Stream lookup'/preview that the field name matches exactly (case included)
  4. Re-save and re-run after upstream changes

Example fix

// before
step configured with sql fieldname 'query' but upstream emits 'sql_text'
// after
configure sql fieldname = 'sql_text' (matching the upstream field)
Defensive patterns

Strategy: validation

Validate before calling

// Ensure the configured field exists in the incoming stream:
String field = meta.getSQLFieldName();
if (field == null || inputRowMeta.indexOfValue(field) < 0) {
  throw new IllegalStateException("Field '" + field + "' not present in input stream");
}

Try / catch

try {
  lookupValues(inputRowMeta, row);
} catch (KettleException e) {
  logError("SQL field not found in input: check upstream steps", e);
  stopAll(); setErrors(1);
  return false;
}

Prevention

When it happens

Trigger: At runtime when getInputRowMeta().indexOfValue(sqlFieldName) returns -1 — the field named in the step settings is not present in the row arriving from the previous step (renamed, removed, or wrong name configured).

Common situations: Upstream step renamed or dropped the field; typo in the SQL fieldname setting; inserting a Select values step that removes the field; case-sensitivity differences.

Understand the failure class

Background: Record Not Found Errors: "not found", RecordNotFound, and "was not found" — what they mean and how to fix them — this error's family across 28 libraries.

Related errors


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

Appendix: source

Thrown at engine/src/main/java/org/pentaho/di/trans/steps/dynamicsqlrow/DynamicSQLRow.java:230

    if ( r == null ) { // no more input to be expected...
      setOutputDone();
      return false;
    }
    if ( first ) {
      if ( Utils.isEmpty( meta.getSQLFieldName() ) ) {
        throw new KettleException( BaseMessages.getString( PKG, "DynamicSQLRow.Exception.SQLFieldNameEmpty" ) );
      }

      if ( Utils.isEmpty( meta.getSql() ) ) {
        throw new KettleException( BaseMessages.getString( PKG, "DynamicSQLRow.Exception.SQLEmpty" ) );
      }

      // cache the position of the field
      if ( data.indexOfSQLField < 0 ) {
        data.indexOfSQLField = getInputRowMeta().indexOfValue( meta.getSQLFieldName() );
        if ( data.indexOfSQLField < 0 ) {
          // The field is unreachable !
          throw new KettleException( BaseMessages.getString( PKG, "DynamicSQLRow.Exception.FieldNotFound", meta
            .getSQLFieldName() ) );
        }
      }
    }
    try {
      lookupValues( getInputRowMeta(), r );

      if ( checkFeedback( getLinesRead() ) ) {
        if ( log.isDetailed() ) {
          logDetailed( BaseMessages.getString( PKG, "DynamicSQLRow.Log.LineNumber" ) + getLinesRead() );
        }
      }
    } catch ( KettleException e ) {
      boolean sendToErrorRow = false;
      String errorMessage = null;

      if ( getStepMeta().isDoingErrorHandling() ) {
        sendToErrorRow = true;

View on GitHub (pinned to f3058517a1)