{"record":{"id":"acc9a2eeb0f122ff","repo":"apache/iceberg","slug":"cannot-get-value-for-invalid-index-index","errorCode":null,"errorMessage":"Cannot get value for invalid index: <index>","messagePattern":"Cannot get value for invalid index: <index>","errorType":"exception","errorClass":"IllegalArgumentException","httpStatus":null,"severity":"error","filePath":"parquet/src/main/java/org/apache/iceberg/parquet/ParquetValueWriters.java","lineNumber":733,"sourceCode":"\n  public static class PositionDeleteStructWriter<R> extends StructWriter<PositionDelete<R>> {\n    private final Function<CharSequence, ?> pathTransformFunc;\n\n    public PositionDeleteStructWriter(\n        StructWriter<?> replacedWriter, Function<CharSequence, ?> pathTransformFunc) {\n      super(Arrays.asList(replacedWriter.writers));\n      this.pathTransformFunc = pathTransformFunc;\n    }\n\n    @Override\n    protected Object get(PositionDelete<R> delete, int index) {\n      switch (index) {\n        case 0:\n          return pathTransformFunc.apply(delete.path());\n        case 1:\n          return delete.pos();\n      }\n      throw new IllegalArgumentException(\"Cannot get value for invalid index: \" + index);\n    }\n  }\n\n  /** Returns a mapping from writer index to field index, skipping Unknown columns. */\n  static int[] writerToFieldIndex(Types.StructType struct, int numWriters) {\n    if (null == struct) {\n      return IntStream.rangeClosed(0, numWriters).toArray();\n    }\n\n    List<Types.NestedField> recordFields = struct.fields();\n\n    // value writer index to record field index\n    int[] indexes = new int[numWriters];\n    int writerIndex = 0;\n    for (int pos = 0; pos < recordFields.size(); pos += 1) {\n      if (recordFields.get(pos).type().typeId() != org.apache.iceberg.types.Type.TypeID.UNKNOWN) {\n        indexes[writerIndex] = pos;\n        writerIndex += 1;","sourceCodeStart":715,"sourceCodeEnd":751,"githubUrl":"https://github.com/apache/iceberg/blob/86d9c8fc543e7c56c9f624eb725f76c9baff9570/parquet/src/main/java/org/apache/iceberg/parquet/ParquetValueWriters.java#L715-L751","documentation":"Thrown by a positional accessor (e.g. the delete-vector record reader's get) when asked for a value at an index that the underlying structure does not have. These composite readers only expose a fixed number of positional fields (here 0 and 1 for path and pos of a delete); any other index is invalid and raises IllegalArgumentException.","triggerScenarios":"Calling get(int index) on the reader's internal position-accessor with an index other than 0 or 1, usually from code that assumes a different field layout or passes a writer/field index computed against a different struct type.","commonSituations":"Positional deletes/vectorized delete readers where the writer-index mapping is off by the number of columns; code changes adding columns without updating the switch; generic code iterating indices beyond the record width.","solutions":["Only access indices 0..numFields-1 of the composite reader; verify the index against the struct width","Update the switch mapping if new fields (e.g. sequence numbers) were added to the delete schema","Check the writerToFieldIndex mapping when Unknown columns are skipped so indices align"],"exampleFix":"// before: blindly accessing a third column\nObject seq = reader.get(2);\n// after: guard the index\nif (index >= 0 && index < numFields) { value = reader.get(index); }","handlingStrategy":"type-guard","validationCode":"if (index < 0 || index >= reader.numFields()) {\n  throw new IndexOutOfBoundsException(\"reader index \" + index + \" out of range\");\n}","typeGuard":"boolean isValidIndex(int index, int numFields) { return index >= 0 && index < numFields; }","tryCatchPattern":"try {\n  value = accessor.get(index);\n} catch (IllegalArgumentException e) {\n  if (e.getMessage().startsWith(\"Cannot get value for invalid index\")) {\n    // re-map index via writerToFieldIndex before retrying\n  } else throw e;\n}","preventionTips":["Compute indices from the struct type, never hardcode","Use writerToFieldIndex when Unknown columns are skipped","Update composite readers when delete schema columns change"],"tags":["parquet","indexing","deletes"],"backgroundTag":"index-out-of-range","analyzedSha":"86d9c8fc543e7c56c9f624eb725f76c9baff9570","analyzedAt":"2026-09-12T00:46:39.097Z","contentChangedAt":"2026-09-12T00:46:39.097Z","schemaVersion":2},"datasetVersion":"2026-09-23T08:17:48.524Z"}