Annotation of embedaddon/sqlite3/test/indexedby.test, revision 1.1

1.1     ! misho       1: # 2008 October 4
        !             2: #
        !             3: # The author disclaims copyright to this source code.  In place of
        !             4: # a legal notice, here is a blessing:
        !             5: #
        !             6: #    May you do good and not evil.
        !             7: #    May you find forgiveness for yourself and forgive others.
        !             8: #    May you share freely, never taking more than you give.
        !             9: #
        !            10: #***********************************************************************
        !            11: #
        !            12: # $Id: indexedby.test,v 1.5 2009/03/22 20:36:19 drh Exp $
        !            13: 
        !            14: set testdir [file dirname $argv0]
        !            15: source $testdir/tester.tcl
        !            16: 
        !            17: # Create a schema with some indexes.
        !            18: #
        !            19: do_test indexedby-1.1 {
        !            20:   execsql {
        !            21:     CREATE TABLE t1(a, b);
        !            22:     CREATE INDEX i1 ON t1(a);
        !            23:     CREATE INDEX i2 ON t1(b);
        !            24: 
        !            25:     CREATE TABLE t2(c, d);
        !            26:     CREATE INDEX i3 ON t2(c);
        !            27:     CREATE INDEX i4 ON t2(d);
        !            28: 
        !            29:     CREATE TABLE t3(e PRIMARY KEY, f);
        !            30: 
        !            31:     CREATE VIEW v1 AS SELECT * FROM t1;
        !            32:   }
        !            33: } {}
        !            34: 
        !            35: # Explain Query Plan
        !            36: #
        !            37: proc EQP {sql} {
        !            38:   uplevel "execsql {EXPLAIN QUERY PLAN $sql}"
        !            39: }
        !            40: 
        !            41: # These tests are to check that "EXPLAIN QUERY PLAN" is working as expected.
        !            42: #
        !            43: do_execsql_test indexedby-1.2 {
        !            44:   EXPLAIN QUERY PLAN select * from t1 WHERE a = 10; 
        !            45: } {0 0 0 {SEARCH TABLE t1 USING INDEX i1 (a=?) (~10 rows)}}
        !            46: do_execsql_test indexedby-1.3 {
        !            47:   EXPLAIN QUERY PLAN select * from t1 ; 
        !            48: } {0 0 0 {SCAN TABLE t1 (~1000000 rows)}}
        !            49: do_execsql_test indexedby-1.4 {
        !            50:   EXPLAIN QUERY PLAN select * from t1, t2 WHERE c = 10; 
        !            51: } {
        !            52:   0 0 1 {SEARCH TABLE t2 USING INDEX i3 (c=?) (~10 rows)} 
        !            53:   0 1 0 {SCAN TABLE t1 (~1000000 rows)}
        !            54: }
        !            55: 
        !            56: # Parser tests. Test that an INDEXED BY or NOT INDEX clause can be 
        !            57: # attached to a table in the FROM clause, but not to a sub-select or
        !            58: # SQL view. Also test that specifying an index that does not exist or
        !            59: # is attached to a different table is detected as an error.
        !            60: # 
        !            61: do_test indexedby-2.1 {
        !            62:   execsql { SELECT * FROM t1 NOT INDEXED WHERE a = 'one' AND b = 'two'}
        !            63: } {}
        !            64: do_test indexedby-2.2 {
        !            65:   execsql { SELECT * FROM t1 INDEXED BY i1 WHERE a = 'one' AND b = 'two'}
        !            66: } {}
        !            67: do_test indexedby-2.3 {
        !            68:   execsql { SELECT * FROM t1 INDEXED BY i2 WHERE a = 'one' AND b = 'two'}
        !            69: } {}
        !            70: 
        !            71: do_test indexedby-2.4 {
        !            72:   catchsql { SELECT * FROM t1 INDEXED BY i3 WHERE a = 'one' AND b = 'two'}
        !            73: } {1 {no such index: i3}}
        !            74: do_test indexedby-2.5 {
        !            75:   catchsql { SELECT * FROM t1 INDEXED BY i5 WHERE a = 'one' AND b = 'two'}
        !            76: } {1 {no such index: i5}}
        !            77: do_test indexedby-2.6 {
        !            78:   catchsql { SELECT * FROM t1 INDEXED BY WHERE a = 'one' AND b = 'two'}
        !            79: } {1 {near "WHERE": syntax error}}
        !            80: do_test indexedby-2.7 {
        !            81:   catchsql { SELECT * FROM v1 INDEXED BY i1 WHERE a = 'one' }
        !            82: } {1 {no such index: i1}}
        !            83: 
        !            84: # Tests for single table cases.
        !            85: #
        !            86: do_execsql_test indexedby-3.1 {
        !            87:   EXPLAIN QUERY PLAN SELECT * FROM t1 NOT INDEXED WHERE a = 'one' AND b = 'two'
        !            88: } {0 0 0 {SCAN TABLE t1 (~10000 rows)}}
        !            89: do_execsql_test indexedby-3.2 {
        !            90:   EXPLAIN QUERY PLAN 
        !            91:   SELECT * FROM t1 INDEXED BY i1 WHERE a = 'one' AND b = 'two'
        !            92: } {0 0 0 {SEARCH TABLE t1 USING INDEX i1 (a=?) (~2 rows)}}
        !            93: do_execsql_test indexedby-3.3 {
        !            94:   EXPLAIN QUERY PLAN 
        !            95:   SELECT * FROM t1 INDEXED BY i2 WHERE a = 'one' AND b = 'two'
        !            96: } {0 0 0 {SEARCH TABLE t1 USING INDEX i2 (b=?) (~2 rows)}}
        !            97: do_test indexedby-3.4 {
        !            98:   catchsql { SELECT * FROM t1 INDEXED BY i2 WHERE a = 'one' }
        !            99: } {1 {cannot use index: i2}}
        !           100: do_test indexedby-3.5 {
        !           101:   catchsql { SELECT * FROM t1 INDEXED BY i2 ORDER BY a }
        !           102: } {1 {cannot use index: i2}}
        !           103: do_test indexedby-3.6 {
        !           104:   catchsql { SELECT * FROM t1 INDEXED BY i1 WHERE a = 'one' }
        !           105: } {0 {}}
        !           106: do_test indexedby-3.7 {
        !           107:   catchsql { SELECT * FROM t1 INDEXED BY i1 ORDER BY a }
        !           108: } {0 {}}
        !           109: 
        !           110: do_execsql_test indexedby-3.8 {
        !           111:   EXPLAIN QUERY PLAN 
        !           112:   SELECT * FROM t3 INDEXED BY sqlite_autoindex_t3_1 ORDER BY e 
        !           113: } {0 0 0 {SCAN TABLE t3 USING INDEX sqlite_autoindex_t3_1 (~1000000 rows)}}
        !           114: do_execsql_test indexedby-3.9 {
        !           115:   EXPLAIN QUERY PLAN 
        !           116:   SELECT * FROM t3 INDEXED BY sqlite_autoindex_t3_1 WHERE e = 10 
        !           117: } {0 0 0 {SEARCH TABLE t3 USING INDEX sqlite_autoindex_t3_1 (e=?) (~1 rows)}}
        !           118: do_test indexedby-3.10 {
        !           119:   catchsql { SELECT * FROM t3 INDEXED BY sqlite_autoindex_t3_1 WHERE f = 10 }
        !           120: } {1 {cannot use index: sqlite_autoindex_t3_1}}
        !           121: do_test indexedby-3.11 {
        !           122:   catchsql { SELECT * FROM t3 INDEXED BY sqlite_autoindex_t3_2 WHERE f = 10 }
        !           123: } {1 {no such index: sqlite_autoindex_t3_2}}
        !           124: 
        !           125: # Tests for multiple table cases.
        !           126: #
        !           127: do_execsql_test indexedby-4.1 {
        !           128:   EXPLAIN QUERY PLAN SELECT * FROM t1, t2 WHERE a = c 
        !           129: } {
        !           130:   0 0 0 {SCAN TABLE t1 (~1000000 rows)} 
        !           131:   0 1 1 {SEARCH TABLE t2 USING INDEX i3 (c=?) (~10 rows)}
        !           132: }
        !           133: do_execsql_test indexedby-4.2 {
        !           134:   EXPLAIN QUERY PLAN SELECT * FROM t1 INDEXED BY i1, t2 WHERE a = c 
        !           135: } {
        !           136:   0 0 1 {SCAN TABLE t2 (~1000000 rows)} 
        !           137:   0 1 0 {SEARCH TABLE t1 USING INDEX i1 (a=?) (~10 rows)}
        !           138: }
        !           139: do_test indexedby-4.3 {
        !           140:   catchsql {
        !           141:     SELECT * FROM t1 INDEXED BY i1, t2 INDEXED BY i3 WHERE a=c
        !           142:   }
        !           143: } {1 {cannot use index: i1}}
        !           144: do_test indexedby-4.4 {
        !           145:   catchsql {
        !           146:     SELECT * FROM t2 INDEXED BY i3, t1 INDEXED BY i1 WHERE a=c
        !           147:   }
        !           148: } {1 {cannot use index: i3}}
        !           149: 
        !           150: # Test embedding an INDEXED BY in a CREATE VIEW statement. This block
        !           151: # also tests that nothing bad happens if an index refered to by
        !           152: # a CREATE VIEW statement is dropped and recreated.
        !           153: #
        !           154: do_execsql_test indexedby-5.1 {
        !           155:   CREATE VIEW v2 AS SELECT * FROM t1 INDEXED BY i1 WHERE a > 5;
        !           156:   EXPLAIN QUERY PLAN SELECT * FROM v2 
        !           157: } {0 0 0 {SEARCH TABLE t1 USING INDEX i1 (a>?) (~250000 rows)}}
        !           158: do_execsql_test indexedby-5.2 {
        !           159:   EXPLAIN QUERY PLAN SELECT * FROM v2 WHERE b = 10 
        !           160: } {0 0 0 {SEARCH TABLE t1 USING INDEX i1 (a>?) (~25000 rows)}}
        !           161: do_test indexedby-5.3 {
        !           162:   execsql { DROP INDEX i1 }
        !           163:   catchsql { SELECT * FROM v2 }
        !           164: } {1 {no such index: i1}}
        !           165: do_test indexedby-5.4 {
        !           166:   # Recreate index i1 in such a way as it cannot be used by the view query.
        !           167:   execsql { CREATE INDEX i1 ON t1(b) }
        !           168:   catchsql { SELECT * FROM v2 }
        !           169: } {1 {cannot use index: i1}}
        !           170: do_test indexedby-5.5 {
        !           171:   # Drop and recreate index i1 again. This time, create it so that it can
        !           172:   # be used by the query.
        !           173:   execsql { DROP INDEX i1 ; CREATE INDEX i1 ON t1(a) }
        !           174:   catchsql { SELECT * FROM v2 }
        !           175: } {0 {}}
        !           176: 
        !           177: # Test that "NOT INDEXED" may use the rowid index, but not others.
        !           178: # 
        !           179: do_execsql_test indexedby-6.1 {
        !           180:   EXPLAIN QUERY PLAN SELECT * FROM t1 WHERE b = 10 ORDER BY rowid 
        !           181: } {0 0 0 {SEARCH TABLE t1 USING INDEX i2 (b=?) (~10 rows)}}
        !           182: do_execsql_test indexedby-6.2 {
        !           183:   EXPLAIN QUERY PLAN SELECT * FROM t1 NOT INDEXED WHERE b = 10 ORDER BY rowid 
        !           184: } {0 0 0 {SCAN TABLE t1 USING INTEGER PRIMARY KEY (~100000 rows)}}
        !           185: 
        !           186: # Test that "INDEXED BY" can be used in a DELETE statement.
        !           187: # 
        !           188: do_execsql_test indexedby-7.1 {
        !           189:   EXPLAIN QUERY PLAN DELETE FROM t1 WHERE a = 5 
        !           190: } {0 0 0 {SEARCH TABLE t1 USING COVERING INDEX i1 (a=?) (~10 rows)}}
        !           191: do_execsql_test indexedby-7.2 {
        !           192:   EXPLAIN QUERY PLAN DELETE FROM t1 NOT INDEXED WHERE a = 5 
        !           193: } {0 0 0 {SCAN TABLE t1 (~100000 rows)}}
        !           194: do_execsql_test indexedby-7.3 {
        !           195:   EXPLAIN QUERY PLAN DELETE FROM t1 INDEXED BY i1 WHERE a = 5 
        !           196: } {0 0 0 {SEARCH TABLE t1 USING COVERING INDEX i1 (a=?) (~10 rows)}}
        !           197: do_execsql_test indexedby-7.4 {
        !           198:   EXPLAIN QUERY PLAN DELETE FROM t1 INDEXED BY i1 WHERE a = 5 AND b = 10
        !           199: } {0 0 0 {SEARCH TABLE t1 USING INDEX i1 (a=?) (~2 rows)}}
        !           200: do_execsql_test indexedby-7.5 {
        !           201:   EXPLAIN QUERY PLAN DELETE FROM t1 INDEXED BY i2 WHERE a = 5 AND b = 10
        !           202: } {0 0 0 {SEARCH TABLE t1 USING INDEX i2 (b=?) (~2 rows)}}
        !           203: do_test indexedby-7.6 {
        !           204:   catchsql { DELETE FROM t1 INDEXED BY i2 WHERE a = 5}
        !           205: } {1 {cannot use index: i2}}
        !           206: 
        !           207: # Test that "INDEXED BY" can be used in an UPDATE statement.
        !           208: # 
        !           209: do_execsql_test indexedby-8.1 {
        !           210:   EXPLAIN QUERY PLAN UPDATE t1 SET rowid=rowid+1 WHERE a = 5 
        !           211: } {0 0 0 {SEARCH TABLE t1 USING COVERING INDEX i1 (a=?) (~10 rows)}}
        !           212: do_execsql_test indexedby-8.2 {
        !           213:   EXPLAIN QUERY PLAN UPDATE t1 NOT INDEXED SET rowid=rowid+1 WHERE a = 5 
        !           214: } {0 0 0 {SCAN TABLE t1 (~100000 rows)}}
        !           215: do_execsql_test indexedby-8.3 {
        !           216:   EXPLAIN QUERY PLAN UPDATE t1 INDEXED BY i1 SET rowid=rowid+1 WHERE a = 5 
        !           217: } {0 0 0 {SEARCH TABLE t1 USING COVERING INDEX i1 (a=?) (~10 rows)}}
        !           218: do_execsql_test indexedby-8.4 {
        !           219:   EXPLAIN QUERY PLAN 
        !           220:   UPDATE t1 INDEXED BY i1 SET rowid=rowid+1 WHERE a = 5 AND b = 10
        !           221: } {0 0 0 {SEARCH TABLE t1 USING INDEX i1 (a=?) (~2 rows)}}
        !           222: do_execsql_test indexedby-8.5 {
        !           223:   EXPLAIN QUERY PLAN 
        !           224:   UPDATE t1 INDEXED BY i2 SET rowid=rowid+1 WHERE a = 5 AND b = 10
        !           225: } {0 0 0 {SEARCH TABLE t1 USING INDEX i2 (b=?) (~2 rows)}}
        !           226: do_test indexedby-8.6 {
        !           227:   catchsql { UPDATE t1 INDEXED BY i2 SET rowid=rowid+1 WHERE a = 5}
        !           228: } {1 {cannot use index: i2}}
        !           229: 
        !           230: # Test that bug #3560 is fixed.
        !           231: #
        !           232: do_test indexedby-9.1 {
        !           233:   execsql {
        !           234:     CREATE TABLE maintable( id integer);
        !           235:     CREATE TABLE joinme(id_int integer, id_text text);
        !           236:     CREATE INDEX joinme_id_text_idx on joinme(id_text);
        !           237:     CREATE INDEX joinme_id_int_idx on joinme(id_int);
        !           238:   }
        !           239: } {}
        !           240: do_test indexedby-9.2 {
        !           241:   catchsql {
        !           242:     select * from maintable as m inner join
        !           243:     joinme as j indexed by joinme_id_text_idx
        !           244:     on ( m.id  = j.id_int)
        !           245:   }
        !           246: } {1 {cannot use index: joinme_id_text_idx}}
        !           247: do_test indexedby-9.3 {
        !           248:   catchsql { select * from maintable, joinme INDEXED by joinme_id_text_idx }
        !           249: } {1 {cannot use index: joinme_id_text_idx}}
        !           250: 
        !           251: # Make sure we can still create tables, indices, and columns whose name
        !           252: # is "indexed".
        !           253: #
        !           254: do_test indexedby-10.1 {
        !           255:   execsql {
        !           256:     CREATE TABLE indexed(x,y);
        !           257:     INSERT INTO indexed VALUES(1,2);
        !           258:     SELECT * FROM indexed;
        !           259:   }
        !           260: } {1 2}
        !           261: do_test indexedby-10.2 {
        !           262:   execsql {
        !           263:     CREATE INDEX i10 ON indexed(x);
        !           264:     SELECT * FROM indexed indexed by i10 where x>0;
        !           265:   }
        !           266: } {1 2}
        !           267: do_test indexedby-10.3 {
        !           268:   execsql {
        !           269:     DROP TABLE indexed;
        !           270:     CREATE TABLE t10(indexed INTEGER);
        !           271:     INSERT INTO t10 VALUES(1);
        !           272:     CREATE INDEX indexed ON t10(indexed);
        !           273:     SELECT * FROM t10 indexed by indexed WHERE indexed>0
        !           274:   }
        !           275: } {1}
        !           276: 
        !           277: finish_test

FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>