]> git.ipfire.org Git - thirdparty/sqlite.git/commitdiff
Fix some comments in fkey.c. Add tests to fkey8.test. experimental-fk-actions
authordan <dan@noemail.net>
Wed, 17 Dec 2014 14:38:45 +0000 (14:38 +0000)
committerdan <dan@noemail.net>
Wed, 17 Dec 2014 14:38:45 +0000 (14:38 +0000)
FossilOrigin-Name: 210cb2a6aaf780365064a26c0c99926bd6346e19

manifest
manifest.uuid
src/fkey.c
test/fkey8.test

index d7fc48ce456384d7362c877030a7db6ccade8d65..ec31cc9e8ac0263c7a2e22f2af64e1f5d860d03f 100644 (file)
--- a/manifest
+++ b/manifest
@@ -1,5 +1,5 @@
-C Experimental\sopimizations\sto\sspeed\sup\sFK\sconstraint\sCASCADE\sand\sSET\sNULL\saction\sprocessing.
-D 2014-12-16T20:13:30.440
+C Fix\ssome\scomments\sin\sfkey.c.\sAdd\stests\sto\sfkey8.test.
+D 2014-12-17T14:38:45.643
 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f
 F Makefile.in 6c4f961fa91d0b4fa121946a19f9e5eac2f2f809
 F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23
@@ -184,7 +184,7 @@ F src/date.c 93594514aae68de117ca4a2a0d6cc63eddf26744
 F src/delete.c 0750b1eb4d96cd3fb2c798599a3a7c85e92f1417
 F src/expr.c 00da3072f362b06f39ce4052baa1d4ce2bb36d1c
 F src/fault.c 160a0c015b6c2629d3899ed2daf63d75754a32bb
-F src/fkey.c eab56799b0339b04c258233b0f462b6e9317f90f
+F src/fkey.c e0444b61bed271a76840cbe6182df93a9baa3f12
 F src/func.c 6d3c4ebd72aa7923ce9b110a7dc15f9b8c548430
 F src/global.c 6ded36dda9466fc1c9a3c5492ded81d79bf3977d
 F src/hash.c 4263fbc955f26c2e8cdc0cf214bc42435aa4e4f5
@@ -504,7 +504,7 @@ F test/fkey4.test 86446017011273aad8f9a99c1a65019e7bd9ca9d
 F test/fkey5.test 8a1fde4e7721ae00b05b3178888833726ca2df8d
 F test/fkey6.test abb59f866c1b44926fd02d1fdd217d831fe04f48
 F test/fkey7.test 72e915890ee4a005daaf3002cb208e8fe973ac13
-F test/fkey8.test 2d58cfb990cdd56b2fbac9f4ae54ee53968b3e06
+F test/fkey8.test 8f08203458321e6c19a263829de4cfc936274ab0
 F test/fkey_malloc.test 594a7ea1fbab553c036c70813cd8bd9407d63749
 F test/format4.test 1f0cac8ff3895e9359ed87e41aaabee982a812eb
 F test/fts-9fd058691.test 78b887e30ae6816df0e1fed6259de4b5a64ad33c
@@ -1233,10 +1233,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1
 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4
 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32
 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f
-P ae43539e62e76676a3daf561b629a1b9b4e2d2c9
-R ea6275c5fe67bcf602365c1ede77fced
-T *branch * experimental-fk-actions
-T *sym-experimental-fk-actions *
-T -sym-trunk *
+P 35a20a5f22245c70faa51965951e8cc011defa93
+R c39a2128ba39a16276f2dc7a158fbe28
 U dan
