/ Check-in [4d34a3d4]
Login

Many hyperlinks are disabled.
Use anonymous login to enable hyperlinks.

Overview
Comment:Fix the error message returned by sqlite3session_diff() for tables with no PRIMARY KEY.
Downloads: Tarball | ZIP archive | SQL archive
Timelines: family | ancestors | descendants | both | sessions
Files: files | file ages | folders
SHA1: 4d34a3d40da210bebb2a2e6dff094f9a39c92798
User & Date: dan 2015-04-23 15:03:14
Context
2015-04-23
17:22
Modify the sqlite3session_diff() API so that tables with no PRIMARY KEYs are ignored. This matches the other sessions APIs. Also change sqlite3session_diff() so that it returns SQLITE_SCHEMA, instead of SQLITE_ERROR, if the tables being compared do not have compatible schemas. check-in: aada0ad0 user: dan tags: sessions
15:03
Fix the error message returned by sqlite3session_diff() for tables with no PRIMARY KEY. check-in: 4d34a3d4 user: dan tags: sessions
14:40
Fix a performance problem in sqlite3session_diff(). check-in: ea400eca user: dan tags: sessions
Changes
Hide Diffs Side-by-Side Diffs Ignore Whitespace Patch

Changes to ext/session/sessionD.test.

   180    180     CREATE TABLE t3(a, b, c, PRIMARY KEY(a, b, c));
   181    181     INSERT INTO t3 VALUES(1, 2, 3);
   182    182     INSERT INTO t3 VALUES(4, 5, 6);
   183    183     INSERT INTO t3 VALUES(7, 8, 9);
   184    184   }
   185    185   do_empty_diff_test 3.1
   186    186   
          187  +
          188  +#-------------------------------------------------------------------------
          189  +# Test some error cases:
          190  +# 
          191  +#   1) schema mismatches between the two dbs, and 
          192  +#   2) tables with no primary keys.
          193  +#
          194  +reset_db
          195  +forcedelete test.db2
          196  +do_execsql_test 4.0 {
          197  +  ATTACH 'test.db2' AS ixua;
          198  +  CREATE TABLE ixua.t1(a, b, c);
          199  +  CREATE TABLE main.t1(a, b, c);
          200  +
          201  +  CREATE TABLE ixua.t2(a PRIMARY KEY, b, c);
          202  +  CREATE TABLE main.t2(a PRIMARY KEY, b, x);
          203  +}
          204  +
          205  +do_test 4.1 {
          206  +  sqlite3session S db main
          207  +  S attach t1
          208  +  list [catch { S diff ixua t1 } msg] $msg
          209  +} {1 {table has no primary key}}
          210  +
          211  +do_test 4.2 {
          212  +  S attach t2
          213  +  list [catch { S diff ixua t2 } msg] $msg
          214  +} {1 {table schemas do not match}}
          215  +
          216  +S delete
          217  +
   187    218   finish_test
   188    219   

Changes to ext/session/sqlite3session.c.

  1469   1469         rc = pSession->rc = sessionTableInfo(db, zDb, 
  1470   1470             pTo->zName, &pTo->nCol, 0, &pTo->azCol, &pTo->abPK
  1471   1471         );
  1472   1472       }
  1473   1473   
  1474   1474       /* Check the table schemas match */
  1475   1475       if( rc==SQLITE_OK ){
         1476  +      int bHasPk = 0;
  1476   1477         int nCol;                   /* Columns in zFrom.zTbl */
  1477   1478         u8 *abPK;
  1478   1479         const char **azCol = 0;
  1479   1480         rc = sessionTableInfo(db, zFrom, zTbl, &nCol, 0, &azCol, &abPK);
  1480   1481         if( rc==SQLITE_OK ){
  1481   1482           int bMismatch = 0;
  1482         -        if( pTo->nCol!=nCol || memcmp(pTo->abPK, abPK, nCol) ){
         1483  +        if( pTo->nCol!=nCol ){
  1483   1484             bMismatch = 1;
  1484   1485           }else{
  1485   1486             int i;
  1486   1487             for(i=0; i<nCol; i++){
         1488  +            if( pTo->abPK[i]!=abPK[i] ) bMismatch = 1;
  1487   1489               if( sqlite3_stricmp(azCol[i], pTo->azCol[i]) ) bMismatch = 1;
         1490  +            if( abPK[i] ) bHasPk = 1;
  1488   1491             }
  1489   1492           }
  1490   1493   
  1491   1494           if( bMismatch ){
  1492   1495             *pzErrMsg = sqlite3_mprintf("table schemas do not match");
  1493   1496             rc = SQLITE_ERROR;
  1494   1497           }
         1498  +        if( bHasPk==0 ){
         1499  +          *pzErrMsg = sqlite3_mprintf("table has no primary key");
         1500  +          rc = SQLITE_ERROR;
         1501  +        }
  1495   1502         }
  1496   1503         sqlite3_free(azCol);
  1497   1504       }
  1498   1505   
  1499   1506       if( rc==SQLITE_OK ){
  1500   1507         zExpr = sessionExprComparePK(pTo->nCol, 
  1501   1508             zDb, zFrom, pTo->zName, pTo->azCol, pTo->abPK

Changes to ext/session/test_session.c.

   224    224             Tcl_GetString(objv[2]),
   225    225             Tcl_GetString(objv[3]),
   226    226             &zErr
   227    227         );
   228    228         assert( rc!=SQLITE_OK || zErr==0 );
   229    229         if( zErr ){
   230    230           Tcl_AppendResult(interp, zErr, 0);
          231  +        sqlite3_free(zErr);
   231    232           return TCL_ERROR;
   232    233         }
   233    234         if( rc ){
   234    235           return test_session_error(interp, rc);
   235    236         }
   236    237         break;
   237    238       }