{"record":{"id":"f3ce25abb5232776","repo":"prestodb/presto","slug":"afterlast","errorCode":null,"errorMessage":"afterLast","messagePattern":"afterLast","errorType":"exception","errorClass":"SQLFeatureNotSupportedException","httpStatus":null,"severity":"error","filePath":"presto-jdbc/src/main/java/com/facebook/presto/jdbc/PrestoResultSet.java","lineNumber":650,"sourceCode":"    @Override\n    public boolean isLast()\n            throws SQLException\n    {\n        throw new SQLFeatureNotSupportedException(\"isLast\");\n    }\n\n    @Override\n    public void beforeFirst()\n            throws SQLException\n    {\n        throw new SQLFeatureNotSupportedException(\"beforeFirst\");\n    }\n\n    @Override\n    public void afterLast()\n            throws SQLException\n    {\n        throw new SQLFeatureNotSupportedException(\"afterLast\");\n    }\n\n    @Override\n    public boolean first()\n            throws SQLException\n    {\n        throw new SQLFeatureNotSupportedException(\"first\");\n    }\n\n    @Override\n    public boolean last()\n            throws SQLException\n    {\n        throw new SQLFeatureNotSupportedException(\"last\");\n    }\n\n    @Override\n    public int getRow()","sourceCodeStart":632,"sourceCodeEnd":668,"githubUrl":"https://github.com/prestodb/presto/blob/55bb57d202de3b926896fa966c2c4a44c779634e/presto-jdbc/src/main/java/com/facebook/presto/jdbc/PrestoResultSet.java#L632-L668","documentation":"PrestoResultSet throws SQLFeatureNotSupportedException(\"afterLast\") because Presto result sets are forward-only; the JDBC driver does not buffer rows, so scrollable navigation methods cannot be implemented. Calling afterLast() always fails unconditionally, regardless of result set state.","triggerScenarios":"Calling ResultSet.afterLast() on a PrestoResultSet obtained from a Presto JDBC Statement, regardless of statement type or fetch configuration.","commonSituations":"Generic JDBC frameworks (ORMs, reporting tools, Spring JdbcTemplate) that iterate a result set first and then reposition via afterLast() to count rows or access data in reverse.","solutions":["Rewrite the query with ORDER BY and iterate forward from the beginning instead of using afterLast()","Count rows with a separate SELECT COUNT(*) query instead of repositioning to the end","Materialize rows into a local List/Collection during the forward pass, then index it in memory","Wrap the statement request only if the driver ever supports scrollable types; currently it does not"],"exampleFix":"// before\nif (rs.last()) { int count = rs.getRow(); }\n// after\nint count = 0;\nwhile (rs.next()) { count++; }","handlingStrategy":"try-catch","validationCode":"DatabaseMetaData md = conn.getMetaData();\nif (!md.supportsResultSetType(ResultSet.TYPE_SCROLL_INSENSITIVE)) { /* avoid navigation calls */ }","typeGuard":null,"tryCatchPattern":"try { rs.afterLast(); } catch (SQLFeatureNotSupportedException e) { /* fall back to forward iteration */ }","preventionTips":["Treat Presto result sets as TYPE_FORWARD_ONLY regardless of requested type","Count rows with SELECT COUNT(*) instead of navigating to the end","Buffer rows locally if random access is needed"],"tags":["jdbc","unsupported-operation","forward-only-resultset"],"backgroundTag":"jdbc-resultset-navigation-unsupported","analyzedSha":"55bb57d202de3b926896fa966c2c4a44c779634e","analyzedAt":"2026-09-04T12:50:26.162Z","contentChangedAt":"2026-09-04T12:50:26.162Z","schemaVersion":2},"datasetVersion":"2026-09-11T21:17:09.523Z"}