-
-
Notifications
You must be signed in to change notification settings - Fork 115
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Extract columns cannot create foreign key relation: sqlite3.OperationalError: table sqlite_master may not be modified #235
Comments
I just ran into what appears to be the same issue on a MacBook Pro, M1 Pro. Environment:
Error
|
Note, I do not get this issue using my Intel MacBook Pro =/ Environment
|
I was able to fight through this by capturing the SQL commands from the |
I am getting the same error when using github-to-sqlite (which uses sqlite-utils internally). I am also using an M1 MacBook Pro, with macOS Monterey 12.5, with Python 3.10.6 for arm64 installed using pyenv. I have sqlite-utils 3.28 installed. |
This bug affects me as well. Env:
Similar to @mdrovdahl, I was able to work around this bug by piping the SQL string constructed in
Then from your terminal: If you want to run this with |
I had the problem this morning when running:
I upgraded to: and the error did not appear anymore. Hope this helps |
Hi @ryascott, thanks for sharing this! How did you upgrade your sqlite3 version? I'm running into this issue (also on an m1) with
Unfortunately, For me, the trigger is trying to use the sqlite-utils add-foreign-key library.db book_creators creator_id creators id Some stackoverflow searching suggests that brew installing sqlite may fix it ( https://stackoverflow.com/questions/26345972/how-do-i-upgrade-the-sqlite-version-used-by-pythons-sqlite3-module-on-mac ), but I don't want to risk breaking the version of sqlite used by some other system, I'd only like to upgrade sqlite3 inside my current virtual environment. |
A related historical problem: tekartik/sqflite#525 (comment) I wonder if the version of Sqlite or Python for Intel chip have defensive mode disabled by default, whereas M1 chips versions have it enabled. |
My current workaround is to use this library from a python script instead of as a CLI tool. This lets me set the foreign key constraint at table creation time, instead of trying to modify an existing table. docs I found this stackoverflow helpful, as it explained that Sqlite doesn't support modifying existing tables directly. |
@wpears' workaround also worked for me, but also required me to manually set PRAGMA writable_schema = 1;
UPDATE sqlite_master SET sql = 'CREATE TABLE [foos] (...)'
PRAGMA writable_schema = 0; $ python --version
Python 3.11.2
$ sqlite3 --version
3.41.2 2023-03-22 11:56:21 0d1fc92f94cb6b76bffe3ec34d69cffde2924203304e8ffc4155597af0c191da
$ sqlite-utils --version
sqlite-utils, version 3.30 |
Investigating this one now. The In the broken version's virtual environment directory I ran this:
So it looks like the Xcode As far as I can tell there's no way to turn it OFF again in Python. My virtual environment that DOES work has this:
So the Python 3.11 I installed through Homebrew doesn't exhibit this bug. |
I'll ask on the SQLite forum if it's possible to toggle that mode on and off using regular SQL. My hunch is that it isn't. In which case A utility function that can detect this mode would be really useful too. I'd probably have to do a test that tries to modify |
This seems to work: import sqlite3
db = sqlite3.connect(":memory:")
db.executescript("""
PRAGMA writable_schema = 1;
UPDATE sqlite_master SET sql = 'CREATE TABLE [foos] (id integer primary key)';
PRAGMA writable_schema = 0;
""") It succeeds on my Python 3.11 and raises the following exception on my broken Python 3.9:
Removing the |
I also tested this against the current
Then in the container:
In both cases the Python code did not raise an exception, which suggests that on Ubuntu those two Python versions do not have the defensive mode set. |
Also checked the official Datasette Docker image - I had to run that in Codespaces because it doesn't currently work on my M2 Mac:
So that confirms that the official image also has a Python with a SQLite that's not in defensive mode. |
Ideally a workaround for this right now would be to install
But The "easiest" fix at the moment is to use Python from Homebrew - so |
https://sqlite-utils.datasette.io/en/stable/changelog.html#v3-33 - upgrading to |
I just tested this in a brand new virtual environment using the macOS Python 3: pipenv shell --python /Applications/Xcode.app/Contents/Developer/usr/bin/python3 Then in that virtual environment I ran: pip install sqlite-utils
# Confirm the right one is on the path:
which sqlite-utils
curl "https://data.nasa.gov/resource/y77d-th95.json" | \
sqlite-utils insert meteorites.db meteorites - --pk=id
sqlite-utils extract meteorites.db meteorites recclass This threw the same error reported above. Then I did this: rm meteorites.db
pip install sqlean.py
curl "https://data.nasa.gov/resource/y77d-th95.json" | \
sqlite-utils insert meteorites.db meteorites - --pk=id
sqlite-utils extract meteorites.db meteorites recclass And that second time it worked correctly. |
Thanks for what seems like a truly great suite of libraries. I wanted to try out Datasette, but never got more than half way through your YouTube video with the SF tree dataset. Whenever I try to extract a column, I get a
sqlite3.OperationalError: table sqlite_master may not be modified
error from Python. This snippet reproduces the error on my system, Python 3.9.1 and sqlite-utils 3.5 on an M1 Macbook Pro running in rosetta mode:I have tried googling the problem, but all I've found is that this might be a problem with the sqlite3 database running in defensive mode, but I definitely can't know for sure. Does the problem seem familiar to you?
The text was updated successfully, but these errors were encountered: