{"record":{"id":"e90fc8a7966881a0","repo":"apache/iceberg","slug":"failed-to-close-changelog-scan","errorCode":null,"errorMessage":"Failed to close changelog scan: ","messagePattern":"Failed to close changelog scan: ","errorType":"exception","errorClass":"UncheckedIOException","httpStatus":null,"severity":"error","filePath":"spark/v4.1/spark/src/main/java/org/apache/iceberg/spark/source/SparkChangelogScan.java","lineNumber":121,"sourceCode":"  @Override\n  public Batch toBatch() {\n    return new SparkBatch(\n        sparkContext,\n        table,\n        null != scan ? scan.fileIO() : table::io,\n        readConf,\n        EMPTY_GROUPING_KEY_TYPE,\n        taskGroups(),\n        projection,\n        hashCode());\n  }\n\n  private List<ScanTaskGroup<ChangelogScanTask>> taskGroups() {\n    if (taskGroups == null) {\n      try (CloseableIterable<ScanTaskGroup<ChangelogScanTask>> groups = scan.planTasks()) {\n        this.taskGroups = Lists.newArrayList(groups);\n      } catch (IOException e) {\n        throw new UncheckedIOException(\"Failed to close changelog scan: \" + scan, e);\n      }\n    }\n\n    return taskGroups;\n  }\n\n  @Override\n  public String description() {\n    return String.format(\n        Locale.ROOT,\n        \"IcebergChangelogScan(table=%s, fromSnapshotId=%d, toSnapshotId=%d, filters=%s)\",\n        table,\n        startSnapshotId,\n        endSnapshotId,\n        filtersDesc());\n  }\n\n  @Override","sourceCodeStart":103,"sourceCodeEnd":139,"githubUrl":"https://github.com/apache/iceberg/blob/86d9c8fc543e7c56c9f624eb725f76c9baff9570/spark/v4.1/spark/src/main/java/org/apache/iceberg/spark/source/SparkChangelogScan.java#L103-L139","documentation":"Wrapping error in SparkChangelogScan.taskGroups: while draining scan.planTasks() into a list inside try-with-resources, an IOException from closing (or reading) the task-groups iterable is rethrown as UncheckedIOException with this message. The chained cause identifies the underlying file/stream failure during changelog planning.","triggerScenarios":"IOException thrown by the underlying FileIO while planning or closing changelog task groups (manifest/IO failures, network to object store).","commonSituations":"S3/GCS/HDFS transient failures during scan planning; credentials expiry; corrupted metadata files.","solutions":["Inspect the caused-by chain for the underlying IOException","Retry the query; configure retries on the object store client","Verify FileIO credentials and network access","Check metadata file integrity"],"exampleFix":null,"handlingStrategy":"retry","validationCode":"// pre-check storage reachability\nfileIO.tableOps(); // or probe metadata json location before planning","typeGuard":null,"tryCatchPattern":"try { scan.taskGroups(); } catch (UncheckedIOException e) { retryWithBackoff(); }","preventionTips":["Configure object-store client retries","Verify credentials before long streaming jobs","Monitor storage availability"],"tags":["spark","iceberg","io-exception","scan-planning"],"backgroundTag":"file-read-failed","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"}