{"record":{"id":"0ef0b792bc5e0d72","repo":"apache/beam","slug":"unknown-changelogscantask-type-changelogscanner","errorCode":null,"errorMessage":"Unknown ChangelogScanTask type: {}","messagePattern":"Unknown ChangelogScanTask type: (.+?)","errorType":"exception","errorClass":"IllegalStateException","httpStatus":null,"severity":"error","filePath":"sdks/java/io/iceberg/src/main/java/org/apache/beam/sdk/io/iceberg/cdc/ChangelogScanner.java","lineNumber":544,"sourceCode":"      Schema recIdSchema,\n      Comparator<StructLike> idComp) {\n    // if table doesn't keep track of metrics, we need to play it safe and consider all tasks may\n    // overlap.\n    if (!metricsAreAvailable) {\n      return AnalysisResult.allBidirectional(tasks);\n    }\n\n    List<TaskAndBounds> insertTasks = new ArrayList<>();\n    List<TaskAndBounds> deleteTasks = new ArrayList<>();\n\n    try {\n      for (ChangelogScanTask task : tasks) {\n        if (task instanceof AddedRowsScanTask) {\n          insertTasks.add(TaskAndBounds.of(task, recIdSchema, idComp));\n        } else if (task instanceof DeletedDataFileScanTask || task instanceof DeletedRowsScanTask) {\n          deleteTasks.add(TaskAndBounds.of(task, recIdSchema, idComp));\n        } else {\n          throw new IllegalStateException(\"Unknown ChangelogScanTask type: \" + task.getClass());\n        }\n      }\n    } catch (TaskAndBounds.NoBoundMetricsException e) {\n      // if metrics are not available for some files, we should also play it safe.\n      return AnalysisResult.allBidirectional(tasks);\n    }\n\n    if (!insertTasks.isEmpty() && !deleteTasks.isEmpty()) {\n      Comparator<TaskAndBounds> lowerBoundComp = (t1, t2) -> idComp.compare(t1.lowerId, t2.lowerId);\n      Comparator<TaskAndBounds> upperBoundComp = (t1, t2) -> idComp.compare(t1.upperId, t2.upperId);\n\n      insertTasks.sort(lowerBoundComp);\n      deleteTasks.sort(lowerBoundComp);\n\n      TaskAndBounds firstInsert = insertTasks.get(0);\n      TaskAndBounds firstDelete = deleteTasks.get(0);\n      TaskAndBounds lastInsert = insertTasks.stream().max(upperBoundComp).orElseThrow();\n      TaskAndBounds lastDelete = deleteTasks.stream().max(upperBoundComp).orElseThrow();","sourceCodeStart":526,"sourceCodeEnd":562,"githubUrl":"https://github.com/apache/beam/blob/12126d8942aaf848030c478b4c6a28c6af861c66/sdks/java/io/iceberg/src/main/java/org/apache/beam/sdk/io/iceberg/cdc/ChangelogScanner.java#L526-L562","documentation":"ChangelogScanner.analyzeFiles classifies each ChangelogScanTask into insert-tasks or delete-tasks by concrete type (AddedRowsScanTask, DeletedDataFileScanTask, DeletedRowsScanTask). Any other ChangelogScanTask subtype has no analysis strategy, and the scanner throws IllegalStateException — a defensive check against unknown Iceberg task types.","triggerScenarios":"A changelog/incremental scan produces a ChangelogScanTask instance whose type is not among the three handled subtypes (e.g. a new Iceberg task kind introduced in a newer Iceberg version), passed through result() -> analyzeFiles.","commonSituations":"Iceberg runtime upgraded beyond what the Beam CDC scanner supports; table uses new Iceberg changelog features; mixed library versions on the classpath.","solutions":["Pin/upgrade org.apache.iceberg to the version the Beam CDC connector targets.","Disable the new Iceberg table/scan features producing the unknown task type, or use a standard incremental scan instead of the CDC scanner.","Patch ChangelogScanner to classify the new task type and rebuild.","Check for duplicate/conflicting iceberg-core versions on the classpath (mvn dependency:tree) and de-duplicate."],"exampleFix":"// before\n<dependency>org.apache.iceberg:iceberg-core:1.8.0</dependency> // emits unknown task types\n// after\n<dependency>org.apache.iceberg:iceberg-core:1.5.2</dependency> // matching connector","handlingStrategy":"try-catch","validationCode":"boolean allKnown = tasks.stream().allMatch(t ->\n    t instanceof AddedRowsScanTask || t instanceof DeletedDataFileScanTask || t instanceof DeletedRowsScanTask);\nif (!allKnown) throw new IllegalStateException(\"Incompatible Iceberg task types; check library versions\");","typeGuard":"boolean isKnownTask(ChangelogScanTask t) {\n  return t instanceof AddedRowsScanTask || t instanceof DeletedDataFileScanTask || t instanceof DeletedRowsScanTask;\n}","tryCatchPattern":"try {\n  AnalysisResult r = scanner.result(tasks);\n} catch (IllegalStateException e) {\n  if (e.getMessage().startsWith(\"Unknown ChangelogScanTask type\")) {\n    // fall back to AnalysisResult.allBidirectional(tasks)\n  } else { throw e; }\n}","preventionTips":["Match iceberg-core version to the Beam CDC scanner's expected version.","Disable newer Iceberg changelog features unsupported by the connector.","Check classpath for mixed Iceberg versions."],"tags":["java","iceberg","cdc","version-mismatch","scanner"],"backgroundTag":"invalid-enum-value","analyzedSha":"12126d8942aaf848030c478b4c6a28c6af861c66","analyzedAt":"2026-09-13T01:50:10.254Z","contentChangedAt":"2026-09-13T01:50:10.254Z","schemaVersion":2},"datasetVersion":"2026-09-14T16:17:12.679Z"}