prestodb/presto · error · SQLFeatureNotSupportedException
deleteRow
Error message
deleteRow
What it means
deleteRow() is part of the updatable result set API; Presto result sets are read-only and cannot delete rows through a cursor. The driver therefore throws SQLFeatureNotSupportedException("deleteRow") unconditionally.
Source
Thrown at presto-jdbc/src/main/java/com/facebook/presto/jdbc/PrestoResultSet.java:1054
@Override
public void insertRow()
throws SQLException
{
throw new SQLFeatureNotSupportedException("insertRow");
}
@Override
public void updateRow()
throws SQLException
{
throw new SQLFeatureNotSupportedException("updateRow");
}
@Override
public void deleteRow()
throws SQLException
{
throw new SQLFeatureNotSupportedException("deleteRow");
}
@Override
public void refreshRow()
throws SQLException
{
throw new SQLFeatureNotSupportedException("refreshRow");
}
@Override
public void cancelRowUpdates()
throws SQLException
{
throw new SQLFeatureNotSupportedException("cancelRowUpdates");
}
@Override
public void moveToInsertRow()View on GitHub (pinned to 55bb57d202)
Solutions
- Issue a PreparedStatement DELETE FROM ... WHERE ... statement instead of cursor deletion
- Split read and write phases: collect keys while reading, then delete with a batched SQL DELETE
- Check resultSet.getConcurrency() before attempting cursor deletes and branch to SQL when read-only
Example fix
// before
while (rs.next()) {
if (isStale(rs)) { rs.deleteRow(); }
}
// after
List<Long> stale = new ArrayList<>();
while (rs.next()) { if (isStale(rs)) stale.add(rs.getLong("id")); }
try (PreparedStatement ps = conn.prepareStatement(
"DELETE FROM orders WHERE id = ?")) {
for (Long id : stale) { ps.setLong(1, id); ps.addBatch(); }
ps.executeBatch();
} Defensive patterns
Strategy: try-catch
Validate before calling
if (rs.getConcurrency() == ResultSet.CONCUR_READ_ONLY) {
// use SQL DELETE instead of rs.deleteRow()
} Type guard
static boolean supportsDeleteRow(ResultSet rs) {
try {
return rs.getConcurrency() == ResultSet.CONCUR_UPDATABLE;
} catch (SQLException e) {
return false;
}
} Try / catch
try {
rs.deleteRow();
} catch (SQLFeatureNotSupportedException e) {
// issue DELETE ... WHERE via PreparedStatement
} Prevention
- Delete rows with SQL DELETE statements keyed on primary keys
- Split read and write phases into separate queries
- Do not assume CONCUR_UPDATABLE from other drivers carries over to Presto
When it happens
Trigger: Calling deleteRow() on a ResultSet created from a PrestoStatement while iterating results, intending to remove the current row from the table.
Common situations: Legacy CRUD code ported from OLTP drivers to Presto; data-cleanup scripts that mix reading and deleting in one pass; generic JDBC tooling assuming CONCUR_UPDATABLE.
Related errors
AI-assisted analysis of prestodb/presto@55bb57d202 (2026-09-04).
Data as JSON: /api/errors/d408ebe80c87ec94.
Report an issue: GitHub.