2010-07-21 19 views
6

Ejecuto el siguiente código desde un intérprete de python, y espero que la instrucción de inserción falle y genere algún tipo de excepción. Pero no está sucediendo:¿Por qué no funcionan mis claves externas sqlite3?

Python 2.6.5 (r265:79096, Mar 19 2010, 21:48:26) [MSC v.1500 32 bit (Intel)] on win32 
Type "help", "copyright", "credits" or "license" for more information. 
>>> import sqlite3 
>>> conn = sqlite3.connect("test.db") 
>>> conn.executescript(""" 
... pragma foreign_keys=on; 
... begin transaction; 
... create table t1 (i integer primary key, a); 
... create table t2 (i, a, foreign key (i) references t1(i)); 
... commit; 
... """) 
<sqlite3.Cursor object at 0x0229DAA0> 
>>> c = conn.cursor() 
>>> c.execute("insert into t2 values (6, 8)") 
<sqlite3.Cursor object at 0x0229DAD0> 
>>> #??? 
... 
>>> conn.commit() 
>>> #??????????? 
... 
>>> c.execute("select * from t2") 
<sqlite3.Cursor object at 0x0229DAD0> 
>>> c.fetchall() 
[(6, 8)] 
>>> #but why!? 
... 
>>> 

¿Alguien sabe por qué esto no quiere funcionar? Según entiendo, la inserción debería fallar dado que el valor que di para t2(i) no es una clave principal en t1, pero de todos modos lo hace de todos modos ...?

Respuesta

10

El soporte de la clave externa de trabajo en SQLite es muy nuevo; solo se lanzó en 3.6.19 el 14 de octubre. ¿Estás seguro de que estás usando SQLite 3.6.19 o posterior?

Compruebe la constante sqlite_version en el módulo sqlite3. P.ej. en un sistema Mac OS X 10.6 con el valor por defecto de Python/sqlite instalar:

>>> import sqlite3 
>>> sqlite3.sqlite_version 
'3.6.12' 
>>> 
+0

Iba a decir que debo hacerlo, porque puedo conseguir que funcione con el intérprete interactivo sqlite, pero luego me di cuenta de que python tiene su propia sqlite integrada; debo tener una nueva en mi sistema pero no en mi pitón Gracias –

+0

Ah, tenías razón, tengo 3.5.9. –

2

Como dijo por Nicholas, comprobar si su versión de SQLite tiene soporte clave externa. Esto no importa si la versión de sqlite es mayor o igual a 3.6.19. La fuente puede compilarse con el soporte de clave externa desactivado. Para verificar, ejecuta el siguiente comando.

cursor.execute("PRAGMA foreign_keys")

Si no devuelve ningún dato, su versión no tiene soporte de clave externa.

NB: La compatibilidad con claves foráneas no se aplica en sqlite3 a partir de ahora. Consulte here.

+1

¿No es así? En sqlite 3.8.10 parece aplicarlo bien con foreign_keys pragma activado –

+0

Según su documentación, no lo hace. Por el momento no he encontrado ninguna razón para dudar, porque mi DB se comporta así. De todos modos, revisaré la versión 3.8.10. – Charitoo

+1

Lo probé con el módulo sqlite3 de mi instalación de python 3.5 (que usa 3.8.11) y las restricciones de clave externa son compatibles allí también. La violación de uno me da una restricción 'sqlite3.IntegrityError: FOREIGN KEY failed' –

Cuestiones relacionadas