CREATE TABLE t1(a, b, c, PRIMARY KEY(a, c));
CREATE INDEX i1 ON t1(b);
}
+
+ 10 {
+ CREATE TABLE t1(a INTEGER PRIMARY KEY, b, c);
+ CREATE INDEX i1 ON t1(b DESC);
+ }
+
+ 11 {
+ CREATE TABLE t1(a INTEGER PRIMARY KEY, b, c);
+ CREATE INDEX i1 ON t1(b DESC, a ASC, c DESC);
+ }
+
+ 12 {
+ CREATE TABLE t1(a INT PRIMARY KEY DESC, b, c) WITHOUT ROWID;
+ }
+
+ 13 {
+ CREATE TABLE t1(a INT, b, c, PRIMARY KEY(a DESC)) WITHOUT ROWID;
+ }
+
+ 14 {
+ CREATE TABLE t1(a, b, c, PRIMARY KEY(a DESC, c)) WITHOUT ROWID;
+ CREATE INDEX i1 ON t1(b);
+ }
+
+ 15 {
+ CREATE TABLE t1(a, b, c, PRIMARY KEY(a, c DESC)) WITHOUT ROWID;
+ CREATE INDEX i1 ON t1(b);
+ }
+
+ 16 {
+ CREATE TABLE t1(a, b, c, PRIMARY KEY(c DESC, a)) WITHOUT ROWID;
+ CREATE INDEX i1 ON t1(b DESC, c, a);
+ }
} {
reset_db
execsql $schema
$cmd test.db ota.db
} {SQLITE_DONE}
- do_execsql_test 1.$tn2.$tn.2 {
- SELECT * FROM t1 ORDER BY a ASC;
- } {
+ do_execsql_test 1.$tn2.$tn.2 { SELECT * FROM t1 ORDER BY a ASC } {
1 2 3
2 two three
3 {} 8.2
}
+ do_execsql_test 1.$tn2.$tn.3 { SELECT * FROM t1 ORDER BY b ASC } {
+ 3 {} 8.2
+ 1 2 3
+ 2 two three
+ }
+ do_execsql_test 1.$tn2.$tn.4 { SELECT * FROM t1 ORDER BY c ASC } {
+ 1 2 3
+ 3 {} 8.2
+ 2 two three
+ }
- do_execsql_test 1.$tn2.$tn.3 { PRAGMA integrity_check } ok
+ do_execsql_test 1.$tn2.$tn.5 { PRAGMA integrity_check } ok
}
}
CREATE INDEX i2 ON t1(c, b);
CREATE INDEX i3 ON t1(c, b, c);
}
+
+ 6 {
+ CREATE TABLE t1(a INT PRIMARY KEY DESC, b, c);
+ CREATE INDEX i1 ON t1(b DESC);
+ CREATE INDEX i2 ON t1(c, b);
+ CREATE INDEX i3 ON t1(c DESC, b, c);
+ }
+ 7 {
+ CREATE TABLE t1(a INT PRIMARY KEY DESC, b, c) WITHOUT ROWID;
+ CREATE INDEX i1 ON t1(b);
+ CREATE INDEX i2 ON t1(c, b);
+ CREATE INDEX i3 ON t1(c, b, c);
+ }
} {
reset_db
execsql $schema
}
while( rc==SQLITE_OK && SQLITE_ROW==sqlite3_step(pXInfo) ){
- const char *zCollate = (const char*)sqlite3_column_text(pXInfo, 4);
int iCid = sqlite3_column_int(pXInfo, 1);
+ int bDesc = sqlite3_column_int(pXInfo, 3);
+ const char *zCollate = (const char*)sqlite3_column_text(pXInfo, 4);
const char *zCol;
const char *zType;
zRet = sqlite3_mprintf("%z%s\"%w\" COLLATE %Q", zRet, zCom, zCol, zCollate);
if( pIter->bUnique==0 || sqlite3_column_int(pXInfo, 5) ){
- zImpPK = sqlite3_mprintf("%z%sc%d", zImpPK, zCom, nBind);
+ const char *zOrder = (bDesc ? " DESC" : "");
+ zImpPK = sqlite3_mprintf("%z%sc%d%s", zImpPK, zCom, nBind, zOrder);
}
zImpCols = sqlite3_mprintf(
"%z%sc%d %s COLLATE %Q", zImpCols, zCom, nBind, zType, zCollate
return zRet;
}
+/*
+** The iterator currently points to a table (not index) of type
+** OTA_PK_WITHOUT_ROWID. This function creates the PRIMARY KEY
+** declaration for the corresponding imposter table. For example,
+** if the iterator points to a table created as:
+**
+** CREATE TABLE t1(a, b, c, PRIMARY KEY(b, a DESC)) WITHOUT ROWID
+**
+** this function returns:
+**
+** PRIMARY KEY("b", "a" DESC)
+*/
+static char *otaWithoutRowidPK(sqlite3ota *p, OtaObjIter *pIter){
+ char *z = 0;
+ assert( pIter->zIdx==0 );
+ if( p->rc==SQLITE_OK ){
+ const char *zSep = "PRIMARY KEY(";
+ sqlite3_stmt *pXInfo = 0; /* PRAGMA index_xinfo = (pIter->zTbl) */
+ int rc; /* sqlite3_finalize() return code */
+
+ p->rc = prepareFreeAndCollectError(p->db, &pXInfo, &p->zErrmsg,
+ sqlite3_mprintf("PRAGMA main.index_xinfo = %Q", pIter->zTbl)
+ );
+ while( p->rc==SQLITE_OK && SQLITE_ROW==sqlite3_step(pXInfo) ){
+ if( sqlite3_column_int(pXInfo, 5) ){
+ /* int iCid = sqlite3_column_int(pXInfo, 0); */
+ const char *zCol = (const char*)sqlite3_column_text(pXInfo, 2);
+ const char *zDesc = sqlite3_column_int(pXInfo, 3) ? " DESC" : "";
+ z = otaMPrintfAndCollectError(p, "%z%s\"%w\"%s", z, zSep, zCol, zDesc);
+ zSep = ", ";
+ }
+ }
+ z = otaMPrintfAndCollectError(p, "%z)", z);
+
+ rc = sqlite3_finalize(pXInfo);
+ if( p->rc==SQLITE_OK ) p->rc = rc;
+ }
+ return z;
+}
+
/*
** If an error has already occurred when this function is called, it
** immediately returns zero (without doing any work). Or, if an error
sqlite3_test_control(SQLITE_TESTCTRL_IMPOSTER, p->db, "main", 0, 1);
for(iCol=0; p->rc==SQLITE_OK && iCol<pIter->nTblCol; iCol++){
+ const char *zPk = "";
int iDataCol = pIter->aiTblOrder[iCol];
const char *zCol = pIter->azTblCol[iDataCol];
const char *zColl = 0;
+
p->rc = sqlite3_table_column_metadata(
p->db, "main", pIter->zTbl, zCol, 0, &zColl, 0, 0, 0
);
- zSql = otaMPrintfAndCollectError(p, "%z%s\"%w\" %s COLLATE %s",
- zSql, zComma, zCol, pIter->azTblType[iDataCol], zColl
+
+ if( pIter->eType==OTA_PK_IPK && pIter->abTblPk[iCol] ){
+ /* If the target table column is an "INTEGER PRIMARY KEY", add
+ ** "PRIMARY KEY" to the imposter table column declaration. */
+ zPk = "PRIMARY KEY ";
+ }
+ zSql = otaMPrintfAndCollectError(p, "%z%s\"%w\" %s %sCOLLATE %s",
+ zSql, zComma, zCol, pIter->azTblType[iDataCol], zPk, zColl
);
zComma = ", ";
}
- if( pIter->eType==OTA_PK_IPK || pIter->eType==OTA_PK_WITHOUT_ROWID ){
- zSql = otaMPrintfAndCollectError(p, "%z, PRIMARY KEY(", zSql);
- zComma = "";
- for(iCol=0; iCol<pIter->nTblCol; iCol++){
- if( pIter->abTblPk[iCol] ){
- zSql = otaMPrintfAndCollectError(p, "%z%s\"%w\"",
- zSql, zComma, pIter->azTblCol[iCol]
- );
- zComma = ", ";
- }
+ if( pIter->eType==OTA_PK_WITHOUT_ROWID ){
+ char *zPk = otaWithoutRowidPK(p, pIter);
+ if( zPk ){
+ zSql = otaMPrintfAndCollectError(p, "%z, %z", zSql, zPk);
}
- zSql = otaMPrintfAndCollectError(p, "%z)", zSql);
}
zSql = otaMPrintfAndCollectError(p, "CREATE TABLE ota_imposter(%z)%s",
-C Remove\s"PRAGMA\sota_mode".
-D 2015-02-03T15:56:08.271
+C Fix\ssome\sproblems\ssurrounding\sWITHOUT\sROWID\stables\swith\sDESC\sprimary\skey\sindexes\n.
+D 2015-02-03T18:43:42.428
F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f
F Makefile.in 5407a688f4d77a05c18a8142be8ae5a2829dd610
F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23
F ext/misc/wholenumber.c 784b12543d60702ebdd47da936e278aa03076212
F ext/ota/README.txt 78d4a9f78f567d4bf826cf0f02df6254902562ca
F ext/ota/ota.c c11a85af71dccc45976622fe7a51169a481caa91
-F ext/ota/ota1.test d76b9ec77437759e9da0ff4abe9c070bb9f4eae1
+F ext/ota/ota1.test 719854e444dff2ead58ff6b62d8315954bd7762a
F ext/ota/ota10.test ab815dff9cef7248c504f06b888627d236f25e9c
F ext/ota/ota2.test 2829bc08ffbb71b605392a68fedfd554763356a7
F ext/ota/ota3.test a77efbce7723332eb688d2b28bf18204fc9614d7
F ext/ota/ota8.test cd70e63a0c29c45c0906692827deafa34638feda
F ext/ota/ota9.test d3eee95dd836824d07a22e5efcdb7bf6e869358b
F ext/ota/otafault.test 508ba87c83d632670ac0f94371a465d4bb4d49dd
-F ext/ota/sqlite3ota.c 52c91eec41b8fbb5ed12a8f0a2159bc5ec16498f
+F ext/ota/sqlite3ota.c de2e605697871de02fd9ea717a57c00bf022a27e
F ext/ota/sqlite3ota.h ce378c0c503f625611713133f9c79704ea4ee7a4
F ext/rtree/README 6315c0d73ebf0ec40dedb5aa0e942bc8b54e3761
F ext/rtree/rtree.c 14e6239434d4e3f65d3e90320713f26aa24e167f
F src/pcache.c d210cf90d04365a74f85d21374dded65af67b0cb
F src/pcache.h b44658c9c932d203510279439d891a2a83e12ba8
F src/pcache1.c 1e77432b40b7d3288327d9cdf399dcdfd2b6d3bf
-F src/pragma.c 26fc55619109828c9b7add4cfa8a961b6f4c456d
+F src/pragma.c e39954ff47e287f88bdf9e9adb123da029e83d9f
F src/prepare.c 173a5a499138451b2561614ecb87d78f9f4644b9
F src/printf.c 05edc41450d0eb2c05ef7db113bf32742ae65325
F src/random.c ba2679f80ec82c4190062d756f22d0c358180696
F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4
F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32
F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f
-P cdaeab467f6aa3217be161377a9b78a4eec37093
-R 2703aba199c695992db82956950982ca
+P 1c111447a07687c30ed4ad5a6c27a169c85b7ea6
+R 544935f49f95af3db3c849fcc1fc392c
U dan
-Z fae9dc4e5e5c1a2d2a162b422a05ccf9
+Z 5f7217c8a4b7a144888c5aa7b5260598