apache/iceberg · error · UnsupportedOperationException
Cannot update the sort order of a %s table
Error message
Cannot update the sort order of a %s table
What it means
Iceberg throws this UnsupportedOperationException when replaceSortOrder() is called on a read-only table. Changing the sort order is a metadata write, which BaseReadOnlyTable subclasses (e.g. metadata tables) never allow. The descriptor identifies the read-only table kind.
Source
Thrown at core/src/main/java/org/apache/iceberg/BaseReadOnlyTable.java:49
throw new UnsupportedOperationException(
"Cannot update the schema of a " + descriptor + " table");
}
@Override
public UpdatePartitionSpec updateSpec() {
throw new UnsupportedOperationException(
"Cannot update the partition spec of a " + descriptor + " table");
}
@Override
public UpdateProperties updateProperties() {
throw new UnsupportedOperationException(
"Cannot update the properties of a " + descriptor + " table");
}
@Override
public ReplaceSortOrder replaceSortOrder() {
throw new UnsupportedOperationException(
"Cannot update the sort order of a " + descriptor + " table");
}
@Override
public UpdateLocation updateLocation() {
throw new UnsupportedOperationException(
"Cannot update the location of a " + descriptor + " table");
}
@Override
public AppendFiles newAppend() {
throw new UnsupportedOperationException("Cannot append to a " + descriptor + " table");
}
@Override
public RewriteFiles newRewrite() {
throw new UnsupportedOperationException("Cannot rewrite in a " + descriptor + " table");
}View on GitHub (pinned to 86d9c8fc54)
Solutions
- Run sort-order replacement on the writable data table from catalog.loadTable(identifier).
- Skip sort-order updates for read-only/metadata table instances.
- Use table.sortOrder() if the sort order only needs to be inspected.
Example fix
// before
table.snapshots().replaceSortOrder().asc("id").commit();
// after
Table dataTable = catalog.loadTable(TableIdentifier.of("db", "tbl"));
dataTable.replaceSortOrder().asc("id").commit(); Defensive patterns
Strategy: try-catch
Validate before calling
if (!canWrite(table)) { throw new IllegalArgumentException("Read-only table: " + table.name()); } // canWrite checks the table was loaded from a catalog and is not a metadata table Type guard
boolean canReplaceSortOrder = !(table instanceof BaseReadOnlyTable); // practical proxy: table loaded via catalog.loadTable
Try / catch
try {
table.replaceSortOrder().asc("id").commit();
} catch (UnsupportedOperationException e) {
log.error("Sort order is immutable on read-only table {}", table.name(), e);
} Prevention
- Run sort-order jobs only on catalog-loaded data tables.
- Exclude metadata tables from optimization job table lists.
- Read current order with table.sortOrder() instead of opening a replacement.
When it happens
Trigger: Calling table.replaceSortOrder().asc(...).commit() on an instance extending BaseReadOnlyTable, such as a metadata table reference.
Common situations: Sort-order optimization routines applied generically to all Table handles, accidentally including metadata tables like table.snapshots().
Understand the failure class
Background: UnsupportedOperationException and "is not supported" errors: when a library deliberately refuses a call — this error's family across 30 libraries.
Related errors
- this.getClass().getName() + " does not implement create with
- Cannot update the schema of a %s table
- Cannot update the partition spec of a %s table
- Cannot update the properties of a %s table
- Cannot update the location of a %s table
AI-assisted analysis of apache/iceberg@86d9c8fc54 (2026-09-12).
Data as JSON: /api/errors/63f7561d02b0ab9d.
Report an issue: GitHub.