SQLite “database is locked”: find the competing connection
A lock error usually means the operation cannot acquire the access it needs while another connection or transaction is active. It does not, by itself, mean the database is corrupt.
Start with the process doing the writing
- Identify the app, development server, background worker or shell using the database.
- Check for a transaction that started but never committed or rolled back.
- Finish that transaction through the owning application, then retry the blocked operation.
- If this is your development environment, stop duplicate workers cleanly before trying again.
On Mac, this can help identify processes with the main file open:
lsof "/path/to/database.sqlite"
An open handle is a clue, not proof that a process holds the conflicting lock. Sidecar handles and connection state also matter. Do not kill an unfamiliar process just because it appears in the output.
Keep transactions short
Do not hold a write transaction open while waiting for a network request or user input. SQLite permits one writer at a time. WAL mode lets readers and a writer coexist in many situations, but does not permit unlimited simultaneous writers.
For a brief collision, a connection-level busy timeout can allow a retry window. In the SQLite shell:
.timeout 2000
This sets a two-second wait for that shell connection. It does not unlock another process, change Petti’s timeout, or solve a transaction that remains open indefinitely.
BUSY and LOCKED are not identical
SQLITE_BUSY commonly concerns a competing connection. SQLITE_LOCKED can indicate a conflict within a connection or shared-cache use. Read the full error and the SQLite result-code reference before assuming every lock message needs the same fix.
Inspect without becoming another writer
Use Petti’s read-only mode when you only need to browse. Read-only access reduces unnecessary write contention but cannot guarantee every read succeeds; journal mode and active transactions still matter. See SQLite’s isolation behavior.
Do not delete -wal, -shm or journal files, change broad permissions, or switch journal modes merely to dismiss an error. If you need an isolated inspection copy, make a SQLite-aware backup once access is available.