pentaho/pentaho-kettle · error · KettleStepException
Unable to convert a value to integer while calculating the…
Error message
Unable to convert a value to integer while calculating the partition number
What it means
BaseStep.putError/partitioning code computes the partition number for a row by calling Partitioner.getPartition(rowMeta, row), which must convert a partitioning field value to an integer. When the field value cannot be converted (KettleValueException wrapped in KettleException), BaseStep rethrows it as a KettleStepException with this message. It means the row's partitioning column holds data that is not a valid integer.
Solutions
- Point the partitioner at a field that is guaranteed Integer type (add a 'Select values' / 'Fields select' or Calculator step to convert it beforehand).
- If partitioning on strings, ensure the mapping field contains only numeric strings, or switch to a partitioner that handles the type.
- Clean/null-guard the data upstream: filter or default rows whose partition field is null or non-numeric.
- Catch KettleStepException in a calling routine and inspect the cause (KettleValueException) to identify the offending row/field via row logging.
Example fix
// before (partitioning on a string field directly)
partitioner.setFieldName("order_id_text");
// after (convert to Integer before the partitioned step)
// Add a Calculator/SelectValues step: order_id_text -> Integer order_id
partitioner.setFieldName("order_id"); Defensive patterns
Strategy: validation
Validate before calling
// Java: validate partition field before putRow
Object val = row[getFieldIndex(rowMeta, "partitionField")];
if (val == null || !(val instanceof Number) ) {
throw new IllegalArgumentException("partitionField must be a numeric integer");
} Type guard
boolean isValidPartitionValue(Object v) {
return v instanceof Integer || (v instanceof Number && ((Number) v).doubleValue() == Math.floor(((Number) v).doubleValue()));
} Try / catch
try {
putRow(rowMeta, row);
} catch (KettleStepException e) {
if (e.getMessage().contains("Unable to convert a value to integer")) {
logError("Bad partition key in row: " + Arrays.toString(row), e);
// route to error handling or skip
} else { throw e; }
} Prevention
- Always partition on Integer-typed fields
- Add a value-conversion step before the partitioned step
- Null-guard or filter rows with missing partition keys
When it happens
Trigger: A step is partitioned (e.g. mod partitioning) across multiple copies and the field used as the partitioning key contains a non-integer value (string text, null handling, decimal, or out-of-range number) for the current row, so getPartition() throws while converting it to int.
Common situations: Partitioning on a String field that contains text instead of numbers; using a field with a different type than expected after an upstream step changed metadata; partitioning on a Number field with fractional values; nulls or locale-formatted numbers.
Understand the failure class
Background: "Must be a positive integer", "Invalid value", "Unsupported": the invalid-argument-value error family, when a library rejects the value you pass — this error's family across 35 libraries.
Related errors
- : can't be converted to an Internet Address
- ERROR_ARITHMETIC_VALUE
- Error converting data while looking up value
- : I don't know how to convert a binary value to Internet…
- : I don't know how to convert a binary value to timestamp.
AI-assisted analysis of pentaho/pentaho-kettle@f3058517a1 (2026-09-13).
Data as JSON: /api/errors/927dd6c907384177.
Report an issue: GitHub.
Appendix: source
Thrown at engine/src/main/java/org/pentaho/di/trans/step/BaseStep.java:1379
private void specialPartitioning( RowMetaInterface rowMeta, Object[] row ) throws KettleStepException {
if ( nextStepPartitioningMeta == null ) {
// Look up the partitioning of the next step.
// This is the case for non-clustered partitioning...
//
List<StepMeta> nextSteps = transMeta.findNextSteps( stepMeta );
if ( nextSteps.size() > 0 ) {
nextStepPartitioningMeta = nextSteps.get( 0 ).getStepPartitioningMeta();
}
// TODO: throw exception if we're not partitioning yet.
// For now it throws a NP Exception.
}
int partitionNr;
try {
partitionNr = nextStepPartitioningMeta.getPartition( rowMeta, row );
} catch ( KettleException e ) {
throw new KettleStepException(
"Unable to convert a value to integer while calculating the partition number", e );
}
RowSet selectedRowSet = null;
if ( clusteredPartitioningFirst ) {
clusteredPartitioningFirst = false;
// We are only running remotely if both the distribution is there AND if the distribution is actually contains
// something.
//
clusteredPartitioning =
transMeta.getSlaveStepCopyPartitionDistribution() != null
&& !transMeta.getSlaveStepCopyPartitionDistribution().getDistribution().isEmpty();
}
// OK, we have a SlaveStepCopyPartitionDistribution in the transformation...
// We want to pre-calculate what rowset we're sending data to for which partition...View on GitHub (pinned to f3058517a1)