prestodb/presto · error · SQLFeatureNotSupportedException

moveToInsertRow

Error message

moveToInsertRow

What it means

moveToInsertRow always throws SQLFeatureNotSupportedException in PrestoResultSet: updatable result sets and insert-row positioning are not supported by the Presto driver, so this JDBC cursor operation is unimplemented.

Source

Thrown at presto-jdbc/src/main/java/com/facebook/presto/jdbc/PrestoResultSet.java:1075

    @Override
    public void refreshRow()
            throws SQLException
    {
        throw new SQLFeatureNotSupportedException("refreshRow");
    }

    @Override
    public void cancelRowUpdates()
            throws SQLException
    {
        throw new SQLFeatureNotSupportedException("cancelRowUpdates");
    }

    @Override
    public void moveToInsertRow()
            throws SQLException
    {
        throw new SQLFeatureNotSupportedException("moveToInsertRow");
    }

    @Override
    public void moveToCurrentRow()
            throws SQLException
    {
        throw new SQLFeatureNotSupportedException("moveToCurrentRow");
    }

    @Override
    public Statement getStatement()
    {
        return statement;
    }

    @Override
    public Object getObject(int columnIndex, Map<String, Class<?>> map)
            throws SQLException

View on GitHub (pinned to 55bb57d202)

Solutions

  1. Insert data with PreparedStatement INSERT statements instead
  2. Use Presto's INSERT INTO ... VALUES or a connector-appropriate bulk load path
  3. Detect read-only result sets via getConcurrency() and route to the SQL insert path

Example fix

// before
rs.moveToInsertRow();
rs.updateString("name", "x");
rs.insertRow();
rs.moveToCurrentRow();
// after
try (PreparedStatement ps = conn.prepareStatement(
        "INSERT INTO orders (name) VALUES (?)")) {
    ps.setString(1, "x");
    ps.executeUpdate();
}
Defensive patterns

Strategy: validation

Validate before calling

if (rs.getConcurrency() != ResultSet.CONCUR_UPDATABLE) {
    // skip moveToInsertRow path; use SQL INSERT
}

Type guard

static boolean supportsInsertRowCursor(ResultSet rs) {
    try {
        return rs.getConcurrency() == ResultSet.CONCUR_UPDATABLE;
    } catch (SQLException e) {
        return false;
    }
}

Try / catch

try {
    rs.moveToInsertRow();
} catch (SQLFeatureNotSupportedException e) {
    // switch to PreparedStatement INSERT
}

Prevention

When it happens

Trigger: Calling moveToInsertRow() (usually followed by updateXxx and insertRow) on a ResultSet from a PrestoStatement.

Common situations: Legacy JDBC insert-by-cursor code migrated to Presto; ORMs or ETL tools that insert rows via ResultSet; template code copied from MySQL/Oracle examples.

Related errors


AI-assisted analysis of prestodb/presto@55bb57d202 (2026-09-04). Data as JSON: /api/errors/498b514b5dfd1cd8. Report an issue: GitHub.