{"record":{"id":"7c35c3fd3ad3c667","repo":"apache/iceberg","slug":"classname-does-not-implement-length","errorCode":null,"errorMessage":"<className> does not implement length","messagePattern":"<className> does not implement length","errorType":"exception","errorClass":"UnsupportedOperationException","httpStatus":null,"severity":"warning","filePath":"core/src/main/java/org/apache/iceberg/io/RollingFileWriter.java","lineNumber":88,"sourceCode":"  protected PartitionSpec spec() {\n    return spec;\n  }\n\n  protected StructLike partition() {\n    return partition;\n  }\n\n  public CharSequence currentFilePath() {\n    return currentFile.encryptingOutputFile().location();\n  }\n\n  public long currentFileRows() {\n    return currentFileRows;\n  }\n\n  @Override\n  public long length() {\n    throw new UnsupportedOperationException(\n        this.getClass().getName() + \" does not implement length\");\n  }\n\n  @Override\n  public void write(T row) {\n    currentWriter.write(row);\n    currentFileRows++;\n\n    if (shouldRollToNewFile()) {\n      closeCurrentWriter();\n      openCurrentWriter();\n    }\n  }\n\n  private boolean shouldRollToNewFile() {\n    return currentFileRows % ROWS_DIVISOR == 0 && currentWriter.length() >= targetFileSizeInBytes;\n  }\n","sourceCodeStart":70,"sourceCodeEnd":106,"githubUrl":"https://github.com/apache/iceberg/blob/86d9c8fc543e7c56c9f624eb725f76c9baff9570/core/src/main/java/org/apache/iceberg/io/RollingFileWriter.java#L70-L106","documentation":"RollingFileWriter.length() is not supported: the rolling wrapper does not track the size of its underlying writers and only subclasses that override length() (e.g. file-formats that expose the output file length) support it. Calling it on a base RollingFileWriter instance throws UnsupportedOperationException.","triggerScenarios":"Invoking RollingFileWriter.length() (or code paths such as metadata/statistics collection that query the writer's length) on a subclass that has not overridden length().","commonSituations":"Computing file sizes for metrics or statistics before the file is closed; custom RollingFileWriter subclasses not overriding length(); engine integrations that assume every writer reports a length.","solutions":["Close the rolling writer and call length() on the resulting OutputFile instead (currentFile.encryptingOutputFile().length()).","Track currentFileRows() as a proxy if row count, not byte length, is needed.","Override length() in custom RollingFileWriter subclasses to delegate to the current writer.","Guard the call with instanceof/feature check before invoking length()."],"exampleFix":"// before\nlong size = rollingWriter.length(); // throws UnsupportedOperationException\n\n// after\nrollingWriter.close();\nlong size = rollingWriter.result().length(); // use completed files' lengths","handlingStrategy":"validation","validationCode":"long size(Writer<?> w) {\n  if (w instanceof RollingFileWriter && !(w.getClass().getMethod(\"length\").getDeclaringClass()\n      .isAssignableFrom(RollingFileWriter.class) && w.getClass() != RollingFileWriter.class)) {\n    throw new UnsupportedOperationException(\"length() not supported by \" + w.getClass().getName());\n  }\n  return w.length();\n}","typeGuard":"// check subclass actually overrides length()\nboolean supportsLength(Writer<?> w) {\n  try {\n    return w.getClass().getMethod(\"length\").getDeclaringClass() != RollingFileWriter.class;\n  } catch (NoSuchMethodException e) { return false; }\n}","tryCatchPattern":"try {\n  size = writer.length();\n} catch (UnsupportedOperationException e) {\n  size = -1; // fall back to row count: writer.currentFileRows()\n}","preventionTips":["Prefer currentFileRows() for row counts; use OutputFile.length() after close() for byte sizes","When subclassing RollingFileWriter, always override length() if consumers query sizes","Never compute file sizes before the writer is closed"],"tags":["unsupported-operation","file-writer"],"backgroundTag":"method-not-implemented","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"}