diff options
Diffstat (limited to 'libraries/sqlite/unix/sqlite-3.5.1/test/table.test')
-rw-r--r-- | libraries/sqlite/unix/sqlite-3.5.1/test/table.test | 674 |
1 files changed, 674 insertions, 0 deletions
diff --git a/libraries/sqlite/unix/sqlite-3.5.1/test/table.test b/libraries/sqlite/unix/sqlite-3.5.1/test/table.test new file mode 100644 index 0000000..718f171 --- /dev/null +++ b/libraries/sqlite/unix/sqlite-3.5.1/test/table.test | |||
@@ -0,0 +1,674 @@ | |||
1 | # 2001 September 15 | ||
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 | # This file implements regression tests for SQLite library. The | ||
12 | # focus of this file is testing the CREATE TABLE statement. | ||
13 | # | ||
14 | # $Id: table.test,v 1.47 2007/05/02 17:54:56 drh Exp $ | ||
15 | |||
16 | set testdir [file dirname $argv0] | ||
17 | source $testdir/tester.tcl | ||
18 | |||
19 | # Create a basic table and verify it is added to sqlite_master | ||
20 | # | ||
21 | do_test table-1.1 { | ||
22 | execsql { | ||
23 | CREATE TABLE test1 ( | ||
24 | one varchar(10), | ||
25 | two text | ||
26 | ) | ||
27 | } | ||
28 | execsql { | ||
29 | SELECT sql FROM sqlite_master WHERE type!='meta' | ||
30 | } | ||
31 | } {{CREATE TABLE test1 ( | ||
32 | one varchar(10), | ||
33 | two text | ||
34 | )}} | ||
35 | |||
36 | |||
37 | # Verify the other fields of the sqlite_master file. | ||
38 | # | ||
39 | do_test table-1.3 { | ||
40 | execsql {SELECT name, tbl_name, type FROM sqlite_master WHERE type!='meta'} | ||
41 | } {test1 test1 table} | ||
42 | |||
43 | # Close and reopen the database. Verify that everything is | ||
44 | # still the same. | ||
45 | # | ||
46 | do_test table-1.4 { | ||
47 | db close | ||
48 | sqlite3 db test.db | ||
49 | execsql {SELECT name, tbl_name, type from sqlite_master WHERE type!='meta'} | ||
50 | } {test1 test1 table} | ||
51 | |||
52 | # Drop the database and make sure it disappears. | ||
53 | # | ||
54 | do_test table-1.5 { | ||
55 | execsql {DROP TABLE test1} | ||
56 | execsql {SELECT * FROM sqlite_master WHERE type!='meta'} | ||
57 | } {} | ||
58 | |||
59 | # Close and reopen the database. Verify that the table is | ||
60 | # still gone. | ||
61 | # | ||
62 | do_test table-1.6 { | ||
63 | db close | ||
64 | sqlite3 db test.db | ||
65 | execsql {SELECT name FROM sqlite_master WHERE type!='meta'} | ||
66 | } {} | ||
67 | |||
68 | # Repeat the above steps, but this time quote the table name. | ||
69 | # | ||
70 | do_test table-1.10 { | ||
71 | execsql {CREATE TABLE "create" (f1 int)} | ||
72 | execsql {SELECT name FROM sqlite_master WHERE type!='meta'} | ||
73 | } {create} | ||
74 | do_test table-1.11 { | ||
75 | execsql {DROP TABLE "create"} | ||
76 | execsql {SELECT name FROM "sqlite_master" WHERE type!='meta'} | ||
77 | } {} | ||
78 | do_test table-1.12 { | ||
79 | execsql {CREATE TABLE test1("f1 ho" int)} | ||
80 | execsql {SELECT name as "X" FROM sqlite_master WHERE type!='meta'} | ||
81 | } {test1} | ||
82 | do_test table-1.13 { | ||
83 | execsql {DROP TABLE "TEST1"} | ||
84 | execsql {SELECT name FROM "sqlite_master" WHERE type!='meta'} | ||
85 | } {} | ||
86 | |||
87 | |||
88 | |||
89 | # Verify that we cannot make two tables with the same name | ||
90 | # | ||
91 | do_test table-2.1 { | ||
92 | execsql {CREATE TABLE TEST2(one text)} | ||
93 | catchsql {CREATE TABLE test2(two text default 'hi')} | ||
94 | } {1 {table test2 already exists}} | ||
95 | do_test table-2.1.1 { | ||
96 | catchsql {CREATE TABLE "test2" (two)} | ||
97 | } {1 {table "test2" already exists}} | ||
98 | do_test table-2.1b { | ||
99 | set v [catch {execsql {CREATE TABLE sqlite_master(two text)}} msg] | ||
100 | lappend v $msg | ||
101 | } {1 {object name reserved for internal use: sqlite_master}} | ||
102 | do_test table-2.1c { | ||
103 | db close | ||
104 | sqlite3 db test.db | ||
105 | set v [catch {execsql {CREATE TABLE sqlite_master(two text)}} msg] | ||
106 | lappend v $msg | ||
107 | } {1 {object name reserved for internal use: sqlite_master}} | ||
108 | do_test table-2.1d { | ||
109 | catchsql {CREATE TABLE IF NOT EXISTS test2(x,y)} | ||
110 | } {0 {}} | ||
111 | do_test table-2.1e { | ||
112 | catchsql {CREATE TABLE IF NOT EXISTS test2(x UNIQUE, y TEXT PRIMARY KEY)} | ||
113 | } {0 {}} | ||
114 | do_test table-2.1f { | ||
115 | execsql {DROP TABLE test2; SELECT name FROM sqlite_master WHERE type!='meta'} | ||
116 | } {} | ||
117 | |||
118 | # Verify that we cannot make a table with the same name as an index | ||
119 | # | ||
120 | do_test table-2.2a { | ||
121 | execsql {CREATE TABLE test2(one text); CREATE INDEX test3 ON test2(one)} | ||
122 | set v [catch {execsql {CREATE TABLE test3(two text)}} msg] | ||
123 | lappend v $msg | ||
124 | } {1 {there is already an index named test3}} | ||
125 | do_test table-2.2b { | ||
126 | db close | ||
127 | sqlite3 db test.db | ||
128 | set v [catch {execsql {CREATE TABLE test3(two text)}} msg] | ||
129 | lappend v $msg | ||
130 | } {1 {there is already an index named test3}} | ||
131 | do_test table-2.2c { | ||
132 | execsql {SELECT name FROM sqlite_master WHERE type!='meta' ORDER BY name} | ||
133 | } {test2 test3} | ||
134 | do_test table-2.2d { | ||
135 | execsql {DROP INDEX test3} | ||
136 | set v [catch {execsql {CREATE TABLE test3(two text)}} msg] | ||
137 | lappend v $msg | ||
138 | } {0 {}} | ||
139 | do_test table-2.2e { | ||
140 | execsql {SELECT name FROM sqlite_master WHERE type!='meta' ORDER BY name} | ||
141 | } {test2 test3} | ||
142 | do_test table-2.2f { | ||
143 | execsql {DROP TABLE test2; DROP TABLE test3} | ||
144 | execsql {SELECT name FROM sqlite_master WHERE type!='meta' ORDER BY name} | ||
145 | } {} | ||
146 | |||
147 | # Create a table with many field names | ||
148 | # | ||
149 | set big_table \ | ||
150 | {CREATE TABLE big( | ||
151 | f1 varchar(20), | ||
152 | f2 char(10), | ||
153 | f3 varchar(30) primary key, | ||
154 | f4 text, | ||
155 | f5 text, | ||
156 | f6 text, | ||
157 | f7 text, | ||
158 | f8 text, | ||
159 | f9 text, | ||
160 | f10 text, | ||
161 | f11 text, | ||
162 | f12 text, | ||
163 | f13 text, | ||
164 | f14 text, | ||
165 | f15 text, | ||
166 | f16 text, | ||
167 | f17 text, | ||
168 | f18 text, | ||
169 | f19 text, | ||
170 | f20 text | ||
171 | )} | ||
172 | do_test table-3.1 { | ||
173 | execsql $big_table | ||
174 | execsql {SELECT sql FROM sqlite_master WHERE type=='table'} | ||
175 | } \{$big_table\} | ||
176 | do_test table-3.2 { | ||
177 | set v [catch {execsql {CREATE TABLE BIG(xyz foo)}} msg] | ||
178 | lappend v $msg | ||
179 | } {1 {table BIG already exists}} | ||
180 | do_test table-3.3 { | ||
181 | set v [catch {execsql {CREATE TABLE biG(xyz foo)}} msg] | ||
182 | lappend v $msg | ||
183 | } {1 {table biG already exists}} | ||
184 | do_test table-3.4 { | ||
185 | set v [catch {execsql {CREATE TABLE bIg(xyz foo)}} msg] | ||
186 | lappend v $msg | ||
187 | } {1 {table bIg already exists}} | ||
188 | do_test table-3.5 { | ||
189 | db close | ||
190 | sqlite3 db test.db | ||
191 | set v [catch {execsql {CREATE TABLE Big(xyz foo)}} msg] | ||
192 | lappend v $msg | ||
193 | } {1 {table Big already exists}} | ||
194 | do_test table-3.6 { | ||
195 | execsql {DROP TABLE big} | ||
196 | execsql {SELECT name FROM sqlite_master WHERE type!='meta'} | ||
197 | } {} | ||
198 | |||
199 | # Try creating large numbers of tables | ||
200 | # | ||
201 | set r {} | ||
202 | for {set i 1} {$i<=100} {incr i} { | ||
203 | lappend r [format test%03d $i] | ||
204 | } | ||
205 | do_test table-4.1 { | ||
206 | for {set i 1} {$i<=100} {incr i} { | ||
207 | set sql "CREATE TABLE [format test%03d $i] (" | ||
208 | for {set k 1} {$k<$i} {incr k} { | ||
209 | append sql "field$k text," | ||
210 | } | ||
211 | append sql "last_field text)" | ||
212 | execsql $sql | ||
213 | } | ||
214 | execsql {SELECT name FROM sqlite_master WHERE type!='meta' ORDER BY name} | ||
215 | } $r | ||
216 | do_test table-4.1b { | ||
217 | db close | ||
218 | sqlite3 db test.db | ||
219 | execsql {SELECT name FROM sqlite_master WHERE type!='meta' ORDER BY name} | ||
220 | } $r | ||
221 | |||
222 | # Drop the even numbered tables | ||
223 | # | ||
224 | set r {} | ||
225 | for {set i 1} {$i<=100} {incr i 2} { | ||
226 | lappend r [format test%03d $i] | ||
227 | } | ||
228 | do_test table-4.2 { | ||
229 | for {set i 2} {$i<=100} {incr i 2} { | ||
230 | # if {$i==38} {execsql {pragma vdbe_trace=on}} | ||
231 | set sql "DROP TABLE [format TEST%03d $i]" | ||
232 | execsql $sql | ||
233 | } | ||
234 | execsql {SELECT name FROM sqlite_master WHERE type!='meta' ORDER BY name} | ||
235 | } $r | ||
236 | #exit | ||
237 | |||
238 | # Drop the odd number tables | ||
239 | # | ||
240 | do_test table-4.3 { | ||
241 | for {set i 1} {$i<=100} {incr i 2} { | ||
242 | set sql "DROP TABLE [format test%03d $i]" | ||
243 | execsql $sql | ||
244 | } | ||
245 | execsql {SELECT name FROM sqlite_master WHERE type!='meta' ORDER BY name} | ||
246 | } {} | ||
247 | |||
248 | # Try to drop a table that does not exist | ||
249 | # | ||
250 | do_test table-5.1.1 { | ||
251 | catchsql {DROP TABLE test009} | ||
252 | } {1 {no such table: test009}} | ||
253 | do_test table-5.1.2 { | ||
254 | catchsql {DROP TABLE IF EXISTS test009} | ||
255 | } {0 {}} | ||
256 | |||
257 | # Try to drop sqlite_master | ||
258 | # | ||
259 | do_test table-5.2 { | ||
260 | catchsql {DROP TABLE IF EXISTS sqlite_master} | ||
261 | } {1 {table sqlite_master may not be dropped}} | ||
262 | |||
263 | # Make sure an EXPLAIN does not really create a new table | ||
264 | # | ||
265 | do_test table-5.3 { | ||
266 | ifcapable {explain} { | ||
267 | execsql {EXPLAIN CREATE TABLE test1(f1 int)} | ||
268 | } | ||
269 | execsql {SELECT name FROM sqlite_master WHERE type!='meta'} | ||
270 | } {} | ||
271 | |||
272 | # Make sure an EXPLAIN does not really drop an existing table | ||
273 | # | ||
274 | do_test table-5.4 { | ||
275 | execsql {CREATE TABLE test1(f1 int)} | ||
276 | ifcapable {explain} { | ||
277 | execsql {EXPLAIN DROP TABLE test1} | ||
278 | } | ||
279 | execsql {SELECT name FROM sqlite_master WHERE type!='meta'} | ||
280 | } {test1} | ||
281 | |||
282 | # Create a table with a goofy name | ||
283 | # | ||
284 | #do_test table-6.1 { | ||
285 | # execsql {CREATE TABLE 'Spaces In This Name!'(x int)} | ||
286 | # execsql {INSERT INTO 'spaces in this name!' VALUES(1)} | ||
287 | # set list [glob -nocomplain testdb/spaces*.tbl] | ||
288 | #} {testdb/spaces+in+this+name+.tbl} | ||
289 | |||
290 | # Try using keywords as table names or column names. | ||
291 | # | ||
292 | do_test table-7.1 { | ||
293 | set v [catch {execsql { | ||
294 | CREATE TABLE weird( | ||
295 | desc text, | ||
296 | asc text, | ||
297 | key int, | ||
298 | [14_vac] boolean, | ||
299 | fuzzy_dog_12 varchar(10), | ||
300 | begin blob, | ||
301 | end clob | ||
302 | ) | ||
303 | }} msg] | ||
304 | lappend v $msg | ||
305 | } {0 {}} | ||
306 | do_test table-7.2 { | ||
307 | execsql { | ||
308 | INSERT INTO weird VALUES('a','b',9,0,'xyz','hi','y''all'); | ||
309 | SELECT * FROM weird; | ||
310 | } | ||
311 | } {a b 9 0 xyz hi y'all} | ||
312 | do_test table-7.3 { | ||
313 | execsql2 { | ||
314 | SELECT * FROM weird; | ||
315 | } | ||
316 | } {desc a asc b key 9 14_vac 0 fuzzy_dog_12 xyz begin hi end y'all} | ||
317 | |||
318 | # Try out the CREATE TABLE AS syntax | ||
319 | # | ||
320 | do_test table-8.1 { | ||
321 | execsql2 { | ||
322 | CREATE TABLE t2 AS SELECT * FROM weird; | ||
323 | SELECT * FROM t2; | ||
324 | } | ||
325 | } {desc a asc b key 9 14_vac 0 fuzzy_dog_12 xyz begin hi end y'all} | ||
326 | do_test table-8.1.1 { | ||
327 | execsql { | ||
328 | SELECT sql FROM sqlite_master WHERE name='t2'; | ||
329 | } | ||
330 | } {{CREATE TABLE t2( | ||
331 | "desc" text, | ||
332 | "asc" text, | ||
333 | "key" int, | ||
334 | "14_vac" boolean, | ||
335 | fuzzy_dog_12 varchar(10), | ||
336 | "begin" blob, | ||
337 | "end" clob | ||
338 | )}} | ||
339 | do_test table-8.2 { | ||
340 | execsql { | ||
341 | CREATE TABLE "t3""xyz"(a,b,c); | ||
342 | INSERT INTO [t3"xyz] VALUES(1,2,3); | ||
343 | SELECT * FROM [t3"xyz]; | ||
344 | } | ||
345 | } {1 2 3} | ||
346 | do_test table-8.3 { | ||
347 | execsql2 { | ||
348 | CREATE TABLE [t4"abc] AS SELECT count(*) as cnt, max(b+c) FROM [t3"xyz]; | ||
349 | SELECT * FROM [t4"abc]; | ||
350 | } | ||
351 | } {cnt 1 max(b+c) 5} | ||
352 | |||
353 | # Update for v3: The declaration type of anything except a column is now a | ||
354 | # NULL pointer, so the created table has no column types. (Changed result | ||
355 | # from {{CREATE TABLE 't4"abc'(cnt NUMERIC,"max(b+c)" NUMERIC)}}). | ||
356 | do_test table-8.3.1 { | ||
357 | execsql { | ||
358 | SELECT sql FROM sqlite_master WHERE name='t4"abc' | ||
359 | } | ||
360 | } {{CREATE TABLE "t4""abc"(cnt,"max(b+c)")}} | ||
361 | |||
362 | ifcapable tempdb { | ||
363 | do_test table-8.4 { | ||
364 | execsql2 { | ||
365 | CREATE TEMPORARY TABLE t5 AS SELECT count(*) AS [y'all] FROM [t3"xyz]; | ||
366 | SELECT * FROM t5; | ||
367 | } | ||
368 | } {y'all 1} | ||
369 | } | ||
370 | |||
371 | do_test table-8.5 { | ||
372 | db close | ||
373 | sqlite3 db test.db | ||
374 | execsql2 { | ||
375 | SELECT * FROM [t4"abc]; | ||
376 | } | ||
377 | } {cnt 1 max(b+c) 5} | ||
378 | do_test table-8.6 { | ||
379 | execsql2 { | ||
380 | SELECT * FROM t2; | ||
381 | } | ||
382 | } {desc a asc b key 9 14_vac 0 fuzzy_dog_12 xyz begin hi end y'all} | ||
383 | do_test table-8.7 { | ||
384 | catchsql { | ||
385 | SELECT * FROM t5; | ||
386 | } | ||
387 | } {1 {no such table: t5}} | ||
388 | do_test table-8.8 { | ||
389 | catchsql { | ||
390 | CREATE TABLE t5 AS SELECT * FROM no_such_table; | ||
391 | } | ||
392 | } {1 {no such table: no_such_table}} | ||
393 | |||
394 | # Make sure we cannot have duplicate column names within a table. | ||
395 | # | ||
396 | do_test table-9.1 { | ||
397 | catchsql { | ||
398 | CREATE TABLE t6(a,b,a); | ||
399 | } | ||
400 | } {1 {duplicate column name: a}} | ||
401 | do_test table-9.2 { | ||
402 | catchsql { | ||
403 | CREATE TABLE t6(a varchar(100), b blob, a integer); | ||
404 | } | ||
405 | } {1 {duplicate column name: a}} | ||
406 | |||
407 | # Check the foreign key syntax. | ||
408 | # | ||
409 | ifcapable {foreignkey} { | ||
410 | do_test table-10.1 { | ||
411 | catchsql { | ||
412 | CREATE TABLE t6(a REFERENCES t4(a) NOT NULL); | ||
413 | INSERT INTO t6 VALUES(NULL); | ||
414 | } | ||
415 | } {1 {t6.a may not be NULL}} | ||
416 | do_test table-10.2 { | ||
417 | catchsql { | ||
418 | DROP TABLE t6; | ||
419 | CREATE TABLE t6(a REFERENCES t4(a) MATCH PARTIAL); | ||
420 | } | ||
421 | } {0 {}} | ||
422 | do_test table-10.3 { | ||
423 | catchsql { | ||
424 | DROP TABLE t6; | ||
425 | CREATE TABLE t6(a REFERENCES t4 MATCH FULL ON DELETE SET NULL NOT NULL); | ||
426 | } | ||
427 | } {0 {}} | ||
428 | do_test table-10.4 { | ||
429 | catchsql { | ||
430 | DROP TABLE t6; | ||
431 | CREATE TABLE t6(a REFERENCES t4 MATCH FULL ON UPDATE SET DEFAULT DEFAULT 1); | ||
432 | } | ||
433 | } {0 {}} | ||
434 | do_test table-10.5 { | ||
435 | catchsql { | ||
436 | DROP TABLE t6; | ||
437 | CREATE TABLE t6(a NOT NULL NOT DEFERRABLE INITIALLY IMMEDIATE); | ||
438 | } | ||
439 | } {0 {}} | ||
440 | do_test table-10.6 { | ||
441 | catchsql { | ||
442 | DROP TABLE t6; | ||
443 | CREATE TABLE t6(a NOT NULL DEFERRABLE INITIALLY DEFERRED); | ||
444 | } | ||
445 | } {0 {}} | ||
446 | do_test table-10.7 { | ||
447 | catchsql { | ||
448 | DROP TABLE t6; | ||
449 | CREATE TABLE t6(a, | ||
450 | FOREIGN KEY (a) REFERENCES t4(b) DEFERRABLE INITIALLY DEFERRED | ||
451 | ); | ||
452 | } | ||
453 | } {0 {}} | ||
454 | do_test table-10.8 { | ||
455 | catchsql { | ||
456 | DROP TABLE t6; | ||
457 | CREATE TABLE t6(a,b,c, | ||
458 | FOREIGN KEY (b,c) REFERENCES t4(x,y) MATCH PARTIAL | ||
459 | ON UPDATE SET NULL ON DELETE CASCADE DEFERRABLE INITIALLY DEFERRED | ||
460 | ); | ||
461 | } | ||
462 | } {0 {}} | ||
463 | do_test table-10.9 { | ||
464 | catchsql { | ||
465 | DROP TABLE t6; | ||
466 | CREATE TABLE t6(a,b,c, | ||
467 | FOREIGN KEY (b,c) REFERENCES t4(x) | ||
468 | ); | ||
469 | } | ||
470 | } {1 {number of columns in foreign key does not match the number of columns in the referenced table}} | ||
471 | do_test table-10.10 { | ||
472 | catchsql {DROP TABLE t6} | ||
473 | catchsql { | ||
474 | CREATE TABLE t6(a,b,c, | ||
475 | FOREIGN KEY (b,c) REFERENCES t4(x,y,z) | ||
476 | ); | ||
477 | } | ||
478 | } {1 {number of columns in foreign key does not match the number of columns in the referenced table}} | ||
479 | do_test table-10.11 { | ||
480 | catchsql {DROP TABLE t6} | ||
481 | catchsql { | ||
482 | CREATE TABLE t6(a,b, c REFERENCES t4(x,y)); | ||
483 | } | ||
484 | } {1 {foreign key on c should reference only one column of table t4}} | ||
485 | do_test table-10.12 { | ||
486 | catchsql {DROP TABLE t6} | ||
487 | catchsql { | ||
488 | CREATE TABLE t6(a,b,c, | ||
489 | FOREIGN KEY (b,x) REFERENCES t4(x,y) | ||
490 | ); | ||
491 | } | ||
492 | } {1 {unknown column "x" in foreign key definition}} | ||
493 | do_test table-10.13 { | ||
494 | catchsql {DROP TABLE t6} | ||
495 | catchsql { | ||
496 | CREATE TABLE t6(a,b,c, | ||
497 | FOREIGN KEY (x,b) REFERENCES t4(x,y) | ||
498 | ); | ||
499 | } | ||
500 | } {1 {unknown column "x" in foreign key definition}} | ||
501 | } ;# endif foreignkey | ||
502 | |||
503 | # Test for the "typeof" function. More tests for the | ||
504 | # typeof() function are found in bind.test and types.test. | ||
505 | # | ||
506 | do_test table-11.1 { | ||
507 | execsql { | ||
508 | CREATE TABLE t7( | ||
509 | a integer primary key, | ||
510 | b number(5,10), | ||
511 | c character varying (8), | ||
512 | d VARCHAR(9), | ||
513 | e clob, | ||
514 | f BLOB, | ||
515 | g Text, | ||
516 | h | ||
517 | ); | ||
518 | INSERT INTO t7(a) VALUES(1); | ||
519 | SELECT typeof(a), typeof(b), typeof(c), typeof(d), | ||
520 | typeof(e), typeof(f), typeof(g), typeof(h) | ||
521 | FROM t7 LIMIT 1; | ||
522 | } | ||
523 | } {integer null null null null null null null} | ||
524 | do_test table-11.2 { | ||
525 | execsql { | ||
526 | SELECT typeof(a+b), typeof(a||b), typeof(c+d), typeof(c||d) | ||
527 | FROM t7 LIMIT 1; | ||
528 | } | ||
529 | } {null null null null} | ||
530 | |||
531 | # Test that when creating a table using CREATE TABLE AS, column types are | ||
532 | # assigned correctly for (SELECT ...) and 'x AS y' expressions. | ||
533 | do_test table-12.1 { | ||
534 | ifcapable subquery { | ||
535 | execsql { | ||
536 | CREATE TABLE t8 AS SELECT b, h, a as i, (SELECT f FROM t7) as j FROM t7; | ||
537 | } | ||
538 | } else { | ||
539 | execsql { | ||
540 | CREATE TABLE t8 AS SELECT b, h, a as i, f as j FROM t7; | ||
541 | } | ||
542 | } | ||
543 | } {} | ||
544 | do_test table-12.2 { | ||
545 | execsql { | ||
546 | SELECT sql FROM sqlite_master WHERE tbl_name = 't8' | ||
547 | } | ||
548 | } {{CREATE TABLE t8(b number(5,10),h,i integer,j BLOB)}} | ||
549 | |||
550 | #-------------------------------------------------------------------- | ||
551 | # Test cases table-13.* | ||
552 | # | ||
553 | # Test the ability to have default values of CURRENT_TIME, CURRENT_DATE | ||
554 | # and CURRENT_TIMESTAMP. | ||
555 | # | ||
556 | do_test table-13.1 { | ||
557 | execsql { | ||
558 | CREATE TABLE tablet8( | ||
559 | a integer primary key, | ||
560 | tm text DEFAULT CURRENT_TIME, | ||
561 | dt text DEFAULT CURRENT_DATE, | ||
562 | dttm text DEFAULT CURRENT_TIMESTAMP | ||
563 | ); | ||
564 | SELECT * FROM tablet8; | ||
565 | } | ||
566 | } {} | ||
567 | set i 0 | ||
568 | foreach {date time seconds} { | ||
569 | 1976-07-04 12:00:00 205329600 | ||
570 | 1994-04-16 14:00:00 766504800 | ||
571 | 2000-01-01 00:00:00 946684800 | ||
572 | 2003-12-31 12:34:56 1072874096 | ||
573 | } { | ||
574 | incr i | ||
575 | set sqlite_current_time $seconds | ||
576 | do_test table-13.2.$i { | ||
577 | execsql " | ||
578 | INSERT INTO tablet8(a) VALUES($i); | ||
579 | SELECT tm, dt, dttm FROM tablet8 WHERE a=$i; | ||
580 | " | ||
581 | } [list $time $date [list $date $time]] | ||
582 | } | ||
583 | set sqlite_current_time 0 | ||
584 | |||
585 | #-------------------------------------------------------------------- | ||
586 | # Test cases table-14.* | ||
587 | # | ||
588 | # Test that a table cannot be created or dropped while other virtual | ||
589 | # machines are active. This is required because otherwise when in | ||
590 | # auto-vacuum mode the btree-layer may need to move the root-pages of | ||
591 | # a table for which there is an open cursor. | ||
592 | # | ||
593 | # 2007-05-02: A open btree cursor no longer blocks CREATE TABLE. | ||
594 | # But DROP TABLE is still prohibited because we do not want to | ||
595 | # delete a table out from under a running query. | ||
596 | # | ||
597 | |||
598 | # db eval { | ||
599 | # pragma vdbe_trace = 0; | ||
600 | # } | ||
601 | # Try to create a table from within a callback: | ||
602 | unset -nocomplain result | ||
603 | do_test table-14.1 { | ||
604 | set rc [ | ||
605 | catch { | ||
606 | db eval {SELECT * FROM tablet8 LIMIT 1} {} { | ||
607 | db eval {CREATE TABLE t9(a, b, c)} | ||
608 | } | ||
609 | } msg | ||
610 | ] | ||
611 | set result [list $rc $msg] | ||
612 | } {0 {}} | ||
613 | |||
614 | # Try to drop a table from within a callback: | ||
615 | do_test table-14.3 { | ||
616 | set rc [ | ||
617 | catch { | ||
618 | db eval {SELECT * FROM tablet8 LIMIT 1} {} { | ||
619 | db eval {DROP TABLE t9;} | ||
620 | } | ||
621 | } msg | ||
622 | ] | ||
623 | set result [list $rc $msg] | ||
624 | } {1 {database table is locked}} | ||
625 | |||
626 | # Now attach a database and ensure that a table can be created in the | ||
627 | # attached database whilst in a callback from a query on the main database. | ||
628 | do_test table-14.4 { | ||
629 | file delete -force test2.db | ||
630 | file delete -force test2.db-journal | ||
631 | execsql { | ||
632 | attach 'test2.db' as aux; | ||
633 | } | ||
634 | db eval {SELECT * FROM tablet8 LIMIT 1} {} { | ||
635 | db eval {CREATE TABLE aux.t1(a, b, c)} | ||
636 | } | ||
637 | } {} | ||
638 | |||
639 | # On the other hand, it should be impossible to drop a table when any VMs | ||
640 | # are active. This is because VerifyCookie instructions may have already | ||
641 | # been executed, and btree root-pages may not move after this (which a | ||
642 | # delete table might do). | ||
643 | do_test table-14.4 { | ||
644 | set rc [ | ||
645 | catch { | ||
646 | db eval {SELECT * FROM tablet8 LIMIT 1} {} { | ||
647 | db eval {DROP TABLE aux.t1;} | ||
648 | } | ||
649 | } msg | ||
650 | ] | ||
651 | set result [list $rc $msg] | ||
652 | } {1 {database table is locked}} | ||
653 | |||
654 | # Create and drop 2000 tables. This is to check that the balance_shallow() | ||
655 | # routine works correctly on the sqlite_master table. At one point it | ||
656 | # contained a bug that would prevent the right-child pointer of the | ||
657 | # child page from being copied to the root page. | ||
658 | # | ||
659 | do_test table-15.1 { | ||
660 | execsql {BEGIN} | ||
661 | for {set i 0} {$i<2000} {incr i} { | ||
662 | execsql "CREATE TABLE tbl$i (a, b, c)" | ||
663 | } | ||
664 | execsql {COMMIT} | ||
665 | } {} | ||
666 | do_test table-15.2 { | ||
667 | execsql {BEGIN} | ||
668 | for {set i 0} {$i<2000} {incr i} { | ||
669 | execsql "DROP TABLE tbl$i" | ||
670 | } | ||
671 | execsql {COMMIT} | ||
672 | } {} | ||
673 | |||
674 | finish_test | ||