Briefing

sqlite-utils 4.0rc1 Release Candidate Adds Migrations and Atomic Transactions

competitors

Patch sqlite-utils to 4.0rc1, test migrations and db.atomic() usage, and update code for new upsert syntax and table/view handling.

What to do now

Patch sqlite-utils to 4.0rc1, run migrations on existing databases, update upsert calls to use use_old_upsert=False, adjust table access to use db.view() for views, and verify float column handling.

Summary

sqlite-utils 4.0rc1 was released on 21 June 2026, marking the first release candidate for the upcoming v4 major version. The new release bundles a slightly modified port of the sqlite‑migrate package, providing a migrations API that lets developers define and apply database migrations via a migrations.py file. It also introduces a db.atomic() context manager that wraps SQLite savepoints, enabling nested transactions in a Django‑style syntax.

The release includes several backward‑incompatible changes: the upsert operation now uses INSERT … ON CONFLICT SET on SQLite versions newer than 3.23.1, with an optional use_old_upsert flag; table() now only works with tables, while db.view() must be used for views; table.insert_all() accepts iterators of lists or tuples; the default floating‑point column type changed from FLOAT to REAL; table names are now quoted with double quotes instead of square brackets; and the sqlite‑utils‑tui plugin is now provided separately.

Additional updates drop support for Python 3.8, add support for Python 3.13, and switch packaging to pyproject.toml. The CLI now includes a migrate command that applies migrations from a script file, and the new atomic API is documented in the Python API guide.

Key changes

  • Introduces migrations via bundled sqlite‑migrate with migrations.py example
  • Adds db.atomic() context manager for nested transactions
  • Upsert now uses INSERT … ON CONFLICT SET on SQLite >3.23.1, with use_old_upsert flag
  • Drops Python 3.8 support, adds Python 3.13 support
  • table() now only works with tables; use db.view() for views
  • table.insert_all() accepts iterator of lists/tuples with column header
  • Default floating‑point column type changed from FLOAT to REAL
  • Table names now quoted with double quotes instead of square brackets

Affects

internal

Customer impact

Analyzing matches…

Ask about this story

Impact on an agency? Which customers? Compare historically Risks of waiting