-Z b6352d484674a0d7b3ae6d8d076cd106
+Z 96b8a9e537739194255aed7e579f65ad
index 859f607ae01fe134e4fd172303fcc672ca474ef6..367ac4e6aaad3a1fd6bdadc6c7df42da550f635e 100644 (file)
@@ -1 +1 @@
-35a20a5f22245c70faa51965951e8cc011defa93
\ No newline at end of file
+210cb2a6aaf780365064a26c0c99926bd6346e19
\ No newline at end of file
index 7ea48f5058950964a422ecacc75c134cdb7260c5..fa148ba6a3a306e3188635962c7c28285025d5f6 100644 (file)
@@ -629,9 +629,8 @@ static void fkScanChildren(
   sqlite3ResolveExprNames(&sNameContext, pWhere);
 
   /* Create VDBE to loop through the entries in pSrc that match the WHERE
-  ** clause. If the constraint is not deferred, throw an exception for
-  ** each row found. Otherwise, for deferred constraints, increment the
-  ** deferred constraint counter by nIncr for each row selected.  */
+  ** clause. For each row found, increment either the deferred or immediate
+  ** foreign key constraint counter. */
   pWInfo = sqlite3WhereBegin(pParse, pSrc, pWhere, 0, 0, 0, 0);
   sqlite3VdbeAddOp2(v, OP_FkCounter, pFKey->isDeferred, nIncr);
   if( pWInfo ){
@@ -963,9 +962,9 @@ void sqlite3FkCheck(
       **
       ** If this operation is being performed as part of a trigger program
       ** that is actually a "SET NULL" action belonging to this very 
-      ** foreign key, then omit this scan altogether. As the child keys
+      ** foreign key, then omit this scan altogether. As all child key
       ** values are guaranteed to be NULL, it is not possible for adding
-      ** this row to cause an FK violation. */
+      ** this row to cause an FK violation.  */
       fkLookupParent(pParse, iDb, pTo, pIdx, pFKey, aiCol, regNew, +1, bIgnore);
     }
 
@@ -1015,9 +1014,22 @@ void sqlite3FkCheck(
         int eAction = pFKey->aAction[aChange!=0];
         fkScanChildren(pParse, pSrc, pTab, pIdx, pFKey, aiCol, regOld, 1);
         /* If this is a deferred FK constraint, or a CASCADE or SET NULL
-        ** action applies, do not set the may-abort flag on this statement.
-        ** The flag may be set on this statement for some other reason, but
-        ** not as a result of this FK constraint. */
+        ** action applies, then any foreign key violations caused by
+        ** removing the parent key will be rectified by the action trigger.
+        ** So do not set the "may-abort" flag in this case.
+        **
+        ** Note 1: If the FK is declared "ON UPDATE CASCADE", then the
+        ** may-abort flag will eventually be set on this statement anyway
+        ** (when this function is called as part of processing the UPDATE
+        ** within the action trigger).
+        **
+        ** Note 2: At first glance it may seem like SQLite could simply omit
+        ** all OP_FkCounter related scans when either CASCADE or SET NULL
+        ** applies. The trouble starts if the CASCADE or SET NULL action 
+        ** trigger causes other triggers or action rules attached to the 
+        ** child table to fire. In these cases the fk constraint counters
+        ** might be set incorrectly if any OP_FkCounter related scans are 
+        ** omitted.  */
         if( !pFKey->isDeferred && eAction!=OE_Cascade && eAction!=OE_SetNull ){
           sqlite3MayAbort(pParse);
         }
index e9f30939302120cc333c09b0acfa2ea4d2036f5d..60bb8e4640134208c378aa0d5b343fa1d46f1921 100644 (file)
@@ -67,6 +67,28 @@ foreach {tn use_stmt sql schema} {
     CREATE TABLE c1(b REFERENCES p1 ON DELETE CASCADE, c PRIMARY KEY);
     CREATE TABLE cc1(d REFERENCES c1 ON DELETE SET NULL);
   }
+  5.3   1 "DELETE FROM p1" {
+    CREATE TABLE p1(a PRIMARY KEY);
+    CREATE TABLE c1(b REFERENCES p1 ON DELETE CASCADE, c PRIMARY KEY);
+    CREATE TABLE cc1(d REFERENCES c1 ON DELETE SET DEFAULT);
+  }
+
+  6.1   1 "UPDATE p1 SET a = ?" {
+    CREATE TABLE p1(a PRIMARY KEY);
+    CREATE TABLE c1(b REFERENCES p1 ON UPDATE SET NULL, c);
+  }
+  6.2   0 "UPDATE OR IGNORE p1 SET a = ?" {
+    CREATE TABLE p1(a PRIMARY KEY);
+    CREATE TABLE c1(b REFERENCES p1 ON UPDATE SET NULL, c);
+  }
+  6.3   1 "UPDATE OR IGNORE p1 SET a = ?" {
+    CREATE TABLE p1(a PRIMARY KEY);
+    CREATE TABLE c1(b REFERENCES p1 ON UPDATE CASCADE, c);
+  }
+  6.4   1 "UPDATE OR IGNORE p1 SET a = ?" {
+    CREATE TABLE p1(a PRIMARY KEY);
+    CREATE TABLE c1(b NOT NULL REFERENCES p1 ON UPDATE SET NULL, c);
+  }
 
 } {
   drop_all_tables
@@ -80,6 +102,5 @@ foreach {tn use_stmt sql schema} {
 }
 
 
-
-
 finish_test
+