tursodatabase/turso · error · TypeError
sqlite3.Row is not supported as a row_factory on turso conne
Error message
sqlite3.Row is not supported as a row_factory on turso connections; use turso.Row instead
What it means
pyturso's Connection/Cursor are not subclasses of the stdlib sqlite3 module, so sqlite3.Row cannot wrap turso result rows. When a fetch applies a row_factory that is a subclass of sqlite3.Row, constructing it fails with TypeError, and _reject_stdlib_row_factory replaces that with an explicit message directing you to turso's own Row type (lib.py:917). The error surfaces at fetch time (fetchone/fetchmany/fetchall/iteration), not at assignment time.
Source
Thrown at bindings/python/turso/lib.py:215
"""
Run PyTursoStatement.step() once handling potential async IO loops.
"""
while True:
status = stmt.step()
if status == Status.Io:
stmt.run_io()
if extra_io:
extra_io()
continue
return status
def _reject_stdlib_row_factory(rf: Any) -> None:
stdlib_sqlite3 = sys.modules.get("sqlite3")
if stdlib_sqlite3 is None:
return
if isinstance(rf, type) and issubclass(rf, stdlib_sqlite3.Row):
raise TypeError("sqlite3.Row is not supported as a row_factory on turso connections; use turso.Row instead")
@dataclass
class _Prepared:
stmt: PyTursoStatement
tail_index: int
has_columns: bool
column_names: tuple[str, ...]
# Connection goes FIRST
class Connection:
"""
A connection to a Turso (SQLite-compatible) database.
Similar to sqlite3.Connection with a subset of features focusing on DB-API 2.0.
"""
View on GitHub (pinned to bad083fafb)
Solutions
- Use turso's row type instead: `from turso import Row; conn.row_factory = Row` — it provides the same name-based access over turso rows
- If you don't need mapping-style access, leave row_factory as None and use index-based tuple access
- For shared code supporting both drivers, select the factory conditionally based on the connection type
Example fix
# before
import sqlite3
conn = turso.connect("db")
conn.row_factory = sqlite3.Row # explodes at fetch time
for row in conn.execute("SELECT id, name FROM t"):
print(row["name"])
# after
from turso import Row
conn = turso.connect("db")
conn.row_factory = Row
for row in conn.execute("SELECT id, name FROM t"):
print(row["name"]) Defensive patterns
Strategy: type-guard
Validate before calling
import sqlite3
def pick_row_factory(conn):
"""Return a row factory compatible with the connection's driver."""
driver = type(conn).__module__
if driver.startswith("turso"):
from turso import Row
return Row
return sqlite3.Row
conn.row_factory = pick_row_factory(conn) Type guard
import sqlite3
def row_factory_supported(rf) -> bool:
"""False when rf is a stdlib sqlite3.Row subclass, which turso rejects."""
stdlib_row = getattr(sqlite3, "Row", None)
return not (
isinstance(rf, type)
and stdlib_row is not None
and issubclass(rf, stdlib_row)
) Try / catch
try:
row = cur.fetchone()
except TypeError as e:
if "sqlite3.Row is not supported" in str(e):
conn.row_factory = None # or turso Row; then re-fetch
else:
raise Prevention
- When porting sqlite3 code, grep for `sqlite3.Row` before switching the import to turso
- Centralize row_factory selection in one helper instead of setting it ad hoc
- Prefer turso.Row for name-based access; it is the drop-in replacement for sqlite3.Row
When it happens
Trigger: `import sqlite3` then `conn.row_factory = sqlite3.Row` on a turso connection (or `cur.row_factory = sqlite3.Row`) followed by any row fetch. Typical when porting sqlite3/aiosqlite code: `for row in cur.execute("SELECT ...")` after setting the factory.
Common situations: Migrating an existing sqlite3 project to pyturso; shared helper modules or ORMs that set sqlite3.Row unconditionally; tutorial code copied from the sqlite3 docs; aiosqlite wrappers that inject sqlite3.Row.
Related errors
- no SQL statements to execute
- You can only execute one statement at a time
- autocommit must be True, False, or 'LEGACY'
- query timeout must be non-negative
- Cannot operate on a closed cursor
AI-assisted analysis of tursodatabase/turso@bad083fafb (2026-08-16).
Data as JSON: /api/errors/0dc57d2bc8ae8765.
Report an issue: GitHub.