pentaho/pentaho-kettle · error · KettleException
SalesforceInput.Exception.CanNotReadFromSalesforce
Error message
SalesforceInput.Exception.CanNotReadFromSalesforce
What it means
SalesforceInput wraps any Exception thrown while producing a row inside getOneRow() into a KettleException with the message 'Can not read from Salesforce'. getOneRow() builds the output row (from the query result or field defaults) and clones the previous row; if anything fails there (typically a problem evaluating field mappings against the current row), this error is raised to the transformation runtime.
Solutions
- Inspect the wrapped 'cause' exception in the Kettle log — this message is only a wrapper; the root cause names the real failure
- Verify all fields configured in the Salesforce Input step exist in the incoming row stream
- Run the transformation with detailed logging and check the row being processed when the error occurs
- Test the transformation with a sample of the actual input rows to reproduce the failing row
Example fix
// before
String value = row.getString("Amount"); // throws if field missing
// after
int idx = getInputRowMeta().indexOfValue("Amount");
String value = idx >= 0 ? row.getString(idx) : null; Defensive patterns
Strategy: try-catch
Validate before calling
int idx = transMeta.getPrevStepFields(stepMeta).indexOfValue(fieldName);
if (idx < 0) throw new IllegalStateException("Missing input field: " + fieldName); Try / catch
try {
trans.execute(null);
} catch (KettleException e) {
Throwable root = e;
while (root.getCause() != null) root = root.getCause();
log.error("SalesforceInput row processing failed: {}", root.getMessage(), root);
} Prevention
- Always verify upstream field names match the Salesforce Input step's field mappings before running
- Keep the wrapped cause chain in logs, not just the wrapper message
- Test transformations with representative production data samples
When it happens
Trigger: Any Exception inside getOneRow() during processRow: e.g. a mapped input field expression fails on the current row, outputRowData construction throws, or irow.cloneRow() fails on a malformed/absent input row meta.
Common situations: Transformation with a field lookup/mapping that references a value not present in the incoming row; null input row meta on the first batch; a step upstream emitting unexpected data types.
Related errors
- SalesforceInsert.Error
- SalesforceInsert.log.Exception
- AbsSecurityManager.ERROR_0004_UNABLE_TO_APPLY_LOGICAL_ROLES_TO_RUNTIME_ROLE
- Calculator.ErrorInStepRunning
- e
AI-assisted analysis of pentaho/pentaho-kettle@f3058517a1 (2026-09-13).
Data as JSON: /api/errors/87df2190322ab94d.
Report an issue: GitHub.
Appendix: source
Thrown at plugins/salesforce/core/src/main/java/org/pentaho/di/trans/steps/salesforceinput/SalesforceInput.java:255
// See if we need to add the server timestamp to the row...
if ( meta.includeTimestamp() && !Utils.isEmpty( meta.getTimestampField() ) ) {
outputRowData[rowIndex++] = data.connection.getServerTimestamp();
}
// See if we need to add the row number to the row...
if ( meta.includeRowNumber() && !Utils.isEmpty( meta.getRowNumberField() ) ) {
outputRowData[rowIndex++] = new Long( data.rownr );
}
if ( meta.includeDeletionDate() && !Utils.isEmpty( meta.getDeletionDateField() ) ) {
outputRowData[rowIndex++] = srvalue.getDeletionDate();
}
RowMetaInterface irow = getInputRowMeta();
data.previousRow = irow == null ? outputRowData : irow.cloneRow( outputRowData ); // copy it to make
} catch ( Exception e ) {
throw new KettleException( BaseMessages
.getString( PKG, "SalesforceInput.Exception.CanNotReadFromSalesforce" ), e );
}
return outputRowData;
}
// DO CONVERSIONS...
void doConversions( Object[] outputRowData, int i, String value ) throws KettleValueException {
ValueMetaInterface targetValueMeta = data.outputRowMeta.getValueMeta( i );
ValueMetaInterface sourceValueMeta = data.convertRowMeta.getValueMeta( i );
if ( ValueMetaInterface.TYPE_BINARY != targetValueMeta.getType() ) {
outputRowData[i] = targetValueMeta.convertData( sourceValueMeta, value );
} else {
// binary type of salesforce requires specific conversion
if ( value != null ) {
outputRowData[ i ] = Base64.decode( value );
} else {View on GitHub (pinned to f3058517a1)