{"record":{"id":"46117c531d7b5e91","repo":"apache/iceberg","slug":"unsupported-file-content-type-file-content","errorCode":null,"errorMessage":"Unsupported file content type: ${file.content()}","messagePattern":"Unsupported file content type: (.+?)","errorType":"exception","errorClass":"UnsupportedOperationException","httpStatus":null,"severity":"error","filePath":"core/src/main/java/org/apache/iceberg/SnapshotSummary.java","lineNumber":314,"sourceCode":"          this.addedRecords += file.recordCount();\n          break;\n        case POSITION_DELETES:\n          DeleteFile deleteFile = (DeleteFile) file;\n          if (ContentFileUtil.isDV(deleteFile)) {\n            this.addedDVs += 1;\n          } else {\n            this.addedPosDeleteFiles += 1;\n          }\n          this.addedDeleteFiles += 1;\n          this.addedPosDeletes += file.recordCount();\n          break;\n        case EQUALITY_DELETES:\n          this.addedDeleteFiles += 1;\n          this.addedEqDeleteFiles += 1;\n          this.addedEqDeletes += file.recordCount();\n          break;\n        default:\n          throw new UnsupportedOperationException(\n              \"Unsupported file content type: \" + file.content());\n      }\n    }\n\n    void removedFile(ContentFile<?> file) {\n      this.removedSize += ScanTaskUtil.contentSizeInBytes(file);\n      switch (file.content()) {\n        case DATA:\n          this.removedFiles += 1;\n          this.deletedRecords += file.recordCount();\n          break;\n        case POSITION_DELETES:\n          DeleteFile deleteFile = (DeleteFile) file;\n          if (ContentFileUtil.isDV(deleteFile)) {\n            this.removedDVs += 1;\n          } else {\n            this.removedPosDeleteFiles += 1;\n          }","sourceCodeStart":296,"sourceCodeEnd":332,"githubUrl":"https://github.com/apache/iceberg/blob/86d9c8fc543e7c56c9f624eb725f76c9baff9570/core/src/main/java/org/apache/iceberg/SnapshotSummary.java#L296-L332","documentation":"SnapshotSummary.Builder.addedFile throws UnsupportedOperationException when a ContentFile whose content() is not DATA, POSITION_DELETES, or EQUALITY_DELETES is added to a snapshot summary. Iceberg's FileContent enum is closed, so any unknown value (e.g. from a newer spec or a corrupted/bespoke file implementation) cannot be summarized. It indicates the summary builder encountered a file content type it does not recognize.","triggerScenarios":"Calling appendFiles/overwriteFiles (which route through updatePartitions -> addedFile) with a ContentFile whose FileContent is a value outside the three known enum constants — typically a custom ContentFile implementation, an enum from a future spec version, or deserialization of a file with content=null.","commonSituations":"Custom catalog/FileIO integrations that hand-construct DataFile/DeleteFile objects with the wrong or unset content field; forward-compatibility issues when reading metadata produced by a newer Iceberg spec; test fixtures that mock ContentFile and return an unexpected content().","solutions":["Fix the ContentFile construction so content() returns a valid FileContent (FileContent.DATA for appends, FileContent.POSITION_DELETES or FileContent.EQUALITY_DELETES for delete files).","If the file comes from serialized metadata, verify it was written by a compatible Iceberg version and re-write with a supported writer.","If you implement a custom ContentFile wrapper, delegate content() to the wrapped file instead of returning a custom/unknown value.","Check for null content(): pass through the correct typed interface (DataFile vs DeleteFile) rather than a generic ContentFile when appending."],"exampleFix":"// before\nContentFile<?> file = new MockContentFile(); // content() returns null\nappendFiles(table).appendFile(file);\n\n// after\nDataFile file = DataFiles.builder(table.spec())\n    .withPath(\"/data/file.parquet\")\n    .withFileSizeInBytes(1024)\n    .withRecordCount(10)\n    .build(); // content() == FileContent.DATA\nappendFiles(table).appendFile(file);","handlingStrategy":"validation","validationCode":"// Java\nif (file.content() == null ||\n    (file.content() != FileContent.DATA &&\n     file.content() != FileContent.POSITION_DELETES &&\n     file.content() != FileContent.EQUALITY_DELETES)) {\n  throw new IllegalArgumentException(\"Unexpected file content: \" + file.content());\n}","typeGuard":"// Java\nboolean isKnownContent(ContentFile<?> f) {\n  FileContent c = f.content();\n  return c == FileContent.DATA\n      || c == FileContent.POSITION_DELETES\n      || c == FileContent.EQUALITY_DELETES;\n}","tryCatchPattern":null,"preventionTips":["Always use DataFiles.builder / DeleteFile.builder rather than hand-built ContentFile implementations.","Pin writer and reader to compatible Iceberg versions before reading foreign metadata.","In tests, mock DataFile/DeleteFile concrete types, not generic ContentFile, so content() is always valid."],"tags":["unsupported-operation","enum","snapshot-summary","iceberg"],"backgroundTag":"unsupported-enum-value","analyzedSha":"86d9c8fc543e7c56c9f624eb725f76c9baff9570","analyzedAt":"2026-09-12T00:46:39.097Z","contentChangedAt":"2026-09-12T00:46:39.097Z","schemaVersion":2},"datasetVersion":"2026-09-14T16:17:12.679Z"}