pentaho/pentaho-kettle · error · KettleException

Unknown data type for aggregation :

Error message

Unknown data type for aggregation : 

What it means

MemoryGroupBy.newAggregate() builds the aggregate ValueMeta for each aggregation field based on the configured aggregate type. When the aggregate type doesn't match any known MemoryGroupByMeta TYPE_GROUP_* constant (e.g. an out-of-range or unrecognized value), the switch's default branch throws this KettleException naming the offending aggregate field. This is an internal configuration corruption, not a normal user error.

Solutions

  1. Open the transformation in Spoon, inspect the MemoryGroupBy step's aggregation table, and fix the invalid aggregation type dropdown entry.
  2. Re-enter all aggregation rows in the step dialog to regenerate valid type codes, then re-save.
  3. If building MemoryGroupByMeta in code, use MemoryGroupByMeta.getType("...") or the TYPE_GROUP_* constants instead of raw integers.
  4. Diff the .ktr XML (aggregate_type attributes) against a known-good transformation to spot the corrupted value.

Example fix

// before: raw constant, possibly invalid
meta.getAggregateType()[0] = 99;

// after: use defined constants
meta.getAggregateType()[0] = MemoryGroupByMeta.TYPE_GROUP_SUM; // or TYPE_GROUP_COUNT_ALL, etc.
Defensive patterns

Strategy: validation

Validate before calling

int type = meta.getAggregateType()[i];
boolean isValid = type == MemoryGroupByMeta.TYPE_GROUP_SUM
  || type == MemoryGroupByMeta.TYPE_GROUP_AVERAGE
  || type == MemoryGroupByMeta.TYPE_GROUP_COUNT_ALL
  || type == MemoryGroupByMeta.TYPE_GROUP_COUNT_DISTINCT
  || type == MemoryGroupByMeta.TYPE_GROUP_COUNT_ANY
  || type == MemoryGroupByMeta.TYPE_GROUP_MIN
  || type == MemoryGroupByMeta.TYPE_GROUP_MAX
  || type == MemoryGroupByMeta.TYPE_GROUP_FIRST
  || type == MemoryGroupByMeta.TYPE_GROUP_LAST
  || type == MemoryGroupByMeta.TYPE_GROUP_CONCAT_STRING;
if (!isValid) throw new IllegalArgumentException("Invalid aggregate type " + type + " for field " + meta.getAggregateField()[i]);

Type guard

boolean isValidAggregateType(int t) {
  return t >= MemoryGroupByMeta.TYPE_GROUP_SUM && t <= MemoryGroupByMeta.TYPE_GROUP_CONCAT_STRING;
}

Try / catch

try {
  trans.execute(null);
} catch (KettleException e) {
  if (e.getMessage() != null && e.getMessage().startsWith("Unknown data type for aggregation")) {
    logError("Corrupt aggregate type in MemoryGroupBy step; re-open and re-save the step in Spoon", e);
  }
  throw e;
}

Prevention

When it happens

Trigger: A MemoryGroupBy step whose aggregateType[i] array contains a value that is not one of the defined TYPE_GROUP_* constants — usually from deserializing a corrupted/hand-edited transformation XML or repository record, or programmatic meta construction using a wrong integer constant.

Common situations: Manually editing the .ktr XML and mistyping the aggregate type; transformations written by a different plugin version where type codes shifted; Java code building MemoryGroupByMeta and passing an invalid type int; XML/repo corruption after a failed save.

Understand the failure class

Background: Invalid enum value errors: "Unknown type", "Invalid scope", "must be one of" — when a string is not on the library's allowed list — this error's family across 23 libraries.

Related errors


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

Appendix: source

Thrown at engine/src/main/java/org/pentaho/di/trans/steps/memgroupby/MemoryGroupBy.java:472

        case MemoryGroupByMeta.TYPE_GROUP_LAST:
        case MemoryGroupByMeta.TYPE_GROUP_FIRST_INCL_NULL:
        case MemoryGroupByMeta.TYPE_GROUP_LAST_INCL_NULL:
        case MemoryGroupByMeta.TYPE_GROUP_MIN:
        case MemoryGroupByMeta.TYPE_GROUP_MAX:
          vMeta = subjMeta.clone();
          vMeta.setName( meta.getAggregateField()[i] );
          v = r == null ? null : r[data.subjectnrs[i]];
          break;
        case MemoryGroupByMeta.TYPE_GROUP_CONCAT_COMMA:
          vMeta = new ValueMetaString( meta.getAggregateField()[i] );
          v = new StringBuilder();
          break;
        case MemoryGroupByMeta.TYPE_GROUP_CONCAT_STRING:
          vMeta = new ValueMetaString( meta.getAggregateField()[i] );
          v = new StringBuilder();
          break;
        default:
          throw new KettleException( "Unknown data type for aggregation : " + meta.getAggregateField()[i] );
      }

      if ( meta.getAggregateType()[i] != MemoryGroupByMeta.TYPE_GROUP_COUNT_ALL
        && meta.getAggregateType()[i] != MemoryGroupByMeta.TYPE_GROUP_COUNT_DISTINCT
        && meta.getAggregateType()[i] != MemoryGroupByMeta.TYPE_GROUP_COUNT_ANY ) {
        vMeta.setLength( subjMeta.getLength(), subjMeta.getPrecision() );
      }
      if ( aggregate == null ) {
        data.aggMeta.addValueMeta( vMeta );
      } else {
        aggregate.agg[i] = v;
      }
    }
  }

  private void initGroupMeta( RowMetaInterface previousRowMeta ) throws KettleValueException {
    data.groupMeta = new RowMeta();
    data.entryMeta = new RowMeta();

View on GitHub (pinned to f3058517a1)