sqlez: Set a 5s SQLite busy timeout (#63923)

SQLite fails fast with `SQLITE_BUSY` when another process holds the
database lock. This database, and others like it, are shared between Zed
instances. SQLite allows multiple readers at once, but only one writer
at a time. Writes are short-lived, but if multiple Zed instances try to
write to the file at the same time, the default fail-fast behavior
throws `SQLITE_BUSY` and the write is dropped instead of retried. The
fix is to keep trying the write for up to five seconds, so transient
lock contention resolves and the write succeeds instead of erroring.

A concrete case is the agent threads database (`threads.db`), which
lives in the shared per-user data directory and is not namespaced by
release channel. Running two Zed instances side by side means both can
attempt to write to the same file at the same time, resulting in the
error mentioned previously.

Release Notes:

- Fixed intermittent "database is locked" errors when sharing a database
across Zed instances
This commit is contained in:
whitecat1331 2026-09-09 15:11:24 +00:00 • committed by GitHub
parent 284c72404a
commit e9d2934edf
No known key found for this signature in database
GPG key ID: B5690EEEBB952194

View file

@ -37,6 +37,15 @@ impl Connection {
// Turn on extended error codes
sqlite3_extended_result_codes(connection.sqlite3, 1);
// Wait for the database lock to be released instead of failing
// immediately with SQLITE_BUSY. Some databases (e.g. the agent
// threads database) are shared between Zed instances, so transient
// lock contention is expected; failing fast turns it into a
// storm of dropped saves and retry churn.
if !connection.sqlite3.is_null() {
sqlite3_busy_timeout(connection.sqlite3, 5000);
}
connection.last_error()?;
}