{"record":{"id":"b07ea997665423cf","repo":"tursodatabase/turso","slug":"step-returned-invalid-result-laststepresult","errorCode":null,"errorMessage":"step() returned invalid result: {lastStepResult}","messagePattern":"step\\(\\) returned invalid result: (.+?)","errorType":"exception","errorClass":"java.sql.SQLException","httpStatus":null,"severity":"error","filePath":"bindings/java/src/main/java/tech/turso/core/TursoResultSet.java","lineNumber":97,"sourceCode":"    }\n\n    if (maxRows != 0 && row == maxRows) {\n      return false;\n    }\n\n    lastStepResult = this.statement.step();\n    log.debug(\"lastStepResult: {}\", lastStepResult);\n    if (lastStepResult.isRow()) {\n      row++;\n    }\n\n    if (lastStepResult.isInInvalidState()) {\n      open = false;\n      String errorMessage = lastStepResult.getErrorMessage();\n      if (errorMessage != null && !errorMessage.isEmpty()) {\n        throw new SQLException(\"step() returned invalid result: \" + errorMessage);\n      } else {\n        throw new SQLException(\"step() returned invalid result: \" + lastStepResult);\n      }\n    }\n\n    pastLastRow = lastStepResult.isDone();\n    if (pastLastRow && row == 0) {\n      isEmptyResultSet = true;\n    }\n    return !pastLastRow;\n  }\n\n  /** Checks whether the last step result has returned row result. */\n  public boolean hasLastStepReturnedRow() {\n    return lastStepResult != null && lastStepResult.isRow();\n  }\n\n  /** Checks whether the cursor is positioned after the last row. */\n  public boolean isPastLastRow() {\n    return pastLastRow;","sourceCodeStart":79,"sourceCodeEnd":115,"githubUrl":"https://github.com/tursodatabase/turso/blob/244cde92a7df7f9b8b8b7a4075c35a12977e303e/bindings/java/src/main/java/tech/turso/core/TursoResultSet.java#L79-L115","documentation":"The fallback branch of the same invalid-state check as its sibling error: next() received a TursoStepResult in an invalid state whose getErrorMessage() is null or empty, so the exception stringifies the raw result object instead of an engine message. Semantics are identical — the engine failed during step and the set is now closed — but the missing message makes diagnosis harder, which usually points to a binding/JNI mapping gap rather than a clean engine error.","triggerScenarios":"The same engine-level failures as the message-bearing variant (I/O error, corruption, bad statement state) but on a code path where the native side produced no error text, e.g. an unmapped result code in the JNI layer.","commonSituations":"Version skew between the Java binding and the native library after a partial upgrade; engine error states added before their Java message mapping.","solutions":["Log the full exception: the stringified TursoStepResult in the message carries the result id","Treat it exactly like the message-bearing variant: the set is closed, re-execute on a fresh statement if needed","If it recurs deterministically, verify the Java binding and native library come from the same release; mixed old/new artifacts produce unmapped result codes"],"exampleFix":"// before\nwhile (rs.next()) { /* rows */ } // 'step() returned invalid result: TursoStepResult@...'\n\n// after\ntry {\n  while (rs.next()) { /* rows */ }\n} catch (SQLException e) {\n  // no engine message available; keep the stringified result for diagnosis\n  log.error(\"invalid step result without message: {}\", e.getMessage(), e);\n}","handlingStrategy":"try-catch","validationCode":null,"typeGuard":null,"tryCatchPattern":"try {\n  while (rs.next()) { /* ... */ }\n} catch (SQLException e) {\n  // no engine message available; the stringified result in the message carries the result id\n  log.error(\"step returned invalid result without message: {}\", e.getMessage(), e);\n}","preventionTips":["Keep the Java binding and native library versions in lockstep from the same release artifact","Log full exceptions (not just messages) so result ids survive into logs","After this error, treat the result set as closed and re-execute rather than retry the step"],"tags":["java","jdbc","result-set","native-library","diagnostics"],"backgroundTag":"query-execution-failed","analyzedSha":"244cde92a7df7f9b8b8b7a4075c35a12977e303e","analyzedAt":"2026-08-20T07:02:18.389Z","contentChangedAt":"2026-08-20T07:02:18.389Z","schemaVersion":2},"datasetVersion":"2026-09-23T08:17:48.524Z"}