{"record":{"id":"60f07f1b08c8129c","repo":"tursodatabase/turso","slug":"sql-execution-failed-60f07f","errorCode":null,"errorMessage":"SQL execution failed","messagePattern":"SQL execution failed","errorType":"exception","errorClass":"DatabaseError","httpStatus":null,"severity":"error","filePath":"serverless/javascript/src/statement.ts","lineNumber":298,"sourceCode":"          }\n          break;\n        case 'row':\n          if (entry.row) {\n            const decodedRow = entry.row.map(value => decodeValue(value, this.safeIntegerMode));\n            if (this.presentationMode === 'pluck') {\n              // In pluck mode, yield only the first column value\n              yield decodedRow[0];\n            } else if (this.presentationMode === 'raw') {\n              // In raw mode, yield arrays of values\n              yield decodedRow;\n            } else {\n              yield createExpandedRow(decodedRow, columns);\n            }\n          }\n          break;\n        case 'step_error':\n        case 'error':\n          throw new DatabaseError(entry.error?.message || 'SQL execution failed');\n      }\n    }\n  }\n\n}\n","sourceCodeStart":280,"sourceCodeEnd":304,"githubUrl":"https://github.com/tursodatabase/turso/blob/244cde92a7df7f9b8b8b7a4075c35a12977e303e/serverless/javascript/src/statement.ts#L280-L304","documentation":"Statement.iterate()'s async generator hit a step_error or error entry while streaming rows. Because the throw is inside the generator, it surfaces during `for await` iteration, not at the iterate() call itself. Unlike session.processCursorEntries, this site does not forward the server error code, so only the message distinguishes the failure.","triggerScenarios":"Iterating a statement whose execution fails server-side mid-stream (constraint violation on a RETURNING row, statement invalidated mid-iteration); malformed SQL that fails on the first entry; the underlying stream erroring after partial rows were already yielded.","commonSituations":"Streaming a large SELECT when the connection or stream breaks partway; iterating INSERT ... RETURNING where a later row violates a constraint; consuming the iterator after the session already errored.","solutions":["Wrap the `for await` loop (not just the iterate() call) in try/catch","Reproduce with all() to get the same failure with the server error code attached (session.ts forwards it, statement iterate does not)","Fix the underlying SQL/schema problem named in the message","Break out of the loop and let the generator's finally release the reader when abandoning early"],"exampleFix":"// before\nconst rows = stmt.iterate([category]);\nfor await (const row of rows) { handle(row); } // unhandled mid-stream throw\n\n// after\ntry {\n  for await (const row of stmt.iterate([category])) { handle(row); }\n} catch (e) {\n  if (e instanceof DatabaseError) { /* log e.message, fall back to stmt.all() */ }\n  throw e;\n}","handlingStrategy":"try-catch","validationCode":null,"typeGuard":"import { DatabaseError } from '@tursodatabase/serverless';\n\nfunction isIterateError(e: unknown): e is DatabaseError {\n  return e instanceof DatabaseError && e.message === 'SQL execution failed';\n}","tryCatchPattern":"try {\n  for await (const row of stmt.iterate(args)) { process(row); }\n} catch (e) {\n  // throws mid-iteration, not at iterate() — this try must wrap the loop\n  if (e instanceof DatabaseError) logAndRecover(e);\n  throw e;\n}","preventionTips":["Always wrap the `for await` loop itself — the generator throws lazily during iteration","This site does not forward error.code; during debugging use all() to get the code, then switch back to iterate()","Break out of the loop explicitly when abandoning early so the generator's cleanup releases the stream reader"],"tags":["sql","iterator","streaming","typescript"],"backgroundTag":"sql-execution-error","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"